]> git.lizzy.rs Git - rust.git/commitdiff
Rollup merge of #61279 - llogiq:implicit-option-main-doctests, r=GuillaumeGomez
authorMazdak Farrokhzad <twingoow@gmail.com>
Thu, 30 May 2019 08:52:56 +0000 (10:52 +0200)
committerGitHub <noreply@github.com>
Thu, 30 May 2019 08:52:56 +0000 (10:52 +0200)
implicit `Option`-returning doctests

This distinguishes `Option` and `Result`-returning doctests with implicit `main` method, where the former tests must end with `Some(())`.

Open question: Does this need a feature gate?

r? @GuillaumeGomez

1110 files changed:
.mailmap
Cargo.lock
src/bootstrap/builder.rs
src/bootstrap/compile.rs
src/bootstrap/dist.rs
src/bootstrap/doc.rs
src/bootstrap/install.rs
src/bootstrap/test.rs
src/bootstrap/tool.rs
src/doc/unstable-book/src/library-features/borrow-state.md [deleted file]
src/liballoc/rc.rs
src/liballoc/slice.rs
src/liballoc/sync.rs
src/libcore/cell.rs
src/libcore/iter/range.rs
src/libcore/iter/traits/accum.rs
src/libcore/mem.rs [deleted file]
src/libcore/mem/manually_drop.rs [new file with mode: 0644]
src/libcore/mem/maybe_uninit.rs [new file with mode: 0644]
src/libcore/mem/mod.rs [new file with mode: 0644]
src/libcore/ptr.rs [deleted file]
src/libcore/ptr/mod.rs [new file with mode: 0644]
src/libcore/ptr/non_null.rs [new file with mode: 0644]
src/libcore/ptr/unique.rs [new file with mode: 0644]
src/libcore/slice/mod.rs
src/libcore/tests/iter.rs
src/libcore/tests/slice.rs
src/librustc/hir/mod.rs
src/librustc/infer/error_reporting/mod.rs
src/librustc/infer/error_reporting/need_type_info.rs
src/librustc/infer/error_reporting/nice_region_error/placeholder_error.rs
src/librustc/infer/fudge.rs
src/librustc/infer/mod.rs
src/librustc/infer/opaque_types/mod.rs
src/librustc/infer/outlives/env.rs
src/librustc/infer/outlives/obligations.rs
src/librustc/infer/resolve.rs
src/librustc/lint/builtin.rs
src/librustc/middle/mem_categorization.rs
src/librustc/middle/resolve_lifetime.rs
src/librustc/mir/cache.rs
src/librustc/mir/interpret/allocation.rs
src/librustc/mir/interpret/mod.rs
src/librustc/mir/interpret/pointer.rs
src/librustc/mir/interpret/value.rs
src/librustc/mir/mod.rs
src/librustc/mir/mono.rs
src/librustc/mir/traversal.rs
src/librustc/mir/visit.rs
src/librustc/query/mod.rs
src/librustc/session/config.rs
src/librustc/session/mod.rs
src/librustc/traits/auto_trait.rs
src/librustc/traits/chalk_fulfill.rs
src/librustc/traits/codegen/mod.rs
src/librustc/traits/coherence.rs
src/librustc/traits/error_reporting.rs
src/librustc/traits/fulfill.rs
src/librustc/traits/mod.rs
src/librustc/traits/project.rs
src/librustc/traits/query/dropck_outlives.rs
src/librustc/traits/query/type_op/custom.rs
src/librustc/traits/select.rs
src/librustc/traits/specialize/mod.rs
src/librustc/ty/context.rs
src/librustc/ty/error.rs
src/librustc/ty/mod.rs
src/librustc/ty/print/pretty.rs
src/librustc/ty/relate.rs
src/librustc/ty/steal.rs
src/librustc/ty/sty.rs
src/librustc/util/profiling.rs
src/librustc_codegen_llvm/back/write.rs
src/librustc_codegen_llvm/base.rs
src/librustc_codegen_llvm/builder.rs
src/librustc_codegen_llvm/common.rs
src/librustc_codegen_llvm/consts.rs
src/librustc_codegen_llvm/context.rs
src/librustc_codegen_llvm/debuginfo/create_scope_map.rs
src/librustc_codegen_llvm/debuginfo/mod.rs
src/librustc_codegen_llvm/lib.rs
src/librustc_codegen_ssa/back/write.rs
src/librustc_codegen_ssa/base.rs
src/librustc_codegen_ssa/mir/analyze.rs
src/librustc_codegen_ssa/mir/mod.rs
src/librustc_codegen_ssa/mir/place.rs
src/librustc_codegen_ssa/traits/backend.rs
src/librustc_codegen_ssa/traits/debuginfo.rs
src/librustc_codegen_ssa/traits/misc.rs
src/librustc_codegen_utils/symbol_names.rs
src/librustc_data_structures/indexed_vec.rs
src/librustc_errors/emitter.rs
src/librustc_macros/Cargo.toml
src/librustc_metadata/decoder.rs
src/librustc_metadata/encoder.rs
src/librustc_metadata/schema.rs
src/librustc_mir/borrow_check/borrow_set.rs
src/librustc_mir/borrow_check/conflict_errors.rs
src/librustc_mir/borrow_check/error_reporting.rs
src/librustc_mir/borrow_check/location.rs
src/librustc_mir/borrow_check/mod.rs
src/librustc_mir/borrow_check/mutability_errors.rs
src/librustc_mir/borrow_check/nll/constraint_generation.rs
src/librustc_mir/borrow_check/nll/explain_borrow/find_use.rs
src/librustc_mir/borrow_check/nll/explain_borrow/mod.rs
src/librustc_mir/borrow_check/nll/invalidation.rs
src/librustc_mir/borrow_check/nll/mod.rs
src/librustc_mir/borrow_check/nll/region_infer/error_reporting/mod.rs
src/librustc_mir/borrow_check/nll/region_infer/error_reporting/region_name.rs
src/librustc_mir/borrow_check/nll/region_infer/error_reporting/var_name.rs
src/librustc_mir/borrow_check/nll/region_infer/mod.rs
src/librustc_mir/borrow_check/nll/region_infer/values.rs
src/librustc_mir/borrow_check/nll/renumber.rs
src/librustc_mir/borrow_check/nll/type_check/input_output.rs
src/librustc_mir/borrow_check/nll/type_check/liveness/local_use_map.rs
src/librustc_mir/borrow_check/nll/type_check/liveness/mod.rs
src/librustc_mir/borrow_check/nll/type_check/liveness/trace.rs
src/librustc_mir/borrow_check/nll/type_check/mod.rs
src/librustc_mir/borrow_check/path_utils.rs
src/librustc_mir/borrow_check/place_ext.rs
src/librustc_mir/borrow_check/places_conflict.rs
src/librustc_mir/borrow_check/prefixes.rs
src/librustc_mir/borrow_check/used_muts.rs
src/librustc_mir/build/expr/as_rvalue.rs
src/librustc_mir/build/mod.rs
src/librustc_mir/const_eval.rs
src/librustc_mir/dataflow/drop_flag_effects.rs
src/librustc_mir/dataflow/graphviz.rs
src/librustc_mir/dataflow/impls/borrowed_locals.rs
src/librustc_mir/dataflow/impls/borrows.rs
src/librustc_mir/dataflow/impls/mod.rs
src/librustc_mir/dataflow/impls/storage_liveness.rs
src/librustc_mir/dataflow/mod.rs
src/librustc_mir/dataflow/move_paths/builder.rs
src/librustc_mir/dataflow/move_paths/mod.rs
src/librustc_mir/hair/constant.rs
src/librustc_mir/hair/cx/mod.rs
src/librustc_mir/interpret/cast.rs
src/librustc_mir/interpret/eval_context.rs
src/librustc_mir/interpret/machine.rs
src/librustc_mir/interpret/memory.rs
src/librustc_mir/interpret/operand.rs
src/librustc_mir/interpret/place.rs
src/librustc_mir/interpret/snapshot.rs
src/librustc_mir/interpret/validity.rs
src/librustc_mir/lints.rs
src/librustc_mir/monomorphize/collector.rs
src/librustc_mir/shim.rs
src/librustc_mir/transform/add_call_guards.rs
src/librustc_mir/transform/add_moves_for_packed_drops.rs
src/librustc_mir/transform/add_retag.rs
src/librustc_mir/transform/check_unsafety.rs
src/librustc_mir/transform/cleanup_post_borrowck.rs
src/librustc_mir/transform/const_prop.rs
src/librustc_mir/transform/copy_prop.rs
src/librustc_mir/transform/deaggregator.rs
src/librustc_mir/transform/dump_mir.rs
src/librustc_mir/transform/elaborate_drops.rs
src/librustc_mir/transform/erase_regions.rs
src/librustc_mir/transform/generator.rs
src/librustc_mir/transform/inline.rs
src/librustc_mir/transform/instcombine.rs
src/librustc_mir/transform/lower_128bit.rs
src/librustc_mir/transform/mod.rs
src/librustc_mir/transform/no_landing_pads.rs
src/librustc_mir/transform/promote_consts.rs
src/librustc_mir/transform/qualify_consts.rs
src/librustc_mir/transform/qualify_min_const_fn.rs
src/librustc_mir/transform/remove_noop_landing_pads.rs
src/librustc_mir/transform/rustc_peek.rs
src/librustc_mir/transform/simplify.rs
src/librustc_mir/transform/simplify_branches.rs
src/librustc_mir/transform/uniform_array_move_out.rs
src/librustc_mir/util/collect_writes.rs
src/librustc_mir/util/def_use.rs
src/librustc_mir/util/elaborate_drops.rs
src/librustc_mir/util/graphviz.rs
src/librustc_mir/util/liveness.rs
src/librustc_mir/util/patch.rs
src/librustc_mir/util/pretty.rs
src/librustc_privacy/lib.rs
src/librustc_resolve/lib.rs
src/librustc_traits/chalk_context/mod.rs
src/librustc_traits/chalk_context/program_clauses/mod.rs
src/librustc_traits/chalk_context/resolvent_ops.rs
src/librustc_traits/implied_outlives_bounds.rs
src/librustc_traits/normalize_erasing_regions.rs
src/librustc_typeck/check/_match.rs
src/librustc_typeck/check/autoderef.rs
src/librustc_typeck/check/cast.rs
src/librustc_typeck/check/closure.rs
src/librustc_typeck/check/coercion.rs
src/librustc_typeck/check/demand.rs
src/librustc_typeck/check/generator_interior.rs
src/librustc_typeck/check/method/confirm.rs
src/librustc_typeck/check/method/mod.rs
src/librustc_typeck/check/method/probe.rs
src/librustc_typeck/check/method/suggest.rs
src/librustc_typeck/check/mod.rs
src/librustc_typeck/check/op.rs
src/librustc_typeck/check/regionck.rs
src/librustc_typeck/check/writeback.rs
src/librustc_typeck/collect.rs
src/librustdoc/Cargo.toml
src/librustdoc/clean/mod.rs
src/librustdoc/html/markdown.rs
src/librustdoc/test.rs
src/libstd/error.rs
src/libstd/fs.rs
src/libstd/io/buffered.rs
src/libstd/sys/redox/ext/fs.rs
src/libstd/sys/unix/ext/fs.rs
src/libsyntax/source_map.rs
src/test/codegen/pgo-instrumentation.rs
src/test/compile-fail/issue-23595-1.rs
src/test/run-make-fulldeps/pgo-gen-lto/Makefile
src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
src/test/run-make-fulldeps/pgo-gen/Makefile
src/test/run-make-fulldeps/pgo-use/Makefile
src/test/run-make-fulldeps/print-target-list/Makefile
src/test/run-pass-fulldeps/pprust-expr-roundtrip.rs
src/test/run-pass/alignment-gep-tup-like-1.rs
src/test/run-pass/associated-types/associated-types-doubleendediterator-object.rs
src/test/run-pass/associated-types/associated-types-eq-obj.rs
src/test/run-pass/associated-types/associated-types-projection-in-object-type.rs
src/test/run-pass/autoref-autoderef/autoderef-method-on-trait.rs
src/test/run-pass/borrowck/borrowck-trait-lifetime.rs
src/test/run-pass/cast-rfc0401-vtable-kinds.rs
src/test/run-pass/cast-rfc0401.rs
src/test/run-pass/close-over-big-then-small-data.rs
src/test/run-pass/codegen-object-shim.rs
src/test/run-pass/coerce/coerce-expect-unsized.rs
src/test/run-pass/consts/const-trait-to-trait.rs
src/test/run-pass/deriving/deriving-show.rs
src/test/run-pass/drop/drop-struct-as-object.rs
src/test/run-pass/dynamically-sized-types/dst-coerce-custom.rs
src/test/run-pass/dynamically-sized-types/dst-coerce-rc.rs
src/test/run-pass/dynamically-sized-types/dst-coercions.rs
src/test/run-pass/dynamically-sized-types/dst-field-align.rs
src/test/run-pass/dynamically-sized-types/dst-index.rs
src/test/run-pass/dynamically-sized-types/dst-raw.rs
src/test/run-pass/dynamically-sized-types/dst-trait-tuple.rs
src/test/run-pass/dynamically-sized-types/dst-trait.rs
src/test/run-pass/extern/extern-types-trait-impl.rs
src/test/run-pass/fat-ptr-cast.rs
src/test/run-pass/functions-closures/closure-expected-type/issue-38714.rs
src/test/run-pass/generics/generic-object.rs
src/test/run-pass/hashmap-memory.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-binder-levels-in-object-types.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-debruijn-object-types-in-closures.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-fn-like-trait-object.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-parse.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-precedence-of-plus.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-resolve-lifetime.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-trait-object-paren-notation.rs
src/test/run-pass/higher-rank-trait-bounds/hrtb-trait-object-passed-to-closure.rs
src/test/run-pass/ifmt.rs
src/test/run-pass/impl-trait/example-calendar.rs
src/test/run-pass/issues/issue-10802.rs
src/test/run-pass/issues/issue-11205.rs
src/test/run-pass/issues/issue-11267.rs
src/test/run-pass/issues/issue-11677.rs
src/test/run-pass/issues/issue-11709.rs
src/test/run-pass/issues/issue-12744.rs
src/test/run-pass/issues/issue-13507-2.rs
src/test/run-pass/issues/issue-13808.rs
src/test/run-pass/issues/issue-14399.rs
src/test/run-pass/issues/issue-14589.rs
src/test/run-pass/issues/issue-14821.rs
src/test/run-pass/issues/issue-14919.rs
src/test/run-pass/issues/issue-14958.rs
src/test/run-pass/issues/issue-15155.rs
src/test/run-pass/issues/issue-15763.rs
src/test/run-pass/issues/issue-16739.rs
src/test/run-pass/issues/issue-16922.rs
src/test/run-pass/issues/issue-17322.rs
src/test/run-pass/issues/issue-17351.rs
src/test/run-pass/issues/issue-17771.rs
src/test/run-pass/issues/issue-17897.rs
src/test/run-pass/issues/issue-20055-box-trait.rs
src/test/run-pass/issues/issue-20575.rs
src/test/run-pass/issues/issue-20676.rs
src/test/run-pass/issues/issue-20953.rs
src/test/run-pass/issues/issue-21058.rs
src/test/run-pass/issues/issue-21361.rs
src/test/run-pass/issues/issue-21655.rs
src/test/run-pass/issues/issue-2190-1.rs
src/test/run-pass/issues/issue-22346.rs
src/test/run-pass/issues/issue-2288.rs
src/test/run-pass/issues/issue-23261.rs
src/test/run-pass/issues/issue-23485.rs
src/test/run-pass/issues/issue-24010.rs
src/test/run-pass/issues/issue-24086.rs
src/test/run-pass/issues/issue-25339.rs
src/test/run-pass/issues/issue-25515.rs
src/test/run-pass/issues/issue-25549-multiple-drop.rs
src/test/run-pass/issues/issue-25757.rs
src/test/run-pass/issues/issue-26641.rs
src/test/run-pass/issues/issue-26709.rs
src/test/run-pass/issues/issue-26802.rs
src/test/run-pass/issues/issue-26805.rs
src/test/run-pass/issues/issue-26905.rs
src/test/run-pass/issues/issue-27268.rs
src/test/run-pass/issues/issue-2734.rs
src/test/run-pass/issues/issue-2735.rs
src/test/run-pass/issues/issue-27890.rs
src/test/run-pass/issues/issue-2935.rs
src/test/run-pass/issues/issue-3052.rs
src/test/run-pass/issues/issue-30530.rs
src/test/run-pass/issues/issue-30615.rs
src/test/run-pass/issues/issue-32389.rs
src/test/run-pass/issues/issue-33387.rs
src/test/run-pass/issues/issue-33461.rs
src/test/run-pass/issues/issue-34503.rs
src/test/run-pass/issues/issue-35815.rs
src/test/run-pass/issues/issue-36260.rs
src/test/run-pass/issues/issue-36786-resolve-call.rs
src/test/run-pass/issues/issue-3702.rs
src/test/run-pass/issues/issue-3794.rs
src/test/run-pass/issues/issue-39292.rs
src/test/run-pass/issues/issue-39823.rs
src/test/run-pass/issues/issue-41053.rs
src/test/run-pass/issues/issue-41744.rs
src/test/run-pass/issues/issue-42210.rs
src/test/run-pass/issues/issue-43132.rs
src/test/run-pass/issues/issue-4333.rs
src/test/run-pass/issues/issue-47638.rs
src/test/run-pass/issues/issue-5008-borrowed-traitobject-method-call.rs
src/test/run-pass/issues/issue-5192.rs
src/test/run-pass/issues/issue-5666.rs
src/test/run-pass/issues/issue-5708.rs
src/test/run-pass/issues/issue-5988.rs
src/test/run-pass/issues/issue-6128.rs
src/test/run-pass/issues/issue-6157.rs
src/test/run-pass/issues/issue-6318.rs
src/test/run-pass/issues/issue-7563.rs
src/test/run-pass/issues/issue-7911.rs
src/test/run-pass/issues/issue-8248.rs
src/test/run-pass/issues/issue-8249.rs
src/test/run-pass/issues/issue-9129.rs
src/test/run-pass/issues/issue-9394-inherited-trait-calls.rs
src/test/run-pass/issues/issue-9951.rs
src/test/run-pass/last-use-in-cap-clause.rs
src/test/run-pass/macros/colorful-write-macros.rs
src/test/run-pass/macros/type-macros-simple.rs
src/test/run-pass/methods/method-argument-inference-associated-type.rs
src/test/run-pass/mir/mir_codegen_calls.rs
src/test/run-pass/mir/mir_codegen_critical_edge.rs
src/test/run-pass/mir/mir_coercions.rs
src/test/run-pass/mir/mir_raw_fat_ptr.rs
src/test/run-pass/new-box.rs
src/test/run-pass/newlambdas-ret-infer.rs
src/test/run-pass/newlambdas-ret-infer2.rs
src/test/run-pass/object-lifetime-default-default-to-static.rs
src/test/run-pass/object-lifetime-default-from-rptr-box.rs
src/test/run-pass/object-lifetime-default-from-rptr-mut.rs
src/test/run-pass/object-lifetime-default-from-rptr.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/objects-owned-object-owned-method.rs
src/test/run-pass/overloaded/overloaded-calls-object-one-arg.rs
src/test/run-pass/overloaded/overloaded-calls-object-two-args.rs
src/test/run-pass/overloaded/overloaded-calls-object-zero-args.rs
src/test/run-pass/panics/panic-safe.rs
src/test/run-pass/privacy/privacy-ns.rs
src/test/run-pass/raw-fat-ptr.rs
src/test/run-pass/regions/regions-bound-lists-feature-gate.rs
src/test/run-pass/regions/regions-close-over-type-parameter-successfully.rs
src/test/run-pass/regions/regions-copy-closure.rs
src/test/run-pass/regions/regions-debruijn-of-object.rs
src/test/run-pass/regions/regions-early-bound-trait-param.rs
src/test/run-pass/regions/regions-fn-subtyping-2.rs
src/test/run-pass/regions/regions-fn-subtyping.rs
src/test/run-pass/regions/regions-infer-region-in-fn-but-not-type.rs
src/test/run-pass/regions/regions-lifetime-nonfree-late-bound.rs
src/test/run-pass/regions/regions-lub-ref-ref-rc.rs
src/test/run-pass/regions/regions-relate-bound-regions-on-closures-to-inference-variables.rs
src/test/run-pass/regions/regions-static-closure.rs
src/test/run-pass/regions/regions-trait-object-1.rs
src/test/run-pass/string-box-error.rs
src/test/run-pass/structs-enums/class-cast-to-trait-cross-crate-2.rs
src/test/run-pass/structs-enums/class-cast-to-trait-multiple-types.rs
src/test/run-pass/structs-enums/class-cast-to-trait.rs
src/test/run-pass/structs-enums/class-separate-impl.rs
src/test/run-pass/structs-enums/enum-null-pointer-opt.rs
src/test/run-pass/structs-enums/object-lifetime-default-from-ref-struct.rs
src/test/run-pass/structs-enums/object-lifetime-default-from-rptr-struct.rs
src/test/run-pass/traits/auto-traits.rs
src/test/run-pass/traits/impl-inherent-prefer-over-trait.rs
src/test/run-pass/traits/infer-from-object-trait-issue-26952.rs
src/test/run-pass/traits/kindck-owned-trait-contains-1.rs
src/test/run-pass/traits/object-one-type-two-traits.rs
src/test/run-pass/traits/parameterized-trait-with-bounds.rs
src/test/run-pass/traits/trait-bounds-basic.rs
src/test/run-pass/traits/trait-bounds-in-arc.rs
src/test/run-pass/traits/trait-bounds-on-structs-and-enums.rs
src/test/run-pass/traits/trait-coercion-generic.rs
src/test/run-pass/traits/trait-coercion.rs
src/test/run-pass/traits/trait-impl-2.rs
src/test/run-pass/traits/trait-impl.rs
src/test/run-pass/traits/trait-inheritance-cast-without-call-to-supertrait.rs
src/test/run-pass/traits/trait-inheritance-cast.rs
src/test/run-pass/traits/trait-object-exclusion.rs
src/test/run-pass/traits/trait-object-generics.rs
src/test/run-pass/traits/trait-object-lifetime-first.rs
src/test/run-pass/traits/trait-object-with-lifetime-bound.rs
src/test/run-pass/traits/trait-region-pointer-simple.rs
src/test/run-pass/traits/traits-impl-object-overlap-issue-23853.rs
src/test/run-pass/traits/traits-issue-26339.rs
src/test/run-pass/traits/traits-repeated-supertrait.rs
src/test/run-pass/traits/ufcs-trait-object.rs
src/test/run-pass/trivial_casts.rs
src/test/run-pass/type-id-higher-rank-2.rs
src/test/run-pass/type-id-higher-rank.rs
src/test/run-pass/type-infer-generalize-ty-var.rs
src/test/run-pass/unboxed-closures/unboxed-closures-blanket-fn-mut.rs
src/test/run-pass/unboxed-closures/unboxed-closures-blanket-fn.rs
src/test/run-pass/unboxed-closures/unboxed-closures-boxed.rs
src/test/run-pass/unboxed-closures/unboxed-closures-call-sugar-object-autoderef.rs
src/test/run-pass/unboxed-closures/unboxed-closures-call-sugar-object.rs
src/test/run-pass/unboxed-closures/unboxed-closures-extern-fn-hr.rs
src/test/run-pass/unboxed-closures/unboxed-closures-infer-arg-types-from-expected-object-type.rs
src/test/run-pass/unboxed-closures/unboxed-closures-infer-recursive-fn.rs
src/test/run-pass/unboxed-closures/unboxed-closures-manual-impl.rs
src/test/run-pass/unboxed-closures/unboxed-closures-monomorphization.rs
src/test/run-pass/unboxed-closures/unboxed-closures-prelude.rs
src/test/run-pass/unboxed-closures/unboxed-closures-sugar-object.rs
src/test/run-pass/unique/unique-object-move.rs
src/test/run-pass/unsized2.rs
src/test/run-pass/wf-bound-region-in-object-type.rs
src/test/rustdoc-ui/failed-doctest-compile-fail.rs [new file with mode: 0644]
src/test/rustdoc-ui/failed-doctest-compile-fail.stdout [new file with mode: 0644]
src/test/rustdoc-ui/failed-doctest-missing-codes.rs [new file with mode: 0644]
src/test/rustdoc-ui/failed-doctest-missing-codes.stdout [new file with mode: 0644]
src/test/rustdoc-ui/failed-doctest-output.rs
src/test/rustdoc-ui/failed-doctest-output.stdout
src/test/rustdoc-ui/failed-doctest-should-panic.rs [new file with mode: 0644]
src/test/rustdoc-ui/failed-doctest-should-panic.stdout [new file with mode: 0644]
src/test/rustdoc-ui/unparseable-doc-test.stdout
src/test/rustdoc/const-generics/add-impl.rs [new file with mode: 0644]
src/test/rustdoc/const-generics/const-impl.rs [new file with mode: 0644]
src/test/rustdoc/generic-const.rs [deleted file]
src/test/rustdoc/issue-60482.rs [new file with mode: 0644]
src/test/ui/anonymous-higher-ranked-lifetime.rs
src/test/ui/anonymous-higher-ranked-lifetime.stderr
src/test/ui/array-break-length.rs
src/test/ui/array-break-length.stderr
src/test/ui/associated-const/associated-const-in-trait.rs
src/test/ui/associated-const/associated-const-in-trait.stderr
src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.rs
src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr
src/test/ui/associated-types/associated-types-eq-3.rs
src/test/ui/associated-types/associated-types-incomplete-object.rs
src/test/ui/associated-types/associated-types-incomplete-object.stderr
src/test/ui/associated-types/associated-types-overridden-binding-2.rs
src/test/ui/associated-types/associated-types-overridden-binding-2.stderr
src/test/ui/associated-types/associated-types-overridden-binding.rs
src/test/ui/associated-types/bound-lifetime-constrained.object.stderr
src/test/ui/associated-types/bound-lifetime-constrained.rs
src/test/ui/associated-types/bound-lifetime-in-binding-only.angle.stderr
src/test/ui/associated-types/bound-lifetime-in-binding-only.paren.stderr
src/test/ui/associated-types/bound-lifetime-in-binding-only.rs
src/test/ui/associated-types/bound-lifetime-in-return-only.rs
src/test/ui/async-await/async-with-closure.rs
src/test/ui/async-await/issues/issue-53249.rs
src/test/ui/async-await/issues/issue-54974.rs
src/test/ui/bad/bad-sized.rs
src/test/ui/bad/bad-sized.stderr
src/test/ui/borrowck/borrowck-borrow-mut-object-twice.rs
src/test/ui/borrowck/borrowck-consume-upcast-box.rs
src/test/ui/borrowck/borrowck-consume-upcast-box.stderr
src/test/ui/borrowck/borrowck-escaping-closure-error-2.rs
src/test/ui/borrowck/borrowck-in-static.rs
src/test/ui/borrowck/borrowck-object-lifetime.rs
src/test/ui/borrowck/borrowck-use-uninitialized-in-cast-trait.rs
src/test/ui/borrowck/borrowck-use-uninitialized-in-cast-trait.stderr
src/test/ui/borrowck/regions-escape-unboxed-closure.rs
src/test/ui/borrowck/two-phase-nonrecv-autoref.nll.stderr
src/test/ui/borrowck/two-phase-nonrecv-autoref.rs
src/test/ui/bounds-lifetime.rs
src/test/ui/bounds-lifetime.stderr
src/test/ui/cast/cast-to-unsized-trait-object-suggestion.rs
src/test/ui/cast/cast-to-unsized-trait-object-suggestion.stderr
src/test/ui/casts-differing-anon.rs
src/test/ui/class-cast-to-trait.rs
src/test/ui/closure_context/issue-26046-fn-mut.rs
src/test/ui/closure_context/issue-26046-fn-once.rs
src/test/ui/closures/closure-array-break-length.rs
src/test/ui/closures/closure-array-break-length.stderr
src/test/ui/closures/closure-immutable-outer-variable.fixed
src/test/ui/closures/closure-immutable-outer-variable.rs
src/test/ui/codemap_tests/coherence-overlapping-inherent-impl-trait.rs
src/test/ui/codemap_tests/coherence-overlapping-inherent-impl-trait.stderr
src/test/ui/codemap_tests/two_files_data.rs
src/test/ui/coercion/coerce-expect-unsized-ascribed.rs
src/test/ui/coercion/coerce-expect-unsized-ascribed.stderr
src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.old.stderr
src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.re.stderr
src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.rs
src/test/ui/coherence/coherence-impl-trait-for-trait.old.stderr
src/test/ui/coherence/coherence-impl-trait-for-trait.re.stderr
src/test/ui/coherence/coherence-impl-trait-for-trait.rs
src/test/ui/confuse-field-and-method/issue-2392.rs
src/test/ui/confuse-field-and-method/issue-32128.rs
src/test/ui/const-generics/broken-mir-1.rs [new file with mode: 0644]
src/test/ui/const-generics/broken-mir-1.stderr [new file with mode: 0644]
src/test/ui/const-generics/broken-mir-2.rs [new file with mode: 0644]
src/test/ui/const-generics/broken-mir-2.stderr [new file with mode: 0644]
src/test/ui/const-generics/cannot-infer-type-for-const-param.rs
src/test/ui/const-generics/cannot-infer-type-for-const-param.stderr
src/test/ui/const-generics/fn-taking-const-generic-array.rs [new file with mode: 0644]
src/test/ui/const-generics/fn-taking-const-generic-array.stderr [new file with mode: 0644]
src/test/ui/const-generics/issue-60818-struct-constructors.rs [new file with mode: 0644]
src/test/ui/const-generics/issue-60818-struct-constructors.stderr [new file with mode: 0644]
src/test/ui/const-generics/uninferred-consts-during-codegen-1.rs [new file with mode: 0644]
src/test/ui/const-generics/uninferred-consts-during-codegen-1.stderr [new file with mode: 0644]
src/test/ui/const-generics/uninferred-consts-during-codegen-2.rs [new file with mode: 0644]
src/test/ui/const-generics/uninferred-consts-during-codegen-2.stderr [new file with mode: 0644]
src/test/ui/consts/const-array-oob-arith.rs
src/test/ui/consts/const-array-oob-arith.stderr
src/test/ui/consts/const-eval/const_transmute.rs
src/test/ui/consts/const-eval/issue-53401.rs
src/test/ui/consts/const-eval/ub-upvars.rs
src/test/ui/consts/const-eval/ub-upvars.stderr
src/test/ui/consts/const-eval/union-ub-fat-ptr.rs
src/test/ui/consts/const-eval/union-ub-fat-ptr.stderr
src/test/ui/consts/const-size_of-cycle.stderr
src/test/ui/consts/const-unsized.rs
src/test/ui/consts/const-unsized.stderr
src/test/ui/consts/min_const_fn/min_const_fn.nll.stderr
src/test/ui/consts/min_const_fn/min_const_fn.rs
src/test/ui/consts/min_const_fn/min_const_fn.stderr
src/test/ui/cross/cross-borrow-trait.rs
src/test/ui/cross/cross-borrow-trait.stderr
src/test/ui/custom-derive/auxiliary/plugin.rs [deleted file]
src/test/ui/custom-derive/derive-in-mod.rs [deleted file]
src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.rs [deleted file]
src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.stderr [deleted file]
src/test/ui/custom-derive/helper-attr-blocked-by-import.rs [deleted file]
src/test/ui/custom-derive/issue-36935.rs [deleted file]
src/test/ui/custom-derive/issue-36935.stderr [deleted file]
src/test/ui/custom-test-frameworks-simple.rs
src/test/ui/cycle-trait/cycle-trait-default-type-trait.rs
src/test/ui/cycle-trait/cycle-trait-default-type-trait.stderr
src/test/ui/destructure-trait-ref.rs
src/test/ui/destructure-trait-ref.stderr
src/test/ui/did_you_mean/E0178.rs
src/test/ui/did_you_mean/E0178.stderr
src/test/ui/did_you_mean/bad-assoc-ty.rs
src/test/ui/did_you_mean/bad-assoc-ty.stderr
src/test/ui/did_you_mean/issue-40006.rs
src/test/ui/did_you_mean/issue-40006.stderr
src/test/ui/did_you_mean/trait-object-reference-without-parens-suggestion.rs
src/test/ui/did_you_mean/trait-object-reference-without-parens-suggestion.stderr
src/test/ui/dropck/dropck_trait_cycle_checked.rs
src/test/ui/dropck/dropck_trait_cycle_checked.stderr
src/test/ui/dst/dst-bad-assign-2.rs
src/test/ui/dst/dst-bad-assign-3.rs
src/test/ui/dst/dst-bad-assign.rs
src/test/ui/dst/dst-bad-coerce1.rs
src/test/ui/dst/dst-bad-coerce1.stderr
src/test/ui/dst/dst-bad-coerce2.rs
src/test/ui/dst/dst-bad-coerce2.stderr
src/test/ui/dst/dst-bad-coerce3.rs
src/test/ui/dst/dst-bad-coerce3.stderr
src/test/ui/dst/dst-bad-coercions.rs
src/test/ui/dst/dst-bad-coercions.stderr
src/test/ui/dst/dst-index.rs
src/test/ui/dst/dst-object-from-unsized-type.rs
src/test/ui/dst/dst-object-from-unsized-type.stderr
src/test/ui/elide-errors-on-mismatched-tuple.rs
src/test/ui/error-codes/E0033-teach.rs
src/test/ui/error-codes/E0033-teach.stderr
src/test/ui/error-codes/E0033.rs
src/test/ui/error-codes/E0033.stderr
src/test/ui/error-codes/E0038.rs
src/test/ui/error-codes/E0038.stderr
src/test/ui/error-codes/E0120.rs
src/test/ui/error-codes/E0120.stderr
src/test/ui/error-codes/E0191.rs
src/test/ui/error-codes/E0191.stderr
src/test/ui/error-codes/E0220.rs
src/test/ui/error-codes/E0220.stderr
src/test/ui/error-codes/E0393.rs
src/test/ui/error-codes/E0393.stderr
src/test/ui/error-codes/E0478.rs
src/test/ui/error-codes/E0478.stderr
src/test/ui/error-codes/E0719.rs
src/test/ui/error-codes/E0719.stderr
src/test/ui/fat-ptr-cast.rs
src/test/ui/fat-ptr-cast.stderr
src/test/ui/feature-gates/feature-gate-trivial_bounds.rs
src/test/ui/feature-gates/feature-gate-trivial_bounds.stderr
src/test/ui/feature-gates/feature-gate-unsized_locals.rs
src/test/ui/feature-gates/feature-gate-unsized_locals.stderr
src/test/ui/feature-gates/feature-gate-unsized_tuple_coercion.rs
src/test/ui/feature-gates/feature-gate-unsized_tuple_coercion.stderr
src/test/ui/fn/fn-trait-formatting.rs
src/test/ui/fn/fn-trait-formatting.stderr
src/test/ui/higher-lifetime-bounds.rs
src/test/ui/higher-lifetime-bounds.stderr
src/test/ui/impl-trait/hidden-lifetimes.rs [new file with mode: 0644]
src/test/ui/impl-trait/hidden-lifetimes.stderr [new file with mode: 0644]
src/test/ui/impl-trait/multiple-lifetimes.rs [new file with mode: 0644]
src/test/ui/imports/extern-crate-used.rs
src/test/ui/in-band-lifetimes/mismatched_trait_impl-2.rs
src/test/ui/in-band-lifetimes/mismatched_trait_impl-2.stderr
src/test/ui/issue-53912.rs [new file with mode: 0644]
src/test/ui/issues/issue-10291.nll.stderr
src/test/ui/issues/issue-10291.rs
src/test/ui/issues/issue-10291.stderr
src/test/ui/issues/issue-10902.rs
src/test/ui/issues/issue-11374.rs
src/test/ui/issues/issue-11515.rs
src/test/ui/issues/issue-11612.rs
src/test/ui/issues/issue-12470.rs
src/test/ui/issues/issue-13033.rs
src/test/ui/issues/issue-13033.stderr
src/test/ui/issues/issue-13352.rs
src/test/ui/issues/issue-13853-2.rs
src/test/ui/issues/issue-13853-2.stderr
src/test/ui/issues/issue-14285.rs
src/test/ui/issues/issue-14285.stderr
src/test/ui/issues/issue-14366.rs
src/test/ui/issues/issue-14366.stderr
src/test/ui/issues/issue-14901.rs
src/test/ui/issues/issue-14959.rs
src/test/ui/issues/issue-16668.rs
src/test/ui/issues/issue-16922.rs
src/test/ui/issues/issue-16922.stderr
src/test/ui/issues/issue-16994.rs
src/test/ui/issues/issue-17441.rs
src/test/ui/issues/issue-17441.stderr
src/test/ui/issues/issue-17959.rs
src/test/ui/issues/issue-18107.rs
src/test/ui/issues/issue-18107.stderr
src/test/ui/issues/issue-18188.rs
src/test/ui/issues/issue-18446-2.rs
src/test/ui/issues/issue-18446.rs
src/test/ui/issues/issue-18783.rs
src/test/ui/issues/issue-18819.rs
src/test/ui/issues/issue-18819.stderr
src/test/ui/issues/issue-18919.rs
src/test/ui/issues/issue-18937.rs
src/test/ui/issues/issue-18959.rs
src/test/ui/issues/issue-18959.stderr
src/test/ui/issues/issue-18988.rs
src/test/ui/issues/issue-19380.rs
src/test/ui/issues/issue-19380.stderr
src/test/ui/issues/issue-19404.rs
src/test/ui/issues/issue-19482.rs
src/test/ui/issues/issue-19482.stderr
src/test/ui/issues/issue-19538.rs
src/test/ui/issues/issue-19538.stderr
src/test/ui/issues/issue-20396.rs
src/test/ui/issues/issue-20605.rs
src/test/ui/issues/issue-20692.rs
src/test/ui/issues/issue-20692.stderr
src/test/ui/issues/issue-20831-debruijn.rs
src/test/ui/issues/issue-20831-debruijn.stderr
src/test/ui/issues/issue-20939.rs
src/test/ui/issues/issue-20939.stderr
src/test/ui/issues/issue-21363.rs
src/test/ui/issues/issue-21950.rs
src/test/ui/issues/issue-21950.stderr
src/test/ui/issues/issue-22034.rs
src/test/ui/issues/issue-22034.stderr
src/test/ui/issues/issue-22289.rs
src/test/ui/issues/issue-22289.stderr
src/test/ui/issues/issue-22312.rs
src/test/ui/issues/issue-22312.stderr
src/test/ui/issues/issue-22370.rs
src/test/ui/issues/issue-22370.stderr
src/test/ui/issues/issue-22434.rs
src/test/ui/issues/issue-22434.stderr
src/test/ui/issues/issue-22560.rs
src/test/ui/issues/issue-22560.stderr
src/test/ui/issues/issue-22781.rs
src/test/ui/issues/issue-22872.rs
src/test/ui/issues/issue-22872.stderr
src/test/ui/issues/issue-23024.rs
src/test/ui/issues/issue-23024.stderr
src/test/ui/issues/issue-23041.rs
src/test/ui/issues/issue-23046.rs
src/test/ui/issues/issue-23281.rs
src/test/ui/issues/issue-23281.stderr
src/test/ui/issues/issue-24446.rs
src/test/ui/issues/issue-24446.stderr
src/test/ui/issues/issue-25180.rs
src/test/ui/issues/issue-26056.rs
src/test/ui/issues/issue-26056.stderr
src/test/ui/issues/issue-26638.rs
src/test/ui/issues/issue-26638.stderr
src/test/ui/issues/issue-26905.rs
src/test/ui/issues/issue-27105.rs
src/test/ui/issues/issue-28279.rs
src/test/ui/issues/issue-28576.rs
src/test/ui/issues/issue-28576.stderr
src/test/ui/issues/issue-2904.rs
src/test/ui/issues/issue-32963.rs
src/test/ui/issues/issue-32963.stderr
src/test/ui/issues/issue-32995.rs
src/test/ui/issues/issue-32995.stderr
src/test/ui/issues/issue-33140-traitobject-crate.rs
src/test/ui/issues/issue-33140-traitobject-crate.stderr
src/test/ui/issues/issue-33140.rs
src/test/ui/issues/issue-33241.rs
src/test/ui/issues/issue-3424.rs
src/test/ui/issues/issue-35139.rs
src/test/ui/issues/issue-35546.rs
src/test/ui/issues/issue-35570.rs
src/test/ui/issues/issue-35976.rs
src/test/ui/issues/issue-3609.rs
src/test/ui/issues/issue-36839.rs
src/test/ui/issues/issue-3702-2.rs
src/test/ui/issues/issue-37515.rs
src/test/ui/issues/issue-37515.stderr
src/test/ui/issues/issue-38404.rs
src/test/ui/issues/issue-38404.stderr
src/test/ui/issues/issue-38604.rs
src/test/ui/issues/issue-38604.stderr
src/test/ui/issues/issue-40000.rs
src/test/ui/issues/issue-41139.rs
src/test/ui/issues/issue-41139.stderr
src/test/ui/issues/issue-42312.rs
src/test/ui/issues/issue-42312.stderr
src/test/ui/issues/issue-4335.rs
src/test/ui/issues/issue-4335.stderr
src/test/ui/issues/issue-45730.rs
src/test/ui/issues/issue-4972.rs
src/test/ui/issues/issue-50761.rs
src/test/ui/issues/issue-50781.rs
src/test/ui/issues/issue-5153.rs
src/test/ui/issues/issue-5153.stderr
src/test/ui/issues/issue-5216.rs
src/test/ui/issues/issue-53419.rs
src/test/ui/issues/issue-54582.rs
src/test/ui/issues/issue-55796.rs
src/test/ui/issues/issue-5883.rs
src/test/ui/issues/issue-5883.stderr
src/test/ui/issues/issue-60989.rs
src/test/ui/issues/issue-60989.stderr
src/test/ui/issues/issue-7013.rs
src/test/ui/issues/issue-7013.stderr
src/test/ui/issues/issue-7673-cast-generically-implemented-trait.rs
src/test/ui/issues/issue-8398.rs
src/test/ui/issues/issue-9719.rs
src/test/ui/kindck/kindck-copy.rs
src/test/ui/kindck/kindck-copy.stderr
src/test/ui/kindck/kindck-impl-type-params.nll.stderr
src/test/ui/kindck/kindck-impl-type-params.rs
src/test/ui/kindck/kindck-impl-type-params.stderr
src/test/ui/kindck/kindck-inherited-copy-bound.rs
src/test/ui/kindck/kindck-inherited-copy-bound.stderr
src/test/ui/kindck/kindck-send-object.rs
src/test/ui/kindck/kindck-send-object.stderr
src/test/ui/kindck/kindck-send-object1.nll.stderr
src/test/ui/kindck/kindck-send-object1.rs
src/test/ui/kindck/kindck-send-object1.stderr
src/test/ui/kindck/kindck-send-object2.rs
src/test/ui/kindck/kindck-send-object2.stderr
src/test/ui/lifetimes/lifetime-bound-will-change-warning.nll.stderr
src/test/ui/lifetimes/lifetime-bound-will-change-warning.rs
src/test/ui/lifetimes/lifetime-bound-will-change-warning.stderr
src/test/ui/lifetimes/lifetime-elision-return-type-trait.rs
src/test/ui/lifetimes/lifetime-elision-return-type-trait.stderr
src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-using-trait-objects.nll.stderr
src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-using-trait-objects.rs
src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-using-trait-objects.stderr
src/test/ui/linkage-attr/auxiliary/def_colliding_external.rs [new file with mode: 0644]
src/test/ui/linkage-attr/auxiliary/def_illtyped_external.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.stderr [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.stderr [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-requires-raw-ptr.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage-requires-raw-ptr.stderr [new file with mode: 0644]
src/test/ui/linkage-attr/linkage2.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage2.stderr [new file with mode: 0644]
src/test/ui/linkage-attr/linkage3.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage3.stderr [new file with mode: 0644]
src/test/ui/linkage-attr/linkage4.rs [new file with mode: 0644]
src/test/ui/linkage-attr/linkage4.stderr [new file with mode: 0644]
src/test/ui/linkage2.rs [deleted file]
src/test/ui/linkage2.stderr [deleted file]
src/test/ui/linkage3.rs [deleted file]
src/test/ui/linkage3.stderr [deleted file]
src/test/ui/linkage4.rs [deleted file]
src/test/ui/linkage4.stderr [deleted file]
src/test/ui/lint/lint-ctypes.rs
src/test/ui/lint/lint-ctypes.stderr
src/test/ui/lint/lint-dead-code-3.rs
src/test/ui/lint/lint-stability-2.rs
src/test/ui/lint/lint-stability-deprecated.rs
src/test/ui/lint/lint-stability.rs
src/test/ui/lint/lint-unconditional-recursion.rs
src/test/ui/loops/loops-reject-lifetime-shadowing-label.rs
src/test/ui/loops/loops-reject-lifetime-shadowing-label.stderr
src/test/ui/lub-glb/old-lub-glb-object.rs
src/test/ui/map-types.rs
src/test/ui/map-types.stderr
src/test/ui/methods/method-call-lifetime-args-lint-fail.rs
src/test/ui/mismatched_types/cast-rfc0401.rs
src/test/ui/mismatched_types/cast-rfc0401.stderr
src/test/ui/mismatched_types/issue-19109.rs
src/test/ui/mismatched_types/issue-19109.stderr
src/test/ui/mismatched_types/trait-bounds-cant-coerce.rs
src/test/ui/moves/moves-based-on-type-no-recursive-stack-closure.rs
src/test/ui/nll/issue-52663-trait-object.rs
src/test/ui/nll/issue-52663-trait-object.stderr
src/test/ui/nll/issue-53570.rs
src/test/ui/object-does-not-impl-trait.rs
src/test/ui/object-does-not-impl-trait.stderr
src/test/ui/object-lifetime/object-lifetime-default-ambiguous.rs
src/test/ui/object-lifetime/object-lifetime-default-ambiguous.stderr
src/test/ui/object-lifetime/object-lifetime-default-elision.nll.stderr
src/test/ui/object-lifetime/object-lifetime-default-elision.rs
src/test/ui/object-lifetime/object-lifetime-default-elision.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-box-error.nll.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-box-error.rs
src/test/ui/object-lifetime/object-lifetime-default-from-box-error.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-box-error.nll.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-box-error.rs
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-box-error.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-struct-error.nll.stderr
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-struct-error.rs
src/test/ui/object-lifetime/object-lifetime-default-from-rptr-struct-error.stderr
src/test/ui/object-lifetime/object-lifetime-default-mybox.nll.stderr
src/test/ui/object-lifetime/object-lifetime-default-mybox.rs
src/test/ui/object-lifetime/object-lifetime-default-mybox.stderr
src/test/ui/object-pointer-types.rs
src/test/ui/object-safety/object-safety-associated-consts.rs
src/test/ui/object-safety/object-safety-associated-consts.stderr
src/test/ui/object-safety/object-safety-by-value-self-use.rs
src/test/ui/object-safety/object-safety-by-value-self.rs
src/test/ui/object-safety/object-safety-generics.rs
src/test/ui/object-safety/object-safety-generics.stderr
src/test/ui/object-safety/object-safety-issue-22040.rs
src/test/ui/object-safety/object-safety-issue-22040.stderr
src/test/ui/object-safety/object-safety-mentions-Self.rs
src/test/ui/object-safety/object-safety-mentions-Self.stderr
src/test/ui/object-safety/object-safety-no-static.rs
src/test/ui/object-safety/object-safety-no-static.stderr
src/test/ui/object-safety/object-safety-phantom-fn.rs
src/test/ui/object-safety/object-safety-sized-2.rs
src/test/ui/object-safety/object-safety-sized-2.stderr
src/test/ui/object-safety/object-safety-sized.rs
src/test/ui/object-safety/object-safety-sized.stderr
src/test/ui/object-safety/object-safety-supertrait-mentions-Self.rs
src/test/ui/object-safety/object-safety-supertrait-mentions-Self.stderr
src/test/ui/parser/bounds-obj-parens.rs
src/test/ui/parser/trailing-plus-in-bounds.rs
src/test/ui/parser/trait-object-bad-parens.rs
src/test/ui/parser/trait-object-bad-parens.stderr
src/test/ui/parser/trait-object-lifetime-parens.rs
src/test/ui/parser/trait-object-lifetime-parens.stderr
src/test/ui/parser/trait-object-polytrait-priority.rs
src/test/ui/parser/trait-object-polytrait-priority.stderr
src/test/ui/parser/trait-object-trait-parens.rs
src/test/ui/parser/trait-object-trait-parens.stderr
src/test/ui/privacy/private-in-public-non-principal-2.rs
src/test/ui/privacy/private-in-public-non-principal.rs
src/test/ui/privacy/private-in-public-non-principal.stderr
src/test/ui/privacy/private-inferred-type.rs
src/test/ui/proc-macro/attribute-order-restricted.rs
src/test/ui/proc-macro/attribute-order-restricted.stderr
src/test/ui/proc-macro/attribute-with-error.rs
src/test/ui/proc-macro/attribute-with-error.stderr
src/test/ui/proc-macro/auxiliary/attr_proc_macro.rs [deleted file]
src/test/ui/proc-macro/auxiliary/attribute-with-error.rs [deleted file]
src/test/ui/proc-macro/auxiliary/bang_proc_macro.rs [deleted file]
src/test/ui/proc-macro/auxiliary/derive-a-b.rs [deleted file]
src/test/ui/proc-macro/auxiliary/derive-a.rs [deleted file]
src/test/ui/proc-macro/auxiliary/derive-helper-shadowed-2.rs
src/test/ui/proc-macro/auxiliary/derive-helper-shadowed.rs [deleted file]
src/test/ui/proc-macro/auxiliary/derive-helper-shadowing.rs [deleted file]
src/test/ui/proc-macro/auxiliary/derive-panic.rs [deleted file]
src/test/ui/proc-macro/auxiliary/dollar-crate-external.rs
src/test/ui/proc-macro/auxiliary/dollar-crate.rs [deleted file]
src/test/ui/proc-macro/auxiliary/issue-41211.rs [deleted file]
src/test/ui/proc-macro/auxiliary/issue-53481.rs [deleted file]
src/test/ui/proc-macro/auxiliary/macro-brackets.rs [deleted file]
src/test/ui/proc-macro/auxiliary/nested-item-spans.rs [deleted file]
src/test/ui/proc-macro/auxiliary/proc-macro-gates.rs [deleted file]
src/test/ui/proc-macro/auxiliary/span-preservation.rs [deleted file]
src/test/ui/proc-macro/auxiliary/test-macros.rs
src/test/ui/proc-macro/derive-helper-shadowed.rs
src/test/ui/proc-macro/derive-helper-shadowing.rs
src/test/ui/proc-macro/derive-helper-shadowing.stderr
src/test/ui/proc-macro/derive-in-mod.rs [new file with mode: 0644]
src/test/ui/proc-macro/derive-still-gated.rs
src/test/ui/proc-macro/derive-still-gated.stderr
src/test/ui/proc-macro/dollar-crate-issue-57089.rs
src/test/ui/proc-macro/dollar-crate-issue-57089.stdout
src/test/ui/proc-macro/dollar-crate.rs
src/test/ui/proc-macro/dollar-crate.stderr
src/test/ui/proc-macro/dollar-crate.stdout
src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.rs [new file with mode: 0644]
src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.stderr [new file with mode: 0644]
src/test/ui/proc-macro/helper-attr-blocked-by-import.rs [new file with mode: 0644]
src/test/ui/proc-macro/import.rs
src/test/ui/proc-macro/import.stderr
src/test/ui/proc-macro/issue-36935.rs [new file with mode: 0644]
src/test/ui/proc-macro/issue-36935.stderr [new file with mode: 0644]
src/test/ui/proc-macro/issue-37788.rs
src/test/ui/proc-macro/issue-41211.rs
src/test/ui/proc-macro/issue-41211.stderr
src/test/ui/proc-macro/issue-53481.rs
src/test/ui/proc-macro/load-panic.rs
src/test/ui/proc-macro/load-panic.stderr
src/test/ui/proc-macro/macro-brackets.rs
src/test/ui/proc-macro/macro-use-attr.rs
src/test/ui/proc-macro/macro-use-bang.rs
src/test/ui/proc-macro/macros-in-extern.rs
src/test/ui/proc-macro/macros-in-extern.stderr
src/test/ui/proc-macro/nested-item-spans.rs
src/test/ui/proc-macro/nested-item-spans.stderr
src/test/ui/proc-macro/no-macro-use-attr.rs
src/test/ui/proc-macro/no-macro-use-attr.stderr
src/test/ui/proc-macro/proc-macro-gates.rs
src/test/ui/proc-macro/proc-macro-gates.stderr
src/test/ui/proc-macro/proc-macro-gates2.rs
src/test/ui/proc-macro/proc-macro-gates2.stderr
src/test/ui/proc-macro/resolve-error.rs
src/test/ui/proc-macro/resolve-error.stderr
src/test/ui/proc-macro/shadow.rs
src/test/ui/proc-macro/shadow.stderr
src/test/ui/proc-macro/span-preservation.rs
src/test/ui/proc-macro/span-preservation.stderr
src/test/ui/regions/region-borrow-params-issue-29793-small.rs
src/test/ui/regions/region-bounds-on-objects-and-type-parameters.rs
src/test/ui/regions/region-bounds-on-objects-and-type-parameters.stderr
src/test/ui/regions/region-object-lifetime-2.nll.stderr
src/test/ui/regions/region-object-lifetime-2.rs
src/test/ui/regions/region-object-lifetime-2.stderr
src/test/ui/regions/region-object-lifetime-4.nll.stderr
src/test/ui/regions/region-object-lifetime-4.rs
src/test/ui/regions/region-object-lifetime-4.stderr
src/test/ui/regions/region-object-lifetime-5.rs
src/test/ui/regions/region-object-lifetime-in-coercion.nll.stderr
src/test/ui/regions/region-object-lifetime-in-coercion.rs
src/test/ui/regions/region-object-lifetime-in-coercion.stderr
src/test/ui/regions/regions-close-associated-type-into-object.rs
src/test/ui/regions/regions-close-object-into-object-2.nll.stderr
src/test/ui/regions/regions-close-object-into-object-2.rs
src/test/ui/regions/regions-close-object-into-object-2.stderr
src/test/ui/regions/regions-close-object-into-object-4.nll.stderr
src/test/ui/regions/regions-close-object-into-object-4.rs
src/test/ui/regions/regions-close-object-into-object-4.stderr
src/test/ui/regions/regions-close-over-type-parameter-1.nll.stderr
src/test/ui/regions/regions-close-over-type-parameter-1.rs
src/test/ui/regions/regions-close-over-type-parameter-1.stderr
src/test/ui/regions/regions-close-over-type-parameter-multiple.nll.stderr
src/test/ui/regions/regions-close-over-type-parameter-multiple.rs
src/test/ui/regions/regions-close-over-type-parameter-multiple.stderr
src/test/ui/regions/regions-close-param-into-object.rs
src/test/ui/regions/regions-close-param-into-object.stderr
src/test/ui/regions/regions-implied-bounds-projection-gap-hr-1.rs
src/test/ui/regions/regions-implied-bounds-projection-gap-hr-1.stderr
src/test/ui/regions/regions-infer-at-fn-not-param.rs
src/test/ui/regions/regions-infer-invariance-due-to-mutability-3.rs
src/test/ui/regions/regions-infer-invariance-due-to-mutability-4.rs
src/test/ui/regions/regions-infer-not-param.rs
src/test/ui/regions/regions-name-undeclared.rs
src/test/ui/regions/regions-nested-fns.nll.stderr
src/test/ui/regions/regions-nested-fns.rs
src/test/ui/regions/regions-nested-fns.stderr
src/test/ui/regions/regions-proc-bound-capture.rs
src/test/ui/regions/regions-proc-bound-capture.stderr
src/test/ui/regions/regions-steal-closure.rs
src/test/ui/regions/regions-trait-1.rs
src/test/ui/regions/regions-trait-object-subtyping.nll.stderr
src/test/ui/regions/regions-trait-object-subtyping.rs
src/test/ui/regions/regions-trait-object-subtyping.stderr
src/test/ui/regions/regions-trait-variance.rs
src/test/ui/regions/regions-wf-trait-object.rs
src/test/ui/regions/regions-wf-trait-object.stderr
src/test/ui/resolve/issue-23305.rs
src/test/ui/resolve/issue-23305.stderr
src/test/ui/resolve/issue-33876.rs
src/test/ui/resolve/issue-33876.stderr
src/test/ui/resolve/issue-3907-2.rs
src/test/ui/resolve/issue-3907.rs
src/test/ui/resolve/issue-5035-2.rs
src/test/ui/resolve/issue-5035.rs
src/test/ui/rfc-2093-infer-outlives/self-structs.rs
src/test/ui/rfc-2093-infer-outlives/self-structs.stderr
src/test/ui/rfc1598-generic-associated-types/generic-associated-types-where.rs
src/test/ui/rfc1623.rs
src/test/ui/save-analysis/issue-59134-0.rs
src/test/ui/self/arbitrary-self-types-not-object-safe.rs
src/test/ui/self/arbitrary-self-types-not-object-safe.stderr
src/test/ui/self/arbitrary_self_types_raw_pointer_trait.rs
src/test/ui/self/explicit-self-objects-uniq.rs
src/test/ui/self/object-safety-sized-self-by-value-self.rs
src/test/ui/self/object-safety-sized-self-generic-method.rs
src/test/ui/self/object-safety-sized-self-return-Self.rs
src/test/ui/span/borrowck-call-is-borrow-issue-12224.rs
src/test/ui/span/borrowck-call-is-borrow-issue-12224.stderr
src/test/ui/span/borrowck-object-mutability.rs
src/test/ui/span/borrowck-object-mutability.stderr
src/test/ui/span/dropck-object-cycle.rs
src/test/ui/span/issue-25199.rs
src/test/ui/span/issue-26656.rs
src/test/ui/span/regions-close-over-borrowed-ref-in-obj.rs
src/test/ui/span/regions-close-over-type-parameter-2.rs
src/test/ui/span/send-is-not-static-ensures-scoping.rs
src/test/ui/suggestions/issue-52820.rs [new file with mode: 0644]
src/test/ui/suggestions/issue-52820.stderr [new file with mode: 0644]
src/test/ui/suggestions/use-type-argument-instead-of-assoc-type.rs
src/test/ui/suggestions/use-type-argument-instead-of-assoc-type.stderr
src/test/ui/symbol-names/issue-60925.rs [new file with mode: 0644]
src/test/ui/symbol-names/issue-60925.stderr [new file with mode: 0644]
src/test/ui/traits/trait-alias/trait-alias-bounds.rs
src/test/ui/traits/trait-alias/trait-alias-no-duplicates.rs
src/test/ui/traits/trait-alias/trait-alias-no-duplicates.stderr
src/test/ui/traits/trait-bounds-not-on-bare-trait.rs
src/test/ui/traits/trait-bounds-not-on-bare-trait.stderr
src/test/ui/traits/trait-bounds-sugar.rs
src/test/ui/traits/trait-coercion-generic-bad.rs
src/test/ui/traits/trait-coercion-generic-bad.stderr
src/test/ui/traits/trait-coercion-generic-regions.rs
src/test/ui/traits/trait-coercion-generic-regions.stderr
src/test/ui/traits/trait-impl-1.rs
src/test/ui/traits/trait-item-privacy.rs
src/test/ui/traits/trait-object-auto-dedup-in-impl.rs
src/test/ui/traits/trait-object-macro-matcher.rs
src/test/ui/traits/trait-object-macro-matcher.stderr
src/test/ui/traits/trait-object-safety.rs
src/test/ui/traits/trait-object-safety.stderr
src/test/ui/traits/trait-object-vs-lifetime-2.rs
src/test/ui/traits/trait-object-vs-lifetime-2.stderr
src/test/ui/traits/trait-object-vs-lifetime.rs
src/test/ui/traits/trait-object-vs-lifetime.stderr
src/test/ui/traits/trait-test-2.rs
src/test/ui/traits/trait-test-2.stderr
src/test/ui/traits/traits-repeated-supertrait-ambig.rs
src/test/ui/trivial-bounds/trivial-bounds-inconsistent-sized.rs
src/test/ui/trivial-bounds/trivial-bounds-inconsistent-sized.stderr
src/test/ui/trivial-bounds/trivial-bounds-inconsistent.rs
src/test/ui/trivial-bounds/trivial-bounds-inconsistent.stderr
src/test/ui/trivial_casts.rs
src/test/ui/trivial_casts.stderr
src/test/ui/tuple/tuple-arity-mismatch.rs
src/test/ui/tuple/tuple-arity-mismatch.stderr
src/test/ui/type/type-arg-out-of-scope.rs
src/test/ui/type/type-arg-out-of-scope.stderr
src/test/ui/type/type-dependent-def-issue-49241.rs
src/test/ui/type/type-dependent-def-issue-49241.stderr
src/test/ui/type/type-parameter-defaults-referencing-Self-ppaux.rs
src/test/ui/type/type-parameter-defaults-referencing-Self-ppaux.stderr
src/test/ui/type/type-parameter-defaults-referencing-Self.rs
src/test/ui/type/type-parameter-defaults-referencing-Self.stderr
src/test/ui/type_length_limit.stderr
src/test/ui/typeck/typeck-builtin-bound-type-parameters.rs
src/test/ui/typeck/typeck-builtin-bound-type-parameters.stderr
src/test/ui/unboxed-closures/unboxed-closure-feature-gate.rs
src/test/ui/unboxed-closures/unboxed-closure-feature-gate.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-default.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-default.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-equiv.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-equiv.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-lifetime-elision.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-lifetime-elision.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-not-used-on-fn.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-not-used-on-fn.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-region.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-region.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters-1.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters-1.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters-3.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters-3.stderr
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters.rs
src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-number-number-type-parameters.stderr
src/test/ui/unboxed-closures/unboxed-closures-failed-recursive-fn-1.rs
src/test/ui/unboxed-closures/unboxed-closures-failed-recursive-fn-1.stderr
src/test/ui/unboxed-closures/unboxed-closures-recursive-fn-using-fn-mut.rs
src/test/ui/underscore-lifetime/underscore-lifetime-binders.rs
src/test/ui/underscore-lifetime/underscore-lifetime-binders.stderr
src/test/ui/unique-object-noncopyable.rs
src/test/ui/unsized/unsized-enum2.rs
src/test/ui/unsized/unsized-enum2.stderr
src/test/ui/use/use-after-move-implicity-coerced-object.rs
src/test/ui/variance/variance-contravariant-arg-object.nll.stderr
src/test/ui/variance/variance-contravariant-arg-object.rs
src/test/ui/variance/variance-contravariant-arg-object.stderr
src/test/ui/variance/variance-covariant-arg-object.nll.stderr
src/test/ui/variance/variance-covariant-arg-object.rs
src/test/ui/variance/variance-covariant-arg-object.stderr
src/test/ui/variance/variance-invariant-arg-object.nll.stderr
src/test/ui/variance/variance-invariant-arg-object.rs
src/test/ui/variance/variance-invariant-arg-object.stderr
src/test/ui/variance/variance-object-types.rs
src/test/ui/variance/variance-object-types.stderr
src/test/ui/variance/variance-trait-object-bound.rs
src/test/ui/variance/variance-trait-object-bound.stderr
src/test/ui/variance/variance-types-bounds.rs
src/test/ui/variance/variance-types-bounds.stderr
src/test/ui/wf/wf-in-obj-type-static.rs
src/test/ui/wf/wf-in-obj-type-static.stderr
src/test/ui/wf/wf-in-obj-type-trait.rs
src/test/ui/wf/wf-in-obj-type-trait.stderr
src/test/ui/wf/wf-object-safe.rs
src/test/ui/wf/wf-object-safe.stderr
src/test/ui/wf/wf-outlives-ty-in-fn-or-trait.rs
src/test/ui/wf/wf-outlives-ty-in-fn-or-trait.stderr
src/test/ui/where-clauses/where-lifetime-resolution.rs
src/test/ui/where-clauses/where-lifetime-resolution.stderr
src/tools/clippy

index 2d5759b539e5dcd9317ced1226b45e5191597d45..679aa55d314585e447c68c07e8c3fa011cdd45c8 100644 (file)
--- a/.mailmap
+++ b/.mailmap
@@ -5,8 +5,8 @@
 # email addresses.
 #
 
-Aaron Todd <github@opprobrio.us>
 Aaron Power <theaaronepower@gmail.com> Erin Power <xampprocky@gmail.com>
+Aaron Todd <github@opprobrio.us>
 Abhishek Chanda <abhishek.becs@gmail.com> Abhishek Chanda <abhishek@cloudscaling.com>
 Adolfo Ochagavía <aochagavia92@gmail.com>
 Adrien Tétar <adri-from-59@hotmail.fr>
@@ -29,8 +29,8 @@ Ariel Ben-Yehuda <arielb1@mail.tau.ac.il> Ariel Ben-Yehuda <ariel.byd@gmail.com>
 Ariel Ben-Yehuda <arielb1@mail.tau.ac.il> arielb1 <arielb1@mail.tau.ac.il>
 Austin Seipp <mad.one@gmail.com> <as@hacks.yi.org>
 Aydin Kim <ladinjin@hanmail.net> aydin.kim <aydin.kim@samsung.com>
-Bastian Kauschke <bastian_kauschke@hotmail.de>
 Barosl Lee <vcs@barosl.com> Barosl LEE <github@barosl.com>
+Bastian Kauschke <bastian_kauschke@hotmail.de>
 Ben Alpert <ben@benalpert.com> <spicyjalapeno@gmail.com>
 Ben Sago <ogham@users.noreply.github.com> Ben S <ogham@bsago.me>
 Ben Sago <ogham@users.noreply.github.com> Ben S <ogham@users.noreply.github.com>
@@ -46,22 +46,23 @@ Brian Anderson <banderson@mozilla.com> <banderson@mozilla.org>
 Brian Dawn <brian.t.dawn@gmail.com>
 Brian Leibig <brian@brianleibig.com> Brian Leibig <brian.leibig@gmail.com>
 Carl-Anton Ingmarsson <mail@carlanton.se> <ca.ingmarsson@gmail.com>
+Carol (Nichols || Goulding) <carol.nichols@gmail.com> <193874+carols10cents@users.noreply.github.com>
+Carol (Nichols || Goulding) <carol.nichols@gmail.com> <carol.nichols@gmail.com>
 Carol (Nichols || Goulding) <carol.nichols@gmail.com> <cnichols@thinkthroughmath.com>
-Carol (Nichols || Goulding) <carol.nichols@gmail.com> Carol Nichols <carol.nichols@gmail.com>
 Carol Willing <carolcode@willingconsulting.com>
 Chris C Cerami <chrisccerami@users.noreply.github.com> Chris C Cerami <chrisccerami@gmail.com>
 Chris Pressey <cpressey@gmail.com>
 Chris Thorn <chris@thorn.co> Chris Thorn <thorn@thoughtbot.com>
 Chris Vittal <christopher.vittal@gmail.com> Christopher Vittal <christopher.vittal@gmail.com>
-Christian Poveda <christianpoveda@protonmail.com> <z1mvader@protonmail.com>
 Christian Poveda <christianpoveda@protonmail.com> <cn.poveda.ruiz@gmail.com>
+Christian Poveda <christianpoveda@protonmail.com> <z1mvader@protonmail.com>
 Clark Gaebel <cg.wowus.cg@gmail.com> <cgaebel@mozilla.com>
 Clinton Ryan <clint.ryan3@gmail.com>
 Corey Richardson <corey@octayn.net> Elaine "See More" Nemo <corey@octayn.net>
 Cyryl Płotnicki <cyplo@cyplo.net>
 Damien Schoof <damien.schoof@gmail.com>
-Daniel Ramos <dan@daramos.com>
 Daniel J Rollins <drollins@financialforce.com>
+Daniel Ramos <dan@daramos.com>
 David Klein <david.klein@baesystemsdetica.com>
 David Manescu <david.manescu@gmail.com> <dman2626@uni.sydney.edu.au>
 David Ross <daboross@daboross.net>
@@ -70,9 +71,9 @@ Diggory Hardy <diggory.hardy@gmail.com> Diggory Hardy <github@dhardy.name>
 Dylan Braithwaite <dylanbraithwaite1@gmail.com> <mail@dylanb.me>
 Dzmitry Malyshau <kvarkus@gmail.com>
 E. Dunham <edunham@mozilla.com> edunham <edunham@mozilla.com>
+Eduard-Mihai Burtescu <edy.burt@gmail.com>
 Eduardo Bautista <me@eduardobautista.com> <=>
 Eduardo Bautista <me@eduardobautista.com> <mail@eduardobautista.com>
-Eduard-Mihai Burtescu <edy.burt@gmail.com>
 Elliott Slaughter <elliottslaughter@gmail.com> <eslaughter@mozilla.com>
 Elly Fong-Jones <elly@leptoquark.net>
 Eric Holk <eric.holk@gmail.com> <eholk@cs.indiana.edu>
@@ -80,8 +81,8 @@ Eric Holk <eric.holk@gmail.com> <eholk@mozilla.com>
 Eric Holmes <eric@ejholmes.net>
 Eric Reed <ecreed@cs.washington.edu> <ereed@mozilla.com>
 Erick Tryzelaar <erick.tryzelaar@gmail.com> <etryzelaar@iqt.org>
-Esteban Küber <esteban@kuber.com.ar> <estebank@users.noreply.github.com>
 Esteban Küber <esteban@kuber.com.ar> <esteban@commure.com>
+Esteban Küber <esteban@kuber.com.ar> <estebank@users.noreply.github.com>
 Esteban Küber <esteban@kuber.com.ar> <github@kuber.com.ar>
 Evgeny Sologubov
 Falco Hirschenberger <falco.hirschenberger@gmail.com> <hirschen@itwm.fhg.de>
@@ -102,9 +103,9 @@ Herman J. Radtke III <herman@hermanradtke.com> Herman J. Radtke III <hermanradtk
 Ilyong Cho <ilyoan@gmail.com>
 Ivan Ivaschenko <defuz.net@gmail.com>
 J. J. Weber <jjweber@gmail.com>
+Jakub Adam Wieczorek <jakub.adam.wieczorek@gmail.com> <jakub.bukaj@yahoo.com>
 Jakub Adam Wieczorek <jakub.adam.wieczorek@gmail.com> <jakub@jakub.cc>
 Jakub Adam Wieczorek <jakub.adam.wieczorek@gmail.com> <jakubw@jakubw.net>
-Jakub Adam Wieczorek <jakub.adam.wieczorek@gmail.com> <jakub.bukaj@yahoo.com>
 James Deng <cnjamesdeng@gmail.com> <cnJamesDeng@gmail.com>
 James Miller <bladeon@gmail.com> <james@aatch.net>
 James Perry <james.austin.perry@gmail.com>
@@ -119,6 +120,7 @@ Jethro Beekman <github@jbeekman.nl>
 Jihyun Yu <j.yu@navercorp.com> <yjh0502@gmail.com>
 Jihyun Yu <j.yu@navercorp.com> jihyun <jihyun@nablecomm.com>
 Jihyun Yu <j.yu@navercorp.com> Jihyun Yu <jihyun@nclab.kaist.ac.kr>
+João Oliveira <hello@jxs.pt> joaoxsouls <joaoxsouls@gmail.com>
 Johann Hofmann <git@johann-hofmann.com> Johann <git@johann-hofmann.com>
 John Clements <clements@racket-lang.org> <clements@brinckerhoff.org>
 John Hodge <acessdev@gmail.com> John Hodge <tpg@mutabah.net>
@@ -129,7 +131,8 @@ Jonathan S <gereeter@gmail.com> Jonathan S <gereeter+code@gmail.com>
 Jonathan Turner <probata@hotmail.com>
 Jorge Aparicio <japaric@linux.com> <japaricious@gmail.com>
 Joseph Martin <pythoner6@gmail.com>
-João Oliveira <hello@jxs.pt> joaoxsouls <joaoxsouls@gmail.com>
+Joseph T. Lyons <JosephTLyons@gmail.com> <josephtlyons@gmail.com>
+Joseph T. Lyons <JosephTLyons@gmail.com> <JosephTLyons@users.noreply.github.com>
 Junyoung Cho <june0.cho@samsung.com>
 Jyun-Yan You <jyyou.tw@gmail.com> <jyyou@cs.nctu.edu.tw>
 Kang Seonghoon <kang.seonghoon@mearie.org> <public+git@mearie.org>
@@ -145,8 +148,6 @@ Lindsey Kuper <lindsey@composition.al> <lkuper@mozilla.com>
 Luke Metz <luke.metz@students.olin.edu>
 Luqman Aden <me@luqman.ca> <laden@csclub.uwaterloo.ca>
 Luqman Aden <me@luqman.ca> <laden@mozilla.com>
-NAKASHIMA, Makoto <makoto.nksm+github@gmail.com> <makoto.nksm@gmail.com>
-NAKASHIMA, Makoto <makoto.nksm+github@gmail.com> <makoto.nksm+github@gmail.com>
 Marcell Pardavi <marcell.pardavi@gmail.com>
 Margaret Meyerhofer <mmeyerho@andrew.cmu.edu> <mmeyerho@andrew>
 Mark Rousskov <mark.simulacrum@gmail.com>
@@ -167,12 +168,14 @@ Michael Woerister <michaelwoerister@posteo> <michaelwoerister@gmail>
 Mickaël Raybaud-Roig <raybaudroigm@gmail.com> m-r-r <raybaudroigm@gmail.com>
 Ms2ger <ms2ger@gmail.com> <Ms2ger@gmail.com>
 Mukilan Thiagarajan <mukilanthiagarajan@gmail.com>
+NAKASHIMA, Makoto <makoto.nksm+github@gmail.com> <makoto.nksm@gmail.com>
+NAKASHIMA, Makoto <makoto.nksm+github@gmail.com> <makoto.nksm+github@gmail.com>
 Nathan West <Lucretiel@gmail.com> <lucretiel@gmail.com>
 Nathan Wilson <wilnathan@gmail.com>
 Nathaniel Herman <nherman@post.harvard.edu> Nathaniel Herman <nherman@college.harvard.edu>
 Neil Pankey <npankey@gmail.com> <neil@wire.im>
-Nicole Mazzuca <npmazzuca@gmail.com>
 Nick Platt <platt.nicholas@gmail.com>
+Nicole Mazzuca <npmazzuca@gmail.com>
 Nif Ward <nif.ward@gmail.com>
 Oliver Schneider <oliver.schneider@kit.edu> oli-obk <github6541940@oli-obk.de>
 Oliver Schneider <oliver.schneider@kit.edu> Oliver 'ker' Schneider <rust19446194516@oli-obk.de>
@@ -230,8 +233,8 @@ Tim JIANG <p90eri@gmail.com>
 Tim Joseph Dumol <tim@timdumol.com>
 Torsten Weber <TorstenWeber12@gmail.com> <torstenweber12@gmail.com>
 Ty Overby <ty@pre-alpha.com>
-Ulrik Sverdrup <bluss@users.noreply.github.com> bluss <bluss>
 Ulrik Sverdrup <bluss@users.noreply.github.com> bluss <bluss@users.noreply.github.com>
+Ulrik Sverdrup <bluss@users.noreply.github.com> bluss <bluss>
 Ulrik Sverdrup <bluss@users.noreply.github.com> Ulrik Sverdrup <root@localhost>
 Vadim Petrochenkov <vadim.petrochenkov@gmail.com>
 Vadim Petrochenkov <vadim.petrochenkov@gmail.com> petrochenkov <vadim.petrochenkov@gmail.com>
index d5e2969e9649a59fb36efba127c8c5181d64da84..4bee0e0e2ad2f31d25d73115ff04efe537c7dc9e 100644 (file)
@@ -421,7 +421,7 @@ dependencies = [
  "itertools 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)",
- "pulldown-cmark 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
+ "pulldown-cmark 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "quine-mc_cluskey 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex-syntax 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -860,7 +860,7 @@ dependencies = [
  "proc-macro2 0.4.24 (registry+https://github.com/rust-lang/crates.io-index)",
  "quote 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)",
  "syn 0.15.22 (registry+https://github.com/rust-lang/crates.io-index)",
- "synstructure 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
 [[package]]
@@ -2014,23 +2014,13 @@ dependencies = [
 
 [[package]]
 name = "pulldown-cmark"
-version = "0.4.1"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-dependencies = [
- "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
- "unicase 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
-]
-
-[[package]]
-name = "pulldown-cmark"
-version = "0.5.0"
+version = "0.5.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
  "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
  "getopts 0.2.19 (registry+https://github.com/rust-lang/crates.io-index)",
  "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
- "unicase 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
+ "unicase 2.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
 [[package]]
@@ -2875,7 +2865,7 @@ dependencies = [
  "proc-macro2 0.4.24 (registry+https://github.com/rust-lang/crates.io-index)",
  "quote 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)",
  "syn 0.15.22 (registry+https://github.com/rust-lang/crates.io-index)",
- "synstructure 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
 [[package]]
@@ -3077,7 +3067,7 @@ version = "0.0.0"
 dependencies = [
  "minifier 0.0.30 (registry+https://github.com/rust-lang/crates.io-index)",
  "parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
- "pulldown-cmark 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "pulldown-cmark 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "tempfile 3.0.5 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
@@ -3428,7 +3418,7 @@ dependencies = [
 
 [[package]]
 name = "synstructure"
-version = "0.10.1"
+version = "0.10.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
  "proc-macro2 0.4.24 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -3854,7 +3844,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 
 [[package]]
 name = "unicase"
-version = "2.3.0"
+version = "2.4.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
  "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -4285,8 +4275,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 "checksum proc-macro2 0.4.24 (registry+https://github.com/rust-lang/crates.io-index)" = "77619697826f31a02ae974457af0b29b723e5619e113e9397b8b82c6bd253f09"
 "checksum proptest 0.9.2 (registry+https://github.com/rust-lang/crates.io-index)" = "24f5844db2f839e97e3021980975f6ebf8691d9b9b2ca67ed3feb38dc3edb52c"
 "checksum pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "d6fdf85cda6cadfae5428a54661d431330b312bc767ddbc57adbedc24da66e32"
-"checksum pulldown-cmark 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d1b74cc784b038a9921fd1a48310cc2e238101aa8ae0b94201e2d85121dd68b5"
-"checksum pulldown-cmark 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "157737d41407de9c5e0563a991d085117d60ae729af2cc1bf28d6dfbc97bcc1f"
+"checksum pulldown-cmark 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "051e60ace841b3bfecd402fe5051c06cb3bec4a6e6fdd060a37aa8eb829a1db3"
 "checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0"
 "checksum quine-mc_cluskey 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)" = "07589615d719a60c8dd8a4622e7946465dfef20d1a428f969e3443e7386d5f45"
 "checksum quote 0.3.15 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6e920b65c65f10b2ae65c831a81a073a89edd28c7cce89475bff467ab4167a"
@@ -4367,7 +4356,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 "checksum syn 0.11.11 (registry+https://github.com/rust-lang/crates.io-index)" = "d3b891b9015c88c576343b9b3e41c2c11a51c219ef067b264bd9c8aa9b441dad"
 "checksum syn 0.15.22 (registry+https://github.com/rust-lang/crates.io-index)" = "ae8b29eb5210bc5cf63ed6149cbf9adfc82ac0be023d8735c176ee74a2db4da7"
 "checksum synom 0.11.3 (registry+https://github.com/rust-lang/crates.io-index)" = "a393066ed9010ebaed60b9eafa373d4b1baac186dd7e008555b0f702b51945b6"
-"checksum synstructure 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)" = "73687139bf99285483c96ac0add482c3776528beac1d97d444f6e91f203a2015"
+"checksum synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)" = "02353edf96d6e4dc81aea2d8490a7e9db177bf8acb0e951c24940bf866cb313f"
 "checksum tar 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)" = "a303ba60a099fcd2aaa646b14d2724591a96a75283e4b7ed3d1a1658909d9ae2"
 "checksum tempfile 3.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "7e91405c14320e5c79b3d148e1c86f40749a36e490642202a31689cb1a3452b2"
 "checksum tendril 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9de21546595a0873061940d994bbbc5c35f024ae4fd61ec5c5b159115684f508"
@@ -4400,7 +4389,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 "checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169"
 "checksum ucd-trie 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "71a9c5b1fe77426cf144cc30e49e955270f5086e31a6441dfa8b32efc09b9d77"
 "checksum ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "535c204ee4d8434478593480b8f86ab45ec9aae0e83c568ca81abf0fd0e88f86"
-"checksum unicase 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "41d17211f887da8e4a70a45b9536f26fc5de166b81e2d5d80de4a17fd22553bd"
+"checksum unicase 2.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "a84e5511b2a947f3ae965dcb29b13b7b1691b6e7332cf5dbc1744138d5acb7f6"
 "checksum unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5"
 "checksum unicode-normalization 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "6a0180bc61fc5a987082bfa111f4cc95c4caff7f9799f3e46df09163a937aa25"
 "checksum unicode-segmentation 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "aa6024fc12ddfd1c6dbc14a80fa2324d4568849869b779f6bd37e5e4c03344d1"
index 198b7dbc3f9d42cc0fb84da8e7023eaa60973eaa..1d3b4fe33c8119b40cea14d1ba1c9cee96331311 100644 (file)
@@ -581,6 +581,30 @@ pub fn compiler(&self, stage: u32, host: Interned<String>) -> Compiler {
         })
     }
 
+    /// Similar to `compiler`, except handles the full-bootstrap option to
+    /// silently use the stage1 compiler instead of a stage2 compiler if one is
+    /// requested.
+    ///
+    /// Note that this does *not* have the side effect of creating
+    /// `compiler(stage, host)`, unlike `compiler` above which does have such
+    /// a side effect. The returned compiler here can only be used to compile
+    /// new artifacts, it can't be used to rely on the presence of a particular
+    /// sysroot.
+    ///
+    /// See `force_use_stage1` for documentation on what each argument is.
+    pub fn compiler_for(
+        &self,
+        stage: u32,
+        host: Interned<String>,
+        target: Interned<String>,
+    ) -> Compiler {
+        if self.build.force_use_stage1(Compiler { stage, host }, target) {
+            self.compiler(1, self.config.build)
+        } else {
+            self.compiler(stage, host)
+        }
+    }
+
     pub fn sysroot(&self, compiler: Compiler) -> Interned<PathBuf> {
         self.ensure(compile::Sysroot { compiler })
     }
@@ -754,11 +778,7 @@ pub fn cargo(
         // This is for the original compiler, but if we're forced to use stage 1, then
         // std/test/rustc stamps won't exist in stage 2, so we need to get those from stage 1, since
         // we copy the libs forward.
-        let cmp = if self.force_use_stage1(compiler, target) {
-            self.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let cmp = self.compiler_for(compiler.stage, compiler.host, target);
 
         let libstd_stamp = match cmd {
             "check" | "clippy" | "fix" => check::libstd_stamp(self, cmp, target),
@@ -1358,7 +1378,7 @@ fn dist_baseline() {
 
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
-            &[dist::Docs { stage: 2, host: a },]
+            &[dist::Docs { host: a },]
         );
         assert_eq!(
             first(builder.cache.all::<dist::Mingw>()),
@@ -1373,7 +1393,7 @@ fn dist_baseline() {
         assert_eq!(
             first(builder.cache.all::<dist::Std>()),
             &[dist::Std {
-                compiler: Compiler { host: a, stage: 2 },
+                compiler: Compiler { host: a, stage: 1 },
                 target: a,
             },]
         );
@@ -1392,8 +1412,8 @@ fn dist_with_targets() {
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
             &[
-                dist::Docs { stage: 2, host: a },
-                dist::Docs { stage: 2, host: b },
+                dist::Docs { host: a },
+                dist::Docs { host: b },
             ]
         );
         assert_eq!(
@@ -1410,7 +1430,7 @@ fn dist_with_targets() {
             first(builder.cache.all::<dist::Std>()),
             &[
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
                 dist::Std {
@@ -1434,8 +1454,8 @@ fn dist_with_hosts() {
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
             &[
-                dist::Docs { stage: 2, host: a },
-                dist::Docs { stage: 2, host: b },
+                dist::Docs { host: a },
+                dist::Docs { host: b },
             ]
         );
         assert_eq!(
@@ -1457,11 +1477,11 @@ fn dist_with_hosts() {
             first(builder.cache.all::<dist::Std>()),
             &[
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: b,
                 },
             ]
@@ -1469,6 +1489,40 @@ fn dist_with_hosts() {
         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
     }
 
+    #[test]
+    fn dist_only_cross_host() {
+        let a = INTERNER.intern_str("A");
+        let b = INTERNER.intern_str("B");
+        let mut build = Build::new(configure(&["B"], &[]));
+        build.config.docs = false;
+        build.config.extended = true;
+        build.hosts = vec![b];
+        let mut builder = Builder::new(&build);
+        builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
+
+        assert_eq!(
+            first(builder.cache.all::<dist::Rustc>()),
+            &[
+                dist::Rustc {
+                    compiler: Compiler { host: b, stage: 2 }
+                },
+            ]
+        );
+        assert_eq!(
+            first(builder.cache.all::<compile::Rustc>()),
+            &[
+                compile::Rustc {
+                    compiler: Compiler { host: a, stage: 0 },
+                    target: a,
+                },
+                compile::Rustc {
+                    compiler: Compiler { host: a, stage: 1 },
+                    target: b,
+                },
+            ]
+        );
+    }
+
     #[test]
     fn dist_with_targets_and_hosts() {
         let build = Build::new(configure(&["B"], &["C"]));
@@ -1482,9 +1536,9 @@ fn dist_with_targets_and_hosts() {
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
             &[
-                dist::Docs { stage: 2, host: a },
-                dist::Docs { stage: 2, host: b },
-                dist::Docs { stage: 2, host: c },
+                dist::Docs { host: a },
+                dist::Docs { host: b },
+                dist::Docs { host: c },
             ]
         );
         assert_eq!(
@@ -1510,11 +1564,11 @@ fn dist_with_targets_and_hosts() {
             first(builder.cache.all::<dist::Std>()),
             &[
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: b,
                 },
                 dist::Std {
@@ -1541,9 +1595,9 @@ fn dist_with_target_flag() {
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
             &[
-                dist::Docs { stage: 2, host: a },
-                dist::Docs { stage: 2, host: b },
-                dist::Docs { stage: 2, host: c },
+                dist::Docs { host: a },
+                dist::Docs { host: b },
+                dist::Docs { host: c },
             ]
         );
         assert_eq!(
@@ -1559,11 +1613,11 @@ fn dist_with_target_flag() {
             first(builder.cache.all::<dist::Std>()),
             &[
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: b,
                 },
                 dist::Std {
@@ -1587,8 +1641,8 @@ fn dist_with_same_targets_and_hosts() {
         assert_eq!(
             first(builder.cache.all::<dist::Docs>()),
             &[
-                dist::Docs { stage: 2, host: a },
-                dist::Docs { stage: 2, host: b },
+                dist::Docs { host: a },
+                dist::Docs { host: b },
             ]
         );
         assert_eq!(
@@ -1610,11 +1664,11 @@ fn dist_with_same_targets_and_hosts() {
             first(builder.cache.all::<dist::Std>()),
             &[
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
                 dist::Std {
-                    compiler: Compiler { host: a, stage: 2 },
+                    compiler: Compiler { host: a, stage: 1 },
                     target: b,
                 },
             ]
@@ -1664,10 +1718,6 @@ fn dist_with_same_targets_and_hosts() {
                     compiler: Compiler { host: a, stage: 1 },
                     target: b,
                 },
-                compile::Test {
-                    compiler: Compiler { host: a, stage: 2 },
-                    target: b,
-                },
             ]
         );
         assert_eq!(
@@ -1720,10 +1770,6 @@ fn build_default() {
                     compiler: Compiler { host: b, stage: 2 },
                     target: a,
                 },
-                compile::Rustc {
-                    compiler: Compiler { host: a, stage: 0 },
-                    target: b,
-                },
                 compile::Rustc {
                     compiler: Compiler { host: a, stage: 1 },
                     target: b,
@@ -1758,10 +1804,6 @@ fn build_default() {
                     compiler: Compiler { host: b, stage: 2 },
                     target: a,
                 },
-                compile::Test {
-                    compiler: Compiler { host: a, stage: 0 },
-                    target: b,
-                },
                 compile::Test {
                     compiler: Compiler { host: a, stage: 1 },
                     target: b,
@@ -1808,9 +1850,6 @@ fn build_with_target_flag() {
                 compile::Assemble {
                     target_compiler: Compiler { host: a, stage: 1 },
                 },
-                compile::Assemble {
-                    target_compiler: Compiler { host: b, stage: 1 },
-                },
                 compile::Assemble {
                     target_compiler: Compiler { host: a, stage: 2 },
                 },
@@ -1830,10 +1869,6 @@ fn build_with_target_flag() {
                     compiler: Compiler { host: a, stage: 1 },
                     target: a,
                 },
-                compile::Rustc {
-                    compiler: Compiler { host: a, stage: 0 },
-                    target: b,
-                },
                 compile::Rustc {
                     compiler: Compiler { host: a, stage: 1 },
                     target: b,
@@ -1860,10 +1895,6 @@ fn build_with_target_flag() {
                     compiler: Compiler { host: b, stage: 2 },
                     target: a,
                 },
-                compile::Test {
-                    compiler: Compiler { host: a, stage: 0 },
-                    target: b,
-                },
                 compile::Test {
                     compiler: Compiler { host: a, stage: 1 },
                     target: b,
index 50c9602de1b145ccefe013d48373289187d98550..4515c7d672d8a5652f0949bcd76e2c78141d401d 100644 (file)
@@ -70,20 +70,20 @@ fn run(self, builder: &Builder<'_>) {
 
         builder.ensure(StartupObjects { compiler, target });
 
-        if builder.force_use_stage1(compiler, target) {
-            let from = builder.compiler(1, builder.config.build);
+        let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
+        if compiler_to_use != compiler {
             builder.ensure(Std {
-                compiler: from,
+                compiler: compiler_to_use,
                 target,
             });
-            builder.info(&format!("Uplifting stage1 std ({} -> {})", from.host, target));
+            builder.info(&format!("Uplifting stage1 std ({} -> {})", compiler_to_use.host, target));
 
             // Even if we're not building std this stage, the new sysroot must
             // still contain the third party objects needed by various targets.
             copy_third_party_objects(builder, &compiler, target);
 
             builder.ensure(StdLink {
-                compiler: from,
+                compiler: compiler_to_use,
                 target_compiler: compiler,
                 target,
             });
@@ -403,15 +403,16 @@ fn run(self, builder: &Builder<'_>) {
             return;
         }
 
-        if builder.force_use_stage1(compiler, target) {
+        let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
+        if compiler_to_use != compiler {
             builder.ensure(Test {
-                compiler: builder.compiler(1, builder.config.build),
+                compiler: compiler_to_use,
                 target,
             });
             builder.info(
                 &format!("Uplifting stage1 test ({} -> {})", builder.config.build, target));
             builder.ensure(TestLink {
-                compiler: builder.compiler(1, builder.config.build),
+                compiler: compiler_to_use,
                 target_compiler: compiler,
                 target,
             });
@@ -529,15 +530,16 @@ fn run(self, builder: &Builder<'_>) {
             return;
         }
 
-        if builder.force_use_stage1(compiler, target) {
+        let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
+        if compiler_to_use != compiler {
             builder.ensure(Rustc {
-                compiler: builder.compiler(1, builder.config.build),
+                compiler: compiler_to_use,
                 target,
             });
             builder.info(&format!("Uplifting stage1 rustc ({} -> {})",
                 builder.config.build, target));
             builder.ensure(RustcLink {
-                compiler: builder.compiler(1, builder.config.build),
+                compiler: compiler_to_use,
                 target_compiler: compiler,
                 target,
             });
@@ -687,9 +689,10 @@ fn run(self, builder: &Builder<'_>) {
             return;
         }
 
-        if builder.force_use_stage1(compiler, target) {
+        let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
+        if compiler_to_use != compiler {
             builder.ensure(CodegenBackend {
-                compiler: builder.compiler(1, builder.config.build),
+                compiler: compiler_to_use,
                 target,
                 backend,
             });
index b0616ff66918cbbf82711ca893f689bcf88bf9f0..274961916183afff56f22f5a704553dcb770fa49 100644 (file)
@@ -68,7 +68,6 @@ fn missing_tool(tool_name: &str, skip: bool) {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Docs {
-    pub stage: u32,
     pub host: Interned<String>,
 }
 
@@ -82,7 +81,6 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Docs {
-            stage: run.builder.top_stage,
             host: run.target,
         });
     }
@@ -130,7 +128,6 @@ fn run(self, builder: &Builder<'_>) -> PathBuf {
 
 #[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct RustcDocs {
-    pub stage: u32,
     pub host: Interned<String>,
 }
 
@@ -144,7 +141,6 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(RustcDocs {
-            stage: run.builder.top_stage,
             host: run.target,
         });
     }
@@ -647,7 +643,11 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Std {
-            compiler: run.builder.compiler(run.builder.top_stage, run.builder.config.build),
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
@@ -737,7 +737,14 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Analysis {
-            compiler: run.builder.compiler(run.builder.top_stage, run.builder.config.build),
+            // Find the actual compiler (handling the full bootstrap option) which
+            // produced the save-analysis data because that data isn't copied
+            // through the sysroot uplifting.
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
@@ -757,14 +764,6 @@ fn run(self, builder: &Builder<'_>) -> PathBuf {
 
         builder.ensure(Std { compiler, target });
 
-        // Package save-analysis from stage1 if not doing a full bootstrap, as the
-        // stage2 artifacts is simply copied from stage1 in that case.
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler.clone()
-        };
-
         let image = tmpdir(builder).join(format!("{}-{}-image", name, target));
 
         let src = builder.stage_out(compiler, Mode::Std)
@@ -1066,7 +1065,7 @@ fn change_drive(s: &str) -> Option<String> {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Cargo {
-    pub stage: u32,
+    pub compiler: Compiler,
     pub target: Interned<String>,
 }
 
@@ -1080,16 +1079,20 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Cargo {
-            stage: run.builder.top_stage,
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> PathBuf {
-        let stage = self.stage;
+        let compiler = self.compiler;
         let target = self.target;
 
-        builder.info(&format!("Dist cargo stage{} ({})", stage, target));
+        builder.info(&format!("Dist cargo stage{} ({})", compiler.stage, target));
         let src = builder.src.join("src/tools/cargo");
         let etc = src.join("src/etc");
         let release_num = builder.release_num("cargo");
@@ -1104,10 +1107,7 @@ fn run(self, builder: &Builder<'_>) -> PathBuf {
         // Prepare the image directory
         builder.create_dir(&image.join("share/zsh/site-functions"));
         builder.create_dir(&image.join("etc/bash_completion.d"));
-        let cargo = builder.ensure(tool::Cargo {
-            compiler: builder.compiler(stage, builder.config.build),
-            target
-        });
+        let cargo = builder.ensure(tool::Cargo { compiler, target });
         builder.install(&cargo, &image.join("bin"), 0o755);
         for man in t!(etc.join("man").read_dir()) {
             let man = t!(man);
@@ -1152,7 +1152,7 @@ fn run(self, builder: &Builder<'_>) -> PathBuf {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Rls {
-    pub stage: u32,
+    pub compiler: Compiler,
     pub target: Interned<String>,
 }
 
@@ -1166,17 +1166,21 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Rls {
-            stage: run.builder.top_stage,
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
-        let stage = self.stage;
+        let compiler = self.compiler;
         let target = self.target;
         assert!(builder.config.extended);
 
-        builder.info(&format!("Dist RLS stage{} ({})", stage, target));
+        builder.info(&format!("Dist RLS stage{} ({})", compiler.stage, target));
         let src = builder.src.join("src/tools/rls");
         let release_num = builder.release_num("rls");
         let name = pkgname(builder, "rls");
@@ -1191,8 +1195,9 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
         // We expect RLS to build, because we've exited this step above if tool
         // state for RLS isn't testing.
         let rls = builder.ensure(tool::Rls {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new(),
         }).or_else(|| { missing_tool("RLS", builder.build.config.missing_tools); None })?;
 
         builder.install(&rls, &image.join("bin"), 0o755);
@@ -1231,7 +1236,7 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Clippy {
-    pub stage: u32,
+    pub compiler: Compiler,
     pub target: Interned<String>,
 }
 
@@ -1245,17 +1250,21 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Clippy {
-            stage: run.builder.top_stage,
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
-        let stage = self.stage;
+        let compiler = self.compiler;
         let target = self.target;
         assert!(builder.config.extended);
 
-        builder.info(&format!("Dist clippy stage{} ({})", stage, target));
+        builder.info(&format!("Dist clippy stage{} ({})", compiler.stage, target));
         let src = builder.src.join("src/tools/clippy");
         let release_num = builder.release_num("clippy");
         let name = pkgname(builder, "clippy");
@@ -1270,11 +1279,12 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
         // We expect clippy to build, because we've exited this step above if tool
         // state for clippy isn't testing.
         let clippy = builder.ensure(tool::Clippy {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new(),
         }).or_else(|| { missing_tool("clippy", builder.build.config.missing_tools); None })?;
         let cargoclippy = builder.ensure(tool::CargoClippy {
-            compiler: builder.compiler(stage, builder.config.build),
+            compiler,
             target, extra_features: Vec::new()
         }).or_else(|| { missing_tool("cargo clippy", builder.build.config.missing_tools); None })?;
 
@@ -1315,7 +1325,7 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Miri {
-    pub stage: u32,
+    pub compiler: Compiler,
     pub target: Interned<String>,
 }
 
@@ -1329,17 +1339,21 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Miri {
-            stage: run.builder.top_stage,
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
-        let stage = self.stage;
+        let compiler = self.compiler;
         let target = self.target;
         assert!(builder.config.extended);
 
-        builder.info(&format!("Dist miri stage{} ({})", stage, target));
+        builder.info(&format!("Dist miri stage{} ({})", compiler.stage, target));
         let src = builder.src.join("src/tools/miri");
         let release_num = builder.release_num("miri");
         let name = pkgname(builder, "miri");
@@ -1354,12 +1368,14 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
         // We expect miri to build, because we've exited this step above if tool
         // state for miri isn't testing.
         let miri = builder.ensure(tool::Miri {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new(),
         }).or_else(|| { missing_tool("miri", builder.build.config.missing_tools); None })?;
         let cargomiri = builder.ensure(tool::CargoMiri {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new()
         }).or_else(|| { missing_tool("cargo miri", builder.build.config.missing_tools); None })?;
 
         builder.install(&miri, &image.join("bin"), 0o755);
@@ -1399,7 +1415,7 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
 
 #[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
 pub struct Rustfmt {
-    pub stage: u32,
+    pub compiler: Compiler,
     pub target: Interned<String>,
 }
 
@@ -1413,16 +1429,20 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(Rustfmt {
-            stage: run.builder.top_stage,
+            compiler: run.builder.compiler_for(
+                run.builder.top_stage,
+                run.builder.config.build,
+                run.target,
+            ),
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
-        let stage = self.stage;
+        let compiler = self.compiler;
         let target = self.target;
 
-        builder.info(&format!("Dist Rustfmt stage{} ({})", stage, target));
+        builder.info(&format!("Dist Rustfmt stage{} ({})", compiler.stage, target));
         let src = builder.src.join("src/tools/rustfmt");
         let release_num = builder.release_num("rustfmt");
         let name = pkgname(builder, "rustfmt");
@@ -1435,12 +1455,14 @@ fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
 
         // Prepare the image directory
         let rustfmt = builder.ensure(tool::Rustfmt {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new(),
         }).or_else(|| { missing_tool("Rustfmt", builder.build.config.missing_tools); None })?;
         let cargofmt = builder.ensure(tool::Cargofmt {
-            compiler: builder.compiler(stage, builder.config.build),
-            target, extra_features: Vec::new()
+            compiler,
+            target,
+            extra_features: Vec::new(),
         }).or_else(|| { missing_tool("Cargofmt", builder.build.config.missing_tools); None })?;
 
         builder.install(&rustfmt, &image.join("bin"), 0o755);
@@ -1505,30 +1527,28 @@ fn make_run(run: RunConfig<'_>) {
 
     /// Creates a combined installer for the specified target in the provided stage.
     fn run(self, builder: &Builder<'_>) {
-        let stage = self.stage;
         let target = self.target;
+        let stage = self.stage;
+        let compiler = builder.compiler_for(self.stage, self.host, self.target);
 
-        builder.info(&format!("Dist extended stage{} ({})", stage, target));
+        builder.info(&format!("Dist extended stage{} ({})", compiler.stage, target));
 
         let rustc_installer = builder.ensure(Rustc {
             compiler: builder.compiler(stage, target),
         });
-        let cargo_installer = builder.ensure(Cargo { stage, target });
-        let rustfmt_installer = builder.ensure(Rustfmt { stage, target });
-        let rls_installer = builder.ensure(Rls { stage, target });
-        let llvm_tools_installer = builder.ensure(LlvmTools { stage, target });
-        let clippy_installer = builder.ensure(Clippy { stage, target });
-        let miri_installer = builder.ensure(Miri { stage, target });
+        let cargo_installer = builder.ensure(Cargo { compiler, target });
+        let rustfmt_installer = builder.ensure(Rustfmt { compiler, target });
+        let rls_installer = builder.ensure(Rls { compiler, target });
+        let llvm_tools_installer = builder.ensure(LlvmTools { target });
+        let clippy_installer = builder.ensure(Clippy { compiler, target });
+        let miri_installer = builder.ensure(Miri { compiler, target });
         let lldb_installer = builder.ensure(Lldb { target });
         let mingw_installer = builder.ensure(Mingw { host: target });
-        let analysis_installer = builder.ensure(Analysis {
-            compiler: builder.compiler(stage, self.host),
-            target
-        });
+        let analysis_installer = builder.ensure(Analysis { compiler, target });
 
-        let docs_installer = builder.ensure(Docs { stage, host: target, });
+        let docs_installer = builder.ensure(Docs { host: target, });
         let std_installer = builder.ensure(Std {
-            compiler: builder.compiler(stage, self.host),
+            compiler: builder.compiler(stage, target),
             target,
         });
 
@@ -2076,7 +2096,6 @@ pub fn maybe_install_llvm_dylib(builder: &Builder<'_>,
 
 #[derive(Clone, Debug, Eq, Hash, PartialEq)]
 pub struct LlvmTools {
-    pub stage: u32,
     pub target: Interned<String>,
 }
 
@@ -2090,26 +2109,24 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
     fn make_run(run: RunConfig<'_>) {
         run.builder.ensure(LlvmTools {
-            stage: run.builder.top_stage,
             target: run.target,
         });
     }
 
     fn run(self, builder: &Builder<'_>) -> Option<PathBuf> {
-        let stage = self.stage;
         let target = self.target;
         assert!(builder.config.extended);
 
         /* run only if llvm-config isn't used */
         if let Some(config) = builder.config.target_config.get(&target) {
             if let Some(ref _s) = config.llvm_config {
-                builder.info(&format!("Skipping LlvmTools stage{} ({}): external LLVM",
-                    stage, target));
+                builder.info(&format!("Skipping LlvmTools ({}): external LLVM",
+                    target));
                 return None;
             }
         }
 
-        builder.info(&format!("Dist LlvmTools stage{} ({})", stage, target));
+        builder.info(&format!("Dist LlvmTools ({})", target));
         let src = builder.src.join("src/llvm-project/llvm");
         let name = pkgname(builder, "llvm-tools");
 
index 9c3a17bff6b7a619e240a94c29ddb8517d1ff43b..12bdfa5691dc744a7479a6074d6d546ccb3965b0 100644 (file)
@@ -475,12 +475,7 @@ fn run(self, builder: &Builder<'_>) {
         builder.info(&format!("Documenting stage{} std ({})", stage, target));
         let out = builder.doc_out(target);
         t!(fs::create_dir_all(&out));
-        let compiler = builder.compiler(stage, builder.config.build);
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let compiler = builder.compiler_for(stage, builder.config.build, target);
 
         builder.ensure(compile::Std { compiler, target });
         let out_dir = builder.stage_out(compiler, Mode::Std)
@@ -563,12 +558,7 @@ fn run(self, builder: &Builder<'_>) {
         builder.info(&format!("Documenting stage{} test ({})", stage, target));
         let out = builder.doc_out(target);
         t!(fs::create_dir_all(&out));
-        let compiler = builder.compiler(stage, builder.config.build);
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let compiler = builder.compiler_for(stage, builder.config.build, target);
 
         // Build libstd docs so that we generate relative links
         builder.ensure(Std { stage, target });
@@ -632,12 +622,7 @@ fn run(self, builder: &Builder<'_>) {
         builder.info(&format!("Documenting stage{} whitelisted compiler ({})", stage, target));
         let out = builder.doc_out(target);
         t!(fs::create_dir_all(&out));
-        let compiler = builder.compiler(stage, builder.config.build);
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let compiler = builder.compiler_for(stage, builder.config.build, target);
 
         // Build libstd docs so that we generate relative links
         builder.ensure(Std { stage, target });
@@ -706,12 +691,7 @@ fn run(self, builder: &Builder<'_>) {
         t!(fs::create_dir_all(&out));
 
         // Get the correct compiler for this stage.
-        let compiler = builder.compiler(stage, builder.config.build);
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let compiler = builder.compiler_for(stage, builder.config.build, target);
 
         if !builder.config.compiler_docs {
             builder.info("\tskipping - compiler/librustdoc docs disabled");
@@ -728,7 +708,7 @@ fn run(self, builder: &Builder<'_>) {
 
         // Build cargo command.
         let mut cargo = builder.cargo(compiler, Mode::Rustc, target, "doc");
-        cargo.env("RUSTDOCFLAGS", "--document-private-items");
+        cargo.env("RUSTDOCFLAGS", "--document-private-items --passes strip-hidden");
         compile::rustc_cargo(builder, &mut cargo);
 
         // Only include compiler crates, no dependencies of those, such as `libc`.
@@ -807,12 +787,7 @@ fn run(self, builder: &Builder<'_>) {
         t!(fs::create_dir_all(&out));
 
         // Get the correct compiler for this stage.
-        let compiler = builder.compiler(stage, builder.config.build);
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler
-        };
+        let compiler = builder.compiler_for(stage, builder.config.build, target);
 
         if !builder.config.compiler_docs {
             builder.info("\tskipping - compiler/librustdoc docs disabled");
index deda30b6bbd9beb1263219ccd4ec0b098cd1b64e..0047be4d5951b95a4fbc77bcdac5e6f902f1827b 100644 (file)
@@ -5,12 +5,13 @@
 
 use std::env;
 use std::fs;
-use std::path::{Path, PathBuf, Component};
+use std::path::{Component, Path, PathBuf};
 use std::process::Command;
 
 use build_helper::t;
 
 use crate::dist::{self, pkgname, sanitize_sh, tmpdir};
+use crate::Compiler;
 
 use crate::builder::{Builder, RunConfig, ShouldRun, Step};
 use crate::cache::Interned;
@@ -58,7 +59,7 @@ fn install_sh(
     package: &str,
     name: &str,
     stage: u32,
-    host: Option<Interned<String>>
+    host: Option<Interned<String>>,
 ) {
     builder.info(&format!("Install {} stage{} ({:?})", package, stage, host));
 
@@ -144,9 +145,8 @@ macro_rules! install {
         $(
             #[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
         pub struct $name {
-            pub stage: u32,
+            pub compiler: Compiler,
             pub target: Interned<String>,
-            pub host: Interned<String>,
         }
 
         impl $name {
@@ -175,9 +175,8 @@ fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
 
             fn make_run(run: RunConfig<'_>) {
                 run.builder.ensure($name {
-                    stage: run.builder.top_stage,
+                    compiler: run.builder.compiler(run.builder.top_stage, run.builder.config.build),
                     target: run.target,
-                    host: run.builder.config.build,
                 });
             }
 
@@ -190,67 +189,78 @@ fn run($sel, $builder: &Builder<'_>) {
 
 install!((self, builder, _config),
     Docs, "src/doc", _config.docs, only_hosts: false, {
-        builder.ensure(dist::Docs { stage: self.stage, host: self.target });
-        install_docs(builder, self.stage, self.target);
+        builder.ensure(dist::Docs { host: self.target });
+        install_docs(builder, self.compiler.stage, self.target);
     };
     Std, "src/libstd", true, only_hosts: true, {
         for target in &builder.targets {
             builder.ensure(dist::Std {
-                compiler: builder.compiler(self.stage, self.host),
+                compiler: self.compiler,
                 target: *target
             });
-            install_std(builder, self.stage, *target);
+            install_std(builder, self.compiler.stage, *target);
         }
     };
     Cargo, "cargo", Self::should_build(_config), only_hosts: true, {
-        builder.ensure(dist::Cargo { stage: self.stage, target: self.target });
-        install_cargo(builder, self.stage, self.target);
+        builder.ensure(dist::Cargo { compiler: self.compiler, target: self.target });
+        install_cargo(builder, self.compiler.stage, self.target);
     };
     Rls, "rls", Self::should_build(_config), only_hosts: true, {
-        if builder.ensure(dist::Rls { stage: self.stage, target: self.target }).is_some() ||
+        if builder.ensure(dist::Rls { compiler: self.compiler, target: self.target }).is_some() ||
             Self::should_install(builder) {
-            install_rls(builder, self.stage, self.target);
+            install_rls(builder, self.compiler.stage, self.target);
         } else {
-            builder.info(&format!("skipping Install RLS stage{} ({})", self.stage, self.target));
+            builder.info(
+                &format!("skipping Install RLS stage{} ({})", self.compiler.stage, self.target),
+            );
         }
     };
     Clippy, "clippy", Self::should_build(_config), only_hosts: true, {
-        if builder.ensure(dist::Clippy { stage: self.stage, target: self.target }).is_some() ||
-            Self::should_install(builder) {
-            install_clippy(builder, self.stage, self.target);
+        if builder.ensure(dist::Clippy {
+            compiler: self.compiler,
+            target: self.target,
+        }).is_some() || Self::should_install(builder) {
+            install_clippy(builder, self.compiler.stage, self.target);
         } else {
-            builder.info(&format!("skipping Install clippy stage{} ({})", self.stage, self.target));
+            builder.info(
+                &format!("skipping Install clippy stage{} ({})", self.compiler.stage, self.target),
+            );
         }
     };
     Miri, "miri", Self::should_build(_config), only_hosts: true, {
-        if builder.ensure(dist::Miri { stage: self.stage, target: self.target }).is_some() ||
+        if builder.ensure(dist::Miri { compiler: self.compiler, target: self.target }).is_some() ||
             Self::should_install(builder) {
-            install_miri(builder, self.stage, self.target);
+            install_miri(builder, self.compiler.stage, self.target);
         } else {
-            builder.info(&format!("skipping Install miri stage{} ({})", self.stage, self.target));
+            builder.info(
+                &format!("skipping Install miri stage{} ({})", self.compiler.stage, self.target),
+            );
         }
     };
     Rustfmt, "rustfmt", Self::should_build(_config), only_hosts: true, {
-        if builder.ensure(dist::Rustfmt { stage: self.stage, target: self.target }).is_some() ||
-            Self::should_install(builder) {
-            install_rustfmt(builder, self.stage, self.target);
+        if builder.ensure(dist::Rustfmt {
+            compiler: self.compiler,
+            target: self.target
+        }).is_some() || Self::should_install(builder) {
+            install_rustfmt(builder, self.compiler.stage, self.target);
         } else {
             builder.info(
-                &format!("skipping Install Rustfmt stage{} ({})", self.stage, self.target));
+                &format!("skipping Install Rustfmt stage{} ({})", self.compiler.stage, self.target),
+            );
         }
     };
     Analysis, "analysis", Self::should_build(_config), only_hosts: false, {
         builder.ensure(dist::Analysis {
-            compiler: builder.compiler(self.stage, self.host),
+            compiler: self.compiler,
             target: self.target
         });
-        install_analysis(builder, self.stage, self.target);
+        install_analysis(builder, self.compiler.stage, self.target);
     };
     Rustc, "src/librustc", true, only_hosts: true, {
         builder.ensure(dist::Rustc {
-            compiler: builder.compiler(self.stage, self.target),
+            compiler: self.compiler,
         });
-        install_rustc(builder, self.stage, self.target);
+        install_rustc(builder, self.compiler.stage, self.target);
     };
 );
 
@@ -266,15 +276,12 @@ impl Step for Src {
 
     fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
         let config = &run.builder.config;
-        let cond = config.extended &&
-            config.tools.as_ref().map_or(true, |t| t.contains("src"));
+        let cond = config.extended && config.tools.as_ref().map_or(true, |t| t.contains("src"));
         run.path("src").default_condition(cond)
     }
 
     fn make_run(run: RunConfig<'_>) {
-        run.builder.ensure(Src {
-            stage: run.builder.top_stage,
-        });
+        run.builder.ensure(Src { stage: run.builder.top_stage });
     }
 
     fn run(self, builder: &Builder<'_>) {
index 9d0aa09f15cfb01f674bda17b39421769c4ccad6..74caaae2840c5b2b88b2b960321ef12e241d3a94 100644 (file)
@@ -1690,15 +1690,11 @@ fn run(self, builder: &Builder<'_>) {
         builder.ensure(compile::Test { compiler, target });
         builder.ensure(RemoteCopyLibs { compiler, target });
 
-        // If we're not doing a full bootstrap but we're testing a stage2 version of
-        // libstd, then what we're actually testing is the libstd produced in
-        // stage1. Reflect that here by updating the compiler that we're working
-        // with automatically.
-        let compiler = if builder.force_use_stage1(compiler, target) {
-            builder.compiler(1, compiler.host)
-        } else {
-            compiler.clone()
-        };
+        // If we're not doing a full bootstrap but we're testing a stage2
+        // version of libstd, then what we're actually testing is the libstd
+        // produced in stage1. Reflect that here by updating the compiler that
+        // we're working with automatically.
+        let compiler = builder.compiler_for(compiler.stage, compiler.host, target);
 
         let mut cargo = builder.cargo(compiler, mode, target, test_kind.subcommand());
         match mode {
index 68fe92466027a6d6e6bdb056869722c70f5a6889..3b6f02c9368c9570eac86af2bd92566df32de586 100644 (file)
@@ -535,9 +535,9 @@ fn make_run(run: RunConfig<'_>) {
     }
 
     fn run(self, builder: &Builder<'_>) -> PathBuf {
-        // Cargo depends on procedural macros, which requires a full host
-        // compiler to be available, so we need to depend on that.
-        builder.ensure(compile::Rustc {
+        // Cargo depends on procedural macros, so make sure the host
+        // libstd/libproc_macro is available.
+        builder.ensure(compile::Test {
             compiler: self.compiler,
             target: builder.config.build,
         });
@@ -609,26 +609,26 @@ fn run(mut $sel, $builder: &Builder<'_>) -> Option<PathBuf> {
 tool_extended!((self, builder),
     Cargofmt, rustfmt, "src/tools/rustfmt", "cargo-fmt", {};
     CargoClippy, clippy, "src/tools/clippy", "cargo-clippy", {
-        // Clippy depends on procedural macros (serde), which requires a full host
-        // compiler to be available, so we need to depend on that.
-        builder.ensure(compile::Rustc {
+        // Clippy depends on procedural macros, so make sure that's built for
+        // the compiler itself.
+        builder.ensure(compile::Test {
             compiler: self.compiler,
             target: builder.config.build,
         });
     };
     Clippy, clippy, "src/tools/clippy", "clippy-driver", {
-        // Clippy depends on procedural macros (serde), which requires a full host
-        // compiler to be available, so we need to depend on that.
-        builder.ensure(compile::Rustc {
+        // Clippy depends on procedural macros, so make sure that's built for
+        // the compiler itself.
+        builder.ensure(compile::Test {
             compiler: self.compiler,
             target: builder.config.build,
         });
     };
     Miri, miri, "src/tools/miri", "miri", {};
     CargoMiri, miri, "src/tools/miri", "cargo-miri", {
-        // Miri depends on procedural macros (serde), which requires a full host
-        // compiler to be available, so we need to depend on that.
-        builder.ensure(compile::Rustc {
+        // Miri depends on procedural macros, so make sure that's built for
+        // the compiler itself.
+        builder.ensure(compile::Test {
             compiler: self.compiler,
             target: builder.config.build,
         });
@@ -642,9 +642,9 @@ fn run(mut $sel, $builder: &Builder<'_>) -> Option<PathBuf> {
         if clippy.is_some() {
             self.extra_features.push("clippy".to_owned());
         }
-        // RLS depends on procedural macros, which requires a full host
-        // compiler to be available, so we need to depend on that.
-        builder.ensure(compile::Rustc {
+        // RLS depends on procedural macros, so make sure that's built for
+        // the compiler itself.
+        builder.ensure(compile::Test {
             compiler: self.compiler,
             target: builder.config.build,
         });
diff --git a/src/doc/unstable-book/src/library-features/borrow-state.md b/src/doc/unstable-book/src/library-features/borrow-state.md
deleted file mode 100644 (file)
index 304b8df..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-# `borrow_state`
-
-The tracking issue for this feature is: [#27733]
-
-[#27733]: https://github.com/rust-lang/rust/issues/27733
-
-------------------------
index 0dffb19476f3d318dc64968dd31d11663fededd7..1f357a719bb43880725e51309349591dd1777156 100644 (file)
 use core::hash::{Hash, Hasher};
 use core::intrinsics::abort;
 use core::marker::{self, Unpin, Unsize, PhantomData};
-use core::mem::{self, align_of_val, forget, size_of_val};
+use core::mem::{self, align_of, align_of_val, forget, size_of_val};
 use core::ops::{Deref, Receiver, CoerceUnsized, DispatchFromDyn};
 use core::pin::Pin;
 use core::ptr::{self, NonNull};
@@ -416,11 +416,7 @@ pub fn into_raw(this: Self) -> *const T {
     /// ```
     #[stable(feature = "rc_raw", since = "1.17.0")]
     pub unsafe fn from_raw(ptr: *const T) -> Self {
-        // Align the unsized value to the end of the RcBox.
-        // Because it is ?Sized, it will always be the last field in memory.
-        let align = align_of_val(&*ptr);
-        let layout = Layout::new::<RcBox<()>>();
-        let offset = (layout.size() + layout.padding_needed_for(align)) as isize;
+        let offset = data_offset(ptr);
 
         // Reverse the offset to find the original RcBox.
         let fake_ptr = ptr as *mut RcBox<T>;
@@ -1262,6 +1258,143 @@ pub fn new() -> Weak<T> {
             ptr: NonNull::new(usize::MAX as *mut RcBox<T>).expect("MAX is not 0"),
         }
     }
+
+    /// Returns a raw pointer to the object `T` pointed to by this `Weak<T>`.
+    ///
+    /// It is up to the caller to ensure that the object is still alive when accessing it through
+    /// the pointer.
+    ///
+    /// The pointer may be [`null`] or be dangling in case the object has already been destroyed.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::rc::{Rc, Weak};
+    /// use std::ptr;
+    ///
+    /// let strong = Rc::new(42);
+    /// let weak = Rc::downgrade(&strong);
+    /// // Both point to the same object
+    /// assert!(ptr::eq(&*strong, Weak::as_raw(&weak)));
+    /// // The strong here keeps it alive, so we can still access the object.
+    /// assert_eq!(42, unsafe { *Weak::as_raw(&weak) });
+    ///
+    /// drop(strong);
+    /// // But not any more. We can do Weak::as_raw(&weak), but accessing the pointer would lead to
+    /// // undefined behaviour.
+    /// // assert_eq!(42, unsafe { *Weak::as_raw(&weak) });
+    /// ```
+    ///
+    /// [`null`]: ../../std/ptr/fn.null.html
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub fn as_raw(this: &Self) -> *const T {
+        match this.inner() {
+            None => ptr::null(),
+            Some(inner) => {
+                let offset = data_offset_sized::<T>();
+                let ptr = inner as *const RcBox<T>;
+                // Note: while the pointer we create may already point to dropped value, the
+                // allocation still lives (it must hold the weak point as long as we are alive).
+                // Therefore, the offset is OK to do, it won't get out of the allocation.
+                let ptr = unsafe { (ptr as *const u8).offset(offset) };
+                ptr as *const T
+            }
+        }
+    }
+
+    /// Consumes the `Weak<T>` and turns it into a raw pointer.
+    ///
+    /// This converts the weak pointer into a raw pointer, preserving the original weak count. It
+    /// can be turned back into the `Weak<T>` with [`from_raw`].
+    ///
+    /// The same restrictions of accessing the target of the pointer as with
+    /// [`as_raw`] apply.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::rc::{Rc, Weak};
+    ///
+    /// let strong = Rc::new(42);
+    /// let weak = Rc::downgrade(&strong);
+    /// let raw = Weak::into_raw(weak);
+    ///
+    /// assert_eq!(1, Rc::weak_count(&strong));
+    /// assert_eq!(42, unsafe { *raw });
+    ///
+    /// drop(unsafe { Weak::from_raw(raw) });
+    /// assert_eq!(0, Rc::weak_count(&strong));
+    /// ```
+    ///
+    /// [`from_raw`]: struct.Weak.html#method.from_raw
+    /// [`as_raw`]: struct.Weak.html#method.as_raw
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub fn into_raw(this: Self) -> *const T {
+        let result = Self::as_raw(&this);
+        mem::forget(this);
+        result
+    }
+
+    /// Converts a raw pointer previously created by [`into_raw`] back into `Weak<T>`.
+    ///
+    /// This can be used to safely get a strong reference (by calling [`upgrade`]
+    /// later) or to deallocate the weak count by dropping the `Weak<T>`.
+    ///
+    /// It takes ownership of one weak count. In case a [`null`] is passed, a dangling [`Weak`] is
+    /// returned.
+    ///
+    /// # Safety
+    ///
+    /// The pointer must represent one valid weak count. In other words, it must point to `T` which
+    /// is or *was* managed by an [`Rc`] and the weak count of that [`Rc`] must not have reached
+    /// 0. It is allowed for the strong count to be 0.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::rc::{Rc, Weak};
+    ///
+    /// let strong = Rc::new(42);
+    ///
+    /// let raw_1 = Weak::into_raw(Rc::downgrade(&strong));
+    /// let raw_2 = Weak::into_raw(Rc::downgrade(&strong));
+    ///
+    /// assert_eq!(2, Rc::weak_count(&strong));
+    ///
+    /// assert_eq!(42, *Weak::upgrade(&unsafe { Weak::from_raw(raw_1) }).unwrap());
+    /// assert_eq!(1, Rc::weak_count(&strong));
+    ///
+    /// drop(strong);
+    ///
+    /// // Decrement the last weak count.
+    /// assert!(Weak::upgrade(&unsafe { Weak::from_raw(raw_2) }).is_none());
+    /// ```
+    ///
+    /// [`null`]: ../../std/ptr/fn.null.html
+    /// [`into_raw`]: struct.Weak.html#method.into_raw
+    /// [`upgrade`]: struct.Weak.html#method.upgrade
+    /// [`Rc`]: struct.Rc.html
+    /// [`Weak`]: struct.Weak.html
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub unsafe fn from_raw(ptr: *const T) -> Self {
+        if ptr.is_null() {
+            Self::new()
+        } else {
+            // See Rc::from_raw for details
+            let offset = data_offset(ptr);
+            let fake_ptr = ptr as *mut RcBox<T>;
+            let ptr = set_data_ptr(fake_ptr, (ptr as *mut u8).offset(-offset));
+            Weak {
+                ptr: NonNull::new(ptr).expect("Invalid pointer passed to from_raw"),
+            }
+        }
+    }
 }
 
 pub(crate) fn is_dangling<T: ?Sized>(ptr: NonNull<T>) -> bool {
@@ -2007,3 +2140,20 @@ fn as_ref(&self) -> &T {
 
 #[stable(feature = "pin", since = "1.33.0")]
 impl<T: ?Sized> Unpin for Rc<T> { }
+
+unsafe fn data_offset<T: ?Sized>(ptr: *const T) -> isize {
+    // Align the unsized value to the end of the RcBox.
+    // Because it is ?Sized, it will always be the last field in memory.
+    let align = align_of_val(&*ptr);
+    let layout = Layout::new::<RcBox<()>>();
+    (layout.size() + layout.padding_needed_for(align)) as isize
+}
+
+/// Computes the offset of the data field within ArcInner.
+///
+/// Unlike [`data_offset`], this doesn't need the pointer, but it works only on `T: Sized`.
+fn data_offset_sized<T>() -> isize {
+    let align = align_of::<T>();
+    let layout = Layout::new::<RcBox<()>>();
+    (layout.size() + layout.padding_needed_for(align)) as isize
+}
index 8768f1ff081c1f1fadfc7a291867dfd06db8bee4..aeb7f90d3e60e946d0d0e8efc19948bb8b2ef6a0 100644 (file)
 // `core::slice::SliceExt` - we need to supply these functions for the
 // `test_permutations` test
 mod hack {
-    use core::mem;
-
     use crate::boxed::Box;
     use crate::vec::Vec;
     #[cfg(test)]
     use crate::string::ToString;
 
-    pub fn into_vec<T>(mut b: Box<[T]>) -> Vec<T> {
+    pub fn into_vec<T>(b: Box<[T]>) -> Vec<T> {
         unsafe {
-            let xs = Vec::from_raw_parts(b.as_mut_ptr(), b.len(), b.len());
-            mem::forget(b);
+            let len = b.len();
+            let b = Box::into_raw(b);
+            let xs = Vec::from_raw_parts(b as *mut T, len, len);
             xs
         }
     }
index 90c7859b3db9ec457acdbc4f0b0f67fea0f105bf..70865656c510ee7b988d28ad86254a2e6b643f73 100644 (file)
@@ -13,7 +13,7 @@
 use core::fmt;
 use core::cmp::{self, Ordering};
 use core::intrinsics::abort;
-use core::mem::{self, align_of_val, size_of_val};
+use core::mem::{self, align_of, align_of_val, size_of_val};
 use core::ops::{Deref, Receiver, CoerceUnsized, DispatchFromDyn};
 use core::pin::Pin;
 use core::ptr::{self, NonNull};
@@ -397,11 +397,7 @@ pub fn into_raw(this: Self) -> *const T {
     /// ```
     #[stable(feature = "rc_raw", since = "1.17.0")]
     pub unsafe fn from_raw(ptr: *const T) -> Self {
-        // Align the unsized value to the end of the ArcInner.
-        // Because it is ?Sized, it will always be the last field in memory.
-        let align = align_of_val(&*ptr);
-        let layout = Layout::new::<ArcInner<()>>();
-        let offset = (layout.size() + layout.padding_needed_for(align)) as isize;
+        let offset = data_offset(ptr);
 
         // Reverse the offset to find the original ArcInner.
         let fake_ptr = ptr as *mut ArcInner<T>;
@@ -1071,6 +1067,144 @@ pub fn new() -> Weak<T> {
             ptr: NonNull::new(usize::MAX as *mut ArcInner<T>).expect("MAX is not 0"),
         }
     }
+
+    /// Returns a raw pointer to the object `T` pointed to by this `Weak<T>`.
+    ///
+    /// It is up to the caller to ensure that the object is still alive when accessing it through
+    /// the pointer.
+    ///
+    /// The pointer may be [`null`] or be dangling in case the object has already been destroyed.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::sync::{Arc, Weak};
+    /// use std::ptr;
+    ///
+    /// let strong = Arc::new(42);
+    /// let weak = Arc::downgrade(&strong);
+    /// // Both point to the same object
+    /// assert!(ptr::eq(&*strong, Weak::as_raw(&weak)));
+    /// // The strong here keeps it alive, so we can still access the object.
+    /// assert_eq!(42, unsafe { *Weak::as_raw(&weak) });
+    ///
+    /// drop(strong);
+    /// // But not any more. We can do Weak::as_raw(&weak), but accessing the pointer would lead to
+    /// // undefined behaviour.
+    /// // assert_eq!(42, unsafe { *Weak::as_raw(&weak) });
+    /// ```
+    ///
+    /// [`null`]: ../../std/ptr/fn.null.html
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub fn as_raw(this: &Self) -> *const T {
+        match this.inner() {
+            None => ptr::null(),
+            Some(inner) => {
+                let offset = data_offset_sized::<T>();
+                let ptr = inner as *const ArcInner<T>;
+                // Note: while the pointer we create may already point to dropped value, the
+                // allocation still lives (it must hold the weak point as long as we are alive).
+                // Therefore, the offset is OK to do, it won't get out of the allocation.
+                let ptr = unsafe { (ptr as *const u8).offset(offset) };
+                ptr as *const T
+            }
+        }
+    }
+
+    /// Consumes the `Weak<T>` and turns it into a raw pointer.
+    ///
+    /// This converts the weak pointer into a raw pointer, preserving the original weak count. It
+    /// can be turned back into the `Weak<T>` with [`from_raw`].
+    ///
+    /// The same restrictions of accessing the target of the pointer as with
+    /// [`as_raw`] apply.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::sync::{Arc, Weak};
+    ///
+    /// let strong = Arc::new(42);
+    /// let weak = Arc::downgrade(&strong);
+    /// let raw = Weak::into_raw(weak);
+    ///
+    /// assert_eq!(1, Arc::weak_count(&strong));
+    /// assert_eq!(42, unsafe { *raw });
+    ///
+    /// drop(unsafe { Weak::from_raw(raw) });
+    /// assert_eq!(0, Arc::weak_count(&strong));
+    /// ```
+    ///
+    /// [`from_raw`]: struct.Weak.html#method.from_raw
+    /// [`as_raw`]: struct.Weak.html#method.as_raw
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub fn into_raw(this: Self) -> *const T {
+        let result = Self::as_raw(&this);
+        mem::forget(this);
+        result
+    }
+
+    /// Converts a raw pointer previously created by [`into_raw`] back into
+    /// `Weak<T>`.
+    ///
+    /// This can be used to safely get a strong reference (by calling [`upgrade`]
+    /// later) or to deallocate the weak count by dropping the `Weak<T>`.
+    ///
+    /// It takes ownership of one weak count. In case a [`null`] is passed, a dangling [`Weak`] is
+    /// returned.
+    ///
+    /// # Safety
+    ///
+    /// The pointer must represent one valid weak count. In other words, it must point to `T` which
+    /// is or *was* managed by an [`Arc`] and the weak count of that [`Arc`] must not have reached
+    /// 0. It is allowed for the strong count to be 0.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// #![feature(weak_into_raw)]
+    ///
+    /// use std::sync::{Arc, Weak};
+    ///
+    /// let strong = Arc::new(42);
+    ///
+    /// let raw_1 = Weak::into_raw(Arc::downgrade(&strong));
+    /// let raw_2 = Weak::into_raw(Arc::downgrade(&strong));
+    ///
+    /// assert_eq!(2, Arc::weak_count(&strong));
+    ///
+    /// assert_eq!(42, *Weak::upgrade(&unsafe { Weak::from_raw(raw_1) }).unwrap());
+    /// assert_eq!(1, Arc::weak_count(&strong));
+    ///
+    /// drop(strong);
+    ///
+    /// // Decrement the last weak count.
+    /// assert!(Weak::upgrade(&unsafe { Weak::from_raw(raw_2) }).is_none());
+    /// ```
+    ///
+    /// [`null`]: ../../std/ptr/fn.null.html
+    /// [`into_raw`]: struct.Weak.html#method.into_raw
+    /// [`upgrade`]: struct.Weak.html#method.upgrade
+    /// [`Weak`]: struct.Weak.html
+    /// [`Arc`]: struct.Arc.html
+    #[unstable(feature = "weak_into_raw", issue = "60728")]
+    pub unsafe fn from_raw(ptr: *const T) -> Self {
+        if ptr.is_null() {
+            Self::new()
+        } else {
+            // See Arc::from_raw for details
+            let offset = data_offset(ptr);
+            let fake_ptr = ptr as *mut ArcInner<T>;
+            let ptr = set_data_ptr(fake_ptr, (ptr as *mut u8).offset(-offset));
+            Weak {
+                ptr: NonNull::new(ptr).expect("Invalid pointer passed to from_raw"),
+            }
+        }
+    }
 }
 
 impl<T: ?Sized> Weak<T> {
@@ -2150,3 +2284,21 @@ fn as_ref(&self) -> &T {
 
 #[stable(feature = "pin", since = "1.33.0")]
 impl<T: ?Sized> Unpin for Arc<T> { }
+
+/// Computes the offset of the data field within ArcInner.
+unsafe fn data_offset<T: ?Sized>(ptr: *const T) -> isize {
+    // Align the unsized value to the end of the ArcInner.
+    // Because it is ?Sized, it will always be the last field in memory.
+    let align = align_of_val(&*ptr);
+    let layout = Layout::new::<ArcInner<()>>();
+    (layout.size() + layout.padding_needed_for(align)) as isize
+}
+
+/// Computes the offset of the data field within ArcInner.
+///
+/// Unlike [`data_offset`], this doesn't need the pointer, but it works only on `T: Sized`.
+fn data_offset_sized<T>() -> isize {
+    let align = align_of::<T>();
+    let layout = Layout::new::<ArcInner<()>>();
+    (layout.size() + layout.padding_needed_for(align)) as isize
+}
index 80341409037683e6db06685ec7b9c424839fdab7..9d26ecbacdcbbad1802e727b706cd2a5821450ad 100644 (file)
@@ -967,7 +967,6 @@ pub fn get_mut(&mut self) -> &mut T {
     /// # Examples
     ///
     /// ```
-    /// #![feature(borrow_state)]
     /// use std::cell::RefCell;
     ///
     /// let c = RefCell::new(5);
@@ -982,7 +981,7 @@ pub fn get_mut(&mut self) -> &mut T {
     ///     assert!(unsafe { c.try_borrow_unguarded() }.is_ok());
     /// }
     /// ```
-    #[unstable(feature = "borrow_state", issue = "27733")]
+    #[stable(feature = "borrow_state", since = "1.37.0")]
     #[inline]
     pub unsafe fn try_borrow_unguarded(&self) -> Result<&T, BorrowError> {
         if !is_writing(self.borrow.get()) {
index f8a975cc8d47fc3d37f4cb663300c6d540efe1cc..6bbf776fb8f17bb7d6f14266e398ad3fc9e029bc 100644 (file)
@@ -34,6 +34,13 @@ pub trait Step: Clone + PartialOrd + Sized {
 
     /// Adds a `usize`, returning `None` on overflow.
     fn add_usize(&self, n: usize) -> Option<Self>;
+
+    /// Subtracts a `usize`, returning `None` on underflow.
+    fn sub_usize(&self, n: usize) -> Option<Self> {
+        // this default implementation makes the addition of `sub_usize` a non-breaking change
+        let _ = n;
+        unimplemented!()
+    }
 }
 
 // These are still macro-generated because the integer literals resolve to different types.
@@ -85,6 +92,15 @@ fn add_usize(&self, n: usize) -> Option<Self> {
                 }
             }
 
+            #[inline]
+            #[allow(unreachable_patterns)]
+            fn sub_usize(&self, n: usize) -> Option<Self> {
+                match <$t>::try_from(n) {
+                    Ok(n_as_t) => self.checked_sub(n_as_t),
+                    Err(_) => None,
+                }
+            }
+
             step_identical_methods!();
         }
     )*)
@@ -125,6 +141,25 @@ fn add_usize(&self, n: usize) -> Option<Self> {
                 }
             }
 
+            #[inline]
+            #[allow(unreachable_patterns)]
+            fn sub_usize(&self, n: usize) -> Option<Self> {
+                match <$unsigned>::try_from(n) {
+                    Ok(n_as_unsigned) => {
+                        // Wrapping in unsigned space handles cases like
+                        // `80_i8.sub_usize(200) == Some(-120_i8)`,
+                        // even though 200_usize is out of range for i8.
+                        let wrapped = (*self as $unsigned).wrapping_sub(n_as_unsigned) as $t;
+                        if wrapped <= *self {
+                            Some(wrapped)
+                        } else {
+                            None  // Subtraction underflowed
+                        }
+                    }
+                    Err(_) => None,
+                }
+            }
+
             step_identical_methods!();
         }
     )*)
index 7815fe9c59d08636a4af8950bc4c53811641e096..4eac5cbc8e6623142563d8e3186994e4ceb3bfe1 100644 (file)
@@ -223,3 +223,113 @@ fn product<I>(iter: I) -> Result<T, E>
         ResultShunt::process(iter, |i| i.product())
     }
 }
+
+/// An iterator adapter that produces output as long as the underlying
+/// iterator produces `Option::Some` values.
+struct OptionShunt<I> {
+    iter: I,
+    exited_early: bool,
+}
+
+impl<I, T> OptionShunt<I>
+where
+    I: Iterator<Item = Option<T>>,
+{
+    /// Process the given iterator as if it yielded a `T` instead of a
+    /// `Option<T>`. Any `None` value will stop the inner iterator and
+    /// the overall result will be a `None`.
+    pub fn process<F, U>(iter: I, mut f: F) -> Option<U>
+    where
+        F: FnMut(&mut Self) -> U,
+    {
+        let mut shunt = OptionShunt::new(iter);
+        let value = f(shunt.by_ref());
+        shunt.reconstruct(value)
+    }
+
+    fn new(iter: I) -> Self {
+        OptionShunt {
+            iter,
+            exited_early: false,
+        }
+    }
+
+    /// Consume the adapter and rebuild a `Option` value.
+    fn reconstruct<U>(self, val: U) -> Option<U> {
+        if self.exited_early {
+            None
+        } else {
+            Some(val)
+        }
+    }
+}
+
+impl<I, T> Iterator for OptionShunt<I>
+where
+    I: Iterator<Item = Option<T>>,
+{
+    type Item = T;
+
+    fn next(&mut self) -> Option<Self::Item> {
+        match self.iter.next() {
+            Some(Some(v)) => Some(v),
+            Some(None) => {
+                self.exited_early = true;
+                None
+            }
+            None => None,
+        }
+    }
+
+    fn size_hint(&self) -> (usize, Option<usize>) {
+        if self.exited_early {
+            (0, Some(0))
+        } else {
+            let (_, upper) = self.iter.size_hint();
+            (0, upper)
+        }
+    }
+}
+
+#[stable(feature = "iter_arith_traits_option", since = "1.37.0")]
+impl<T, U> Sum<Option<U>> for Option<T>
+where
+    T: Sum<U>,
+{
+    /// Takes each element in the `Iterator`: if it is a `None`, no further
+    /// elements are taken, and the `None` is returned. Should no `None` occur,
+    /// the sum of all elements is returned.
+    ///
+    /// # Examples
+    ///
+    /// This sums up the position of the character 'a' in a vector of strings,
+    /// if a word did not have the character 'a' the operation returns `None`:
+    ///
+    /// ```
+    /// let words = vec!["have", "a", "great", "day"];
+    /// let total: Option<usize> = words.iter().map(|w| w.find('a')).sum();
+    /// assert_eq!(total, Some(5));
+    /// ```
+    fn sum<I>(iter: I) -> Option<T>
+    where
+        I: Iterator<Item = Option<U>>,
+    {
+        OptionShunt::process(iter, |i| i.sum())
+    }
+}
+
+#[stable(feature = "iter_arith_traits_option", since = "1.37.0")]
+impl<T, U> Product<Option<U>> for Option<T>
+where
+    T: Product<U>,
+{
+    /// Takes each element in the `Iterator`: if it is a `None`, no further
+    /// elements are taken, and the `None` is returned. Should no `None` occur,
+    /// the product of all elements is returned.
+    fn product<I>(iter: I) -> Option<T>
+    where
+        I: Iterator<Item = Option<U>>,
+    {
+        OptionShunt::process(iter, |i| i.product())
+    }
+}
diff --git a/src/libcore/mem.rs b/src/libcore/mem.rs
deleted file mode 100644 (file)
index ce4aee7..0000000
+++ /dev/null
@@ -1,1403 +0,0 @@
-//! Basic functions for dealing with memory.
-//!
-//! This module contains functions for querying the size and alignment of
-//! types, initializing and manipulating memory.
-
-#![stable(feature = "rust1", since = "1.0.0")]
-
-use crate::clone;
-use crate::cmp;
-use crate::fmt;
-use crate::hash;
-use crate::intrinsics;
-use crate::marker::{Copy, PhantomData, Sized};
-use crate::ptr;
-use crate::ops::{Deref, DerefMut};
-
-#[stable(feature = "rust1", since = "1.0.0")]
-#[doc(inline)]
-pub use crate::intrinsics::transmute;
-
-/// Takes ownership and "forgets" about the value **without running its destructor**.
-///
-/// Any resources the value manages, such as heap memory or a file handle, will linger
-/// forever in an unreachable state. However, it does not guarantee that pointers
-/// to this memory will remain valid.
-///
-/// * If you want to leak memory, see [`Box::leak`][leak].
-/// * If you want to obtain a raw pointer to the memory, see [`Box::into_raw`][into_raw].
-/// * If you want to dispose of a value properly, running its destructor, see
-/// [`mem::drop`][drop].
-///
-/// # Safety
-///
-/// `forget` is not marked as `unsafe`, because Rust's safety guarantees
-/// do not include a guarantee that destructors will always run. For example,
-/// a program can create a reference cycle using [`Rc`][rc], or call
-/// [`process::exit`][exit] to exit without running destructors. Thus, allowing
-/// `mem::forget` from safe code does not fundamentally change Rust's safety
-/// guarantees.
-///
-/// That said, leaking resources such as memory or I/O objects is usually undesirable,
-/// so `forget` is only recommended for specialized use cases like those shown below.
-///
-/// Because forgetting a value is allowed, any `unsafe` code you write must
-/// allow for this possibility. You cannot return a value and expect that the
-/// caller will necessarily run the value's destructor.
-///
-/// [rc]: ../../std/rc/struct.Rc.html
-/// [exit]: ../../std/process/fn.exit.html
-///
-/// # Examples
-///
-/// Leak an I/O object, never closing the file:
-///
-/// ```no_run
-/// use std::mem;
-/// use std::fs::File;
-///
-/// let file = File::open("foo.txt").unwrap();
-/// mem::forget(file);
-/// ```
-///
-/// The practical use cases for `forget` are rather specialized and mainly come
-/// up in unsafe or FFI code.
-///
-/// [drop]: fn.drop.html
-/// [uninit]: fn.uninitialized.html
-/// [clone]: ../clone/trait.Clone.html
-/// [swap]: fn.swap.html
-/// [box]: ../../std/boxed/struct.Box.html
-/// [leak]: ../../std/boxed/struct.Box.html#method.leak
-/// [into_raw]: ../../std/boxed/struct.Box.html#method.into_raw
-/// [ub]: ../../reference/behavior-considered-undefined.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn forget<T>(t: T) {
-    ManuallyDrop::new(t);
-}
-
-/// Like [`forget`], but also accepts unsized values.
-///
-/// This function is just a shim intended to be removed when the `unsized_locals` feature gets
-/// stabilized.
-///
-/// [`forget`]: fn.forget.html
-#[inline]
-#[unstable(feature = "forget_unsized", issue = "0")]
-pub fn forget_unsized<T: ?Sized>(t: T) {
-    unsafe { intrinsics::forget(t) }
-}
-
-/// Returns the size of a type in bytes.
-///
-/// More specifically, this is the offset in bytes between successive elements
-/// in an array with that item type including alignment padding. Thus, for any
-/// type `T` and length `n`, `[T; n]` has a size of `n * size_of::<T>()`.
-///
-/// In general, the size of a type is not stable across compilations, but
-/// specific types such as primitives are.
-///
-/// The following table gives the size for primitives.
-///
-/// Type | size_of::\<Type>()
-/// ---- | ---------------
-/// () | 0
-/// bool | 1
-/// u8 | 1
-/// u16 | 2
-/// u32 | 4
-/// u64 | 8
-/// u128 | 16
-/// i8 | 1
-/// i16 | 2
-/// i32 | 4
-/// i64 | 8
-/// i128 | 16
-/// f32 | 4
-/// f64 | 8
-/// char | 4
-///
-/// Furthermore, `usize` and `isize` have the same size.
-///
-/// The types `*const T`, `&T`, `Box<T>`, `Option<&T>`, and `Option<Box<T>>` all have
-/// the same size. If `T` is Sized, all of those types have the same size as `usize`.
-///
-/// The mutability of a pointer does not change its size. As such, `&T` and `&mut T`
-/// have the same size. Likewise for `*const T` and `*mut T`.
-///
-/// # Size of `#[repr(C)]` items
-///
-/// The `C` representation for items has a defined layout. With this layout,
-/// the size of items is also stable as long as all fields have a stable size.
-///
-/// ## Size of Structs
-///
-/// For `structs`, the size is determined by the following algorithm.
-///
-/// For each field in the struct ordered by declaration order:
-///
-/// 1. Add the size of the field.
-/// 2. Round up the current size to the nearest multiple of the next field's [alignment].
-///
-/// Finally, round the size of the struct to the nearest multiple of its [alignment].
-/// The alignment of the struct is usually the largest alignment of all its
-/// fields; this can be changed with the use of `repr(align(N))`.
-///
-/// Unlike `C`, zero sized structs are not rounded up to one byte in size.
-///
-/// ## Size of Enums
-///
-/// Enums that carry no data other than the discriminant have the same size as C enums
-/// on the platform they are compiled for.
-///
-/// ## Size of Unions
-///
-/// The size of a union is the size of its largest field.
-///
-/// Unlike `C`, zero sized unions are not rounded up to one byte in size.
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// // Some primitives
-/// assert_eq!(4, mem::size_of::<i32>());
-/// assert_eq!(8, mem::size_of::<f64>());
-/// assert_eq!(0, mem::size_of::<()>());
-///
-/// // Some arrays
-/// assert_eq!(8, mem::size_of::<[i32; 2]>());
-/// assert_eq!(12, mem::size_of::<[i32; 3]>());
-/// assert_eq!(0, mem::size_of::<[i32; 0]>());
-///
-///
-/// // Pointer size equality
-/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<*const i32>());
-/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<Box<i32>>());
-/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<Option<&i32>>());
-/// assert_eq!(mem::size_of::<Box<i32>>(), mem::size_of::<Option<Box<i32>>>());
-/// ```
-///
-/// Using `#[repr(C)]`.
-///
-/// ```
-/// use std::mem;
-///
-/// #[repr(C)]
-/// struct FieldStruct {
-///     first: u8,
-///     second: u16,
-///     third: u8
-/// }
-///
-/// // The size of the first field is 1, so add 1 to the size. Size is 1.
-/// // The alignment of the second field is 2, so add 1 to the size for padding. Size is 2.
-/// // The size of the second field is 2, so add 2 to the size. Size is 4.
-/// // The alignment of the third field is 1, so add 0 to the size for padding. Size is 4.
-/// // The size of the third field is 1, so add 1 to the size. Size is 5.
-/// // Finally, the alignment of the struct is 2 (because the largest alignment amongst its
-/// // fields is 2), so add 1 to the size for padding. Size is 6.
-/// assert_eq!(6, mem::size_of::<FieldStruct>());
-///
-/// #[repr(C)]
-/// struct TupleStruct(u8, u16, u8);
-///
-/// // Tuple structs follow the same rules.
-/// assert_eq!(6, mem::size_of::<TupleStruct>());
-///
-/// // Note that reordering the fields can lower the size. We can remove both padding bytes
-/// // by putting `third` before `second`.
-/// #[repr(C)]
-/// struct FieldStructOptimized {
-///     first: u8,
-///     third: u8,
-///     second: u16
-/// }
-///
-/// assert_eq!(4, mem::size_of::<FieldStructOptimized>());
-///
-/// // Union size is the size of the largest field.
-/// #[repr(C)]
-/// union ExampleUnion {
-///     smaller: u8,
-///     larger: u16
-/// }
-///
-/// assert_eq!(2, mem::size_of::<ExampleUnion>());
-/// ```
-///
-/// [alignment]: ./fn.align_of.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_promotable]
-pub const fn size_of<T>() -> usize {
-    intrinsics::size_of::<T>()
-}
-
-/// Returns the size of the pointed-to value in bytes.
-///
-/// This is usually the same as `size_of::<T>()`. However, when `T` *has* no
-/// statically-known size, e.g., a slice [`[T]`][slice] or a [trait object],
-/// then `size_of_val` can be used to get the dynamically-known size.
-///
-/// [slice]: ../../std/primitive.slice.html
-/// [trait object]: ../../book/ch17-02-trait-objects.html
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// assert_eq!(4, mem::size_of_val(&5i32));
-///
-/// let x: [u8; 13] = [0; 13];
-/// let y: &[u8] = &x;
-/// assert_eq!(13, mem::size_of_val(y));
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn size_of_val<T: ?Sized>(val: &T) -> usize {
-    unsafe { intrinsics::size_of_val(val) }
-}
-
-/// Returns the [ABI]-required minimum alignment of a type.
-///
-/// Every reference to a value of the type `T` must be a multiple of this number.
-///
-/// This is the alignment used for struct fields. It may be smaller than the preferred alignment.
-///
-/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
-///
-/// # Examples
-///
-/// ```
-/// # #![allow(deprecated)]
-/// use std::mem;
-///
-/// assert_eq!(4, mem::min_align_of::<i32>());
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_deprecated(reason = "use `align_of` instead", since = "1.2.0")]
-pub fn min_align_of<T>() -> usize {
-    intrinsics::min_align_of::<T>()
-}
-
-/// Returns the [ABI]-required minimum alignment of the type of the value that `val` points to.
-///
-/// Every reference to a value of the type `T` must be a multiple of this number.
-///
-/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
-///
-/// # Examples
-///
-/// ```
-/// # #![allow(deprecated)]
-/// use std::mem;
-///
-/// assert_eq!(4, mem::min_align_of_val(&5i32));
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_deprecated(reason = "use `align_of_val` instead", since = "1.2.0")]
-pub fn min_align_of_val<T: ?Sized>(val: &T) -> usize {
-    unsafe { intrinsics::min_align_of_val(val) }
-}
-
-/// Returns the [ABI]-required minimum alignment of a type.
-///
-/// Every reference to a value of the type `T` must be a multiple of this number.
-///
-/// This is the alignment used for struct fields. It may be smaller than the preferred alignment.
-///
-/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// assert_eq!(4, mem::align_of::<i32>());
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_promotable]
-pub const fn align_of<T>() -> usize {
-    intrinsics::min_align_of::<T>()
-}
-
-/// Returns the [ABI]-required minimum alignment of the type of the value that `val` points to.
-///
-/// Every reference to a value of the type `T` must be a multiple of this number.
-///
-/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// assert_eq!(4, mem::align_of_val(&5i32));
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn align_of_val<T: ?Sized>(val: &T) -> usize {
-    unsafe { intrinsics::min_align_of_val(val) }
-}
-
-/// Returns `true` if dropping values of type `T` matters.
-///
-/// This is purely an optimization hint, and may be implemented conservatively:
-/// it may return `true` for types that don't actually need to be dropped.
-/// As such always returning `true` would be a valid implementation of
-/// this function. However if this function actually returns `false`, then you
-/// can be certain dropping `T` has no side effect.
-///
-/// Low level implementations of things like collections, which need to manually
-/// drop their data, should use this function to avoid unnecessarily
-/// trying to drop all their contents when they are destroyed. This might not
-/// make a difference in release builds (where a loop that has no side-effects
-/// is easily detected and eliminated), but is often a big win for debug builds.
-///
-/// Note that `ptr::drop_in_place` already performs this check, so if your workload
-/// can be reduced to some small number of drop_in_place calls, using this is
-/// unnecessary. In particular note that you can drop_in_place a slice, and that
-/// will do a single needs_drop check for all the values.
-///
-/// Types like Vec therefore just `drop_in_place(&mut self[..])` without using
-/// needs_drop explicitly. Types like HashMap, on the other hand, have to drop
-/// values one at a time and should use this API.
-///
-///
-/// # Examples
-///
-/// Here's an example of how a collection might make use of needs_drop:
-///
-/// ```
-/// use std::{mem, ptr};
-///
-/// pub struct MyCollection<T> {
-/// #   data: [T; 1],
-///     /* ... */
-/// }
-/// # impl<T> MyCollection<T> {
-/// #   fn iter_mut(&mut self) -> &mut [T] { &mut self.data }
-/// #   fn free_buffer(&mut self) {}
-/// # }
-///
-/// impl<T> Drop for MyCollection<T> {
-///     fn drop(&mut self) {
-///         unsafe {
-///             // drop the data
-///             if mem::needs_drop::<T>() {
-///                 for x in self.iter_mut() {
-///                     ptr::drop_in_place(x);
-///                 }
-///             }
-///             self.free_buffer();
-///         }
-///     }
-/// }
-/// ```
-#[inline]
-#[stable(feature = "needs_drop", since = "1.21.0")]
-pub const fn needs_drop<T>() -> bool {
-    intrinsics::needs_drop::<T>()
-}
-
-/// Creates a value whose bytes are all zero.
-///
-/// This has the same effect as [`MaybeUninit::zeroed().assume_init()`][zeroed].
-/// It is useful for FFI sometimes, but should generally be avoided.
-///
-/// There is no guarantee that an all-zero byte-pattern represents a valid value of
-/// some type `T`. For example, the all-zero byte-pattern is not a valid value
-/// for reference types (`&T` and `&mut T`). Using `zeroed` on such types
-/// causes immediate [undefined behavior][ub] because [the Rust compiler assumes][inv]
-/// that there always is a valid value in a variable it considers initialized.
-///
-/// [zeroed]: union.MaybeUninit.html#method.zeroed
-/// [ub]: ../../reference/behavior-considered-undefined.html
-/// [inv]: union.MaybeUninit.html#initialization-invariant
-///
-/// # Examples
-///
-/// Correct usage of this function: initializing an integer with zero.
-///
-/// ```
-/// use std::mem;
-///
-/// let x: i32 = unsafe { mem::zeroed() };
-/// assert_eq!(0, x);
-/// ```
-///
-/// *Incorrect* usage of this function: initializing a reference with zero.
-///
-/// ```no_run
-/// use std::mem;
-///
-/// let _x: &i32 = unsafe { mem::zeroed() }; // Undefined behavior!
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn zeroed<T>() -> T {
-    intrinsics::panic_if_uninhabited::<T>();
-    intrinsics::init()
-}
-
-/// Bypasses Rust's normal memory-initialization checks by pretending to
-/// produce a value of type `T`, while doing nothing at all.
-///
-/// **This functon is deprecated.** Use [`MaybeUninit<T>`] instead.
-///
-/// The reason for deprecation is that the function basically cannot be used
-/// correctly: [the Rust compiler assumes][inv] that values are properly initialized.
-/// As a consequence, calling e.g. `mem::uninitialized::<bool>()` causes immediate
-/// undefined behavior for returning a `bool` that is not definitely either `true`
-/// or `false`. Worse, truly uninitialized memory like what gets returned here
-/// is special in that the compiler knows that it does not have a fixed value.
-/// This makes it undefined behavior to have uninitialized data in a variable even
-/// if that variable has an integer type.
-/// (Notice that the rules around uninitialized integers are not finalized yet, but
-/// until they are, it is advisable to avoid them.)
-///
-/// [`MaybeUninit<T>`]: union.MaybeUninit.html
-/// [inv]: union.MaybeUninit.html#initialization-invariant
-#[inline]
-#[rustc_deprecated(since = "1.38.0", reason = "use `mem::MaybeUninit` instead")]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn uninitialized<T>() -> T {
-    intrinsics::panic_if_uninhabited::<T>();
-    intrinsics::uninit()
-}
-
-/// Swaps the values at two mutable locations, without deinitializing either one.
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// let mut x = 5;
-/// let mut y = 42;
-///
-/// mem::swap(&mut x, &mut y);
-///
-/// assert_eq!(42, x);
-/// assert_eq!(5, y);
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn swap<T>(x: &mut T, y: &mut T) {
-    unsafe {
-        ptr::swap_nonoverlapping_one(x, y);
-    }
-}
-
-/// Moves `src` into the referenced `dest`, returning the previous `dest` value.
-///
-/// Neither value is dropped.
-///
-/// # Examples
-///
-/// A simple example:
-///
-/// ```
-/// use std::mem;
-///
-/// let mut v: Vec<i32> = vec![1, 2];
-///
-/// let old_v = mem::replace(&mut v, vec![3, 4, 5]);
-/// assert_eq!(vec![1, 2], old_v);
-/// assert_eq!(vec![3, 4, 5], v);
-/// ```
-///
-/// `replace` allows consumption of a struct field by replacing it with another value.
-/// Without `replace` you can run into issues like these:
-///
-/// ```compile_fail,E0507
-/// struct Buffer<T> { buf: Vec<T> }
-///
-/// impl<T> Buffer<T> {
-///     fn get_and_reset(&mut self) -> Vec<T> {
-///         // error: cannot move out of dereference of `&mut`-pointer
-///         let buf = self.buf;
-///         self.buf = Vec::new();
-///         buf
-///     }
-/// }
-/// ```
-///
-/// Note that `T` does not necessarily implement [`Clone`], so it can't even clone and reset
-/// `self.buf`. But `replace` can be used to disassociate the original value of `self.buf` from
-/// `self`, allowing it to be returned:
-///
-/// ```
-/// # #![allow(dead_code)]
-/// use std::mem;
-///
-/// # struct Buffer<T> { buf: Vec<T> }
-/// impl<T> Buffer<T> {
-///     fn get_and_reset(&mut self) -> Vec<T> {
-///         mem::replace(&mut self.buf, Vec::new())
-///     }
-/// }
-/// ```
-///
-/// [`Clone`]: ../../std/clone/trait.Clone.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn replace<T>(dest: &mut T, mut src: T) -> T {
-    swap(dest, &mut src);
-    src
-}
-
-/// Disposes of a value.
-///
-/// This does call the argument's implementation of [`Drop`][drop].
-///
-/// This effectively does nothing for types which implement `Copy`, e.g.
-/// integers. Such values are copied and _then_ moved into the function, so the
-/// value persists after this function call.
-///
-/// This function is not magic; it is literally defined as
-///
-/// ```
-/// pub fn drop<T>(_x: T) { }
-/// ```
-///
-/// Because `_x` is moved into the function, it is automatically dropped before
-/// the function returns.
-///
-/// [drop]: ../ops/trait.Drop.html
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// let v = vec![1, 2, 3];
-///
-/// drop(v); // explicitly drop the vector
-/// ```
-///
-/// Since [`RefCell`] enforces the borrow rules at runtime, `drop` can
-/// release a [`RefCell`] borrow:
-///
-/// ```
-/// use std::cell::RefCell;
-///
-/// let x = RefCell::new(1);
-///
-/// let mut mutable_borrow = x.borrow_mut();
-/// *mutable_borrow = 1;
-///
-/// drop(mutable_borrow); // relinquish the mutable borrow on this slot
-///
-/// let borrow = x.borrow();
-/// println!("{}", *borrow);
-/// ```
-///
-/// Integers and other types implementing [`Copy`] are unaffected by `drop`.
-///
-/// ```
-/// #[derive(Copy, Clone)]
-/// struct Foo(u8);
-///
-/// let x = 1;
-/// let y = Foo(2);
-/// drop(x); // a copy of `x` is moved and dropped
-/// drop(y); // a copy of `y` is moved and dropped
-///
-/// println!("x: {}, y: {}", x, y.0); // still available
-/// ```
-///
-/// [`RefCell`]: ../../std/cell/struct.RefCell.html
-/// [`Copy`]: ../../std/marker/trait.Copy.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub fn drop<T>(_x: T) { }
-
-/// Interprets `src` as having type `&U`, and then reads `src` without moving
-/// the contained value.
-///
-/// This function will unsafely assume the pointer `src` is valid for
-/// [`size_of::<U>`][size_of] bytes by transmuting `&T` to `&U` and then reading
-/// the `&U`. It will also unsafely create a copy of the contained value instead of
-/// moving out of `src`.
-///
-/// It is not a compile-time error if `T` and `U` have different sizes, but it
-/// is highly encouraged to only invoke this function where `T` and `U` have the
-/// same size. This function triggers [undefined behavior][ub] if `U` is larger than
-/// `T`.
-///
-/// [ub]: ../../reference/behavior-considered-undefined.html
-/// [size_of]: fn.size_of.html
-///
-/// # Examples
-///
-/// ```
-/// use std::mem;
-///
-/// #[repr(packed)]
-/// struct Foo {
-///     bar: u8,
-/// }
-///
-/// let foo_slice = [10u8];
-///
-/// unsafe {
-///     // Copy the data from 'foo_slice' and treat it as a 'Foo'
-///     let mut foo_struct: Foo = mem::transmute_copy(&foo_slice);
-///     assert_eq!(foo_struct.bar, 10);
-///
-///     // Modify the copied data
-///     foo_struct.bar = 20;
-///     assert_eq!(foo_struct.bar, 20);
-/// }
-///
-/// // The contents of 'foo_slice' should not have changed
-/// assert_eq!(foo_slice, [10]);
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn transmute_copy<T, U>(src: &T) -> U {
-    ptr::read_unaligned(src as *const T as *const U)
-}
-
-/// Opaque type representing the discriminant of an enum.
-///
-/// See the [`discriminant`] function in this module for more information.
-///
-/// [`discriminant`]: fn.discriminant.html
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-pub struct Discriminant<T>(u64, PhantomData<fn() -> T>);
-
-// N.B. These trait implementations cannot be derived because we don't want any bounds on T.
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> Copy for Discriminant<T> {}
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> clone::Clone for Discriminant<T> {
-    fn clone(&self) -> Self {
-        *self
-    }
-}
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> cmp::PartialEq for Discriminant<T> {
-    fn eq(&self, rhs: &Self) -> bool {
-        self.0 == rhs.0
-    }
-}
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> cmp::Eq for Discriminant<T> {}
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> hash::Hash for Discriminant<T> {
-    fn hash<H: hash::Hasher>(&self, state: &mut H) {
-        self.0.hash(state);
-    }
-}
-
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-impl<T> fmt::Debug for Discriminant<T> {
-    fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
-        fmt.debug_tuple("Discriminant")
-           .field(&self.0)
-           .finish()
-    }
-}
-
-/// Returns a value uniquely identifying the enum variant in `v`.
-///
-/// If `T` is not an enum, calling this function will not result in undefined behavior, but the
-/// return value is unspecified.
-///
-/// # Stability
-///
-/// The discriminant of an enum variant may change if the enum definition changes. A discriminant
-/// of some variant will not change between compilations with the same compiler.
-///
-/// # Examples
-///
-/// This can be used to compare enums that carry data, while disregarding
-/// the actual data:
-///
-/// ```
-/// use std::mem;
-///
-/// enum Foo { A(&'static str), B(i32), C(i32) }
-///
-/// assert!(mem::discriminant(&Foo::A("bar")) == mem::discriminant(&Foo::A("baz")));
-/// assert!(mem::discriminant(&Foo::B(1))     == mem::discriminant(&Foo::B(2)));
-/// assert!(mem::discriminant(&Foo::B(3))     != mem::discriminant(&Foo::C(3)));
-/// ```
-#[stable(feature = "discriminant_value", since = "1.21.0")]
-pub fn discriminant<T>(v: &T) -> Discriminant<T> {
-    unsafe {
-        Discriminant(intrinsics::discriminant_value(v), PhantomData)
-    }
-}
-
-/// A wrapper to inhibit compiler from automatically calling `T`’s destructor.
-///
-/// This wrapper is 0-cost.
-///
-/// `ManuallyDrop<T>` is subject to the same layout optimizations as `T`.
-/// As a consequence, it has *no effect* on the assumptions that the compiler makes
-/// about all values being initialized at their type.  In particular, initializing
-/// a `ManuallyDrop<&mut T>` with [`mem::zeroed`] is undefined behavior.
-/// If you need to handle uninitialized data, use [`MaybeUninit<T>`] instead.
-///
-/// # Examples
-///
-/// This wrapper helps with explicitly documenting the drop order dependencies between fields of
-/// the type:
-///
-/// ```rust
-/// use std::mem::ManuallyDrop;
-/// struct Peach;
-/// struct Banana;
-/// struct Melon;
-/// struct FruitBox {
-///     // Immediately clear there’s something non-trivial going on with these fields.
-///     peach: ManuallyDrop<Peach>,
-///     melon: Melon, // Field that’s independent of the other two.
-///     banana: ManuallyDrop<Banana>,
-/// }
-///
-/// impl Drop for FruitBox {
-///     fn drop(&mut self) {
-///         unsafe {
-///             // Explicit ordering in which field destructors are run specified in the intuitive
-///             // location – the destructor of the structure containing the fields.
-///             // Moreover, one can now reorder fields within the struct however much they want.
-///             ManuallyDrop::drop(&mut self.peach);
-///             ManuallyDrop::drop(&mut self.banana);
-///         }
-///         // After destructor for `FruitBox` runs (this function), the destructor for Melon gets
-///         // invoked in the usual manner, as it is not wrapped in `ManuallyDrop`.
-///     }
-/// }
-/// ```
-///
-/// [`mem::zeroed`]: fn.zeroed.html
-/// [`MaybeUninit<T>`]: union.MaybeUninit.html
-#[stable(feature = "manually_drop", since = "1.20.0")]
-#[lang = "manually_drop"]
-#[derive(Copy, Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
-#[repr(transparent)]
-pub struct ManuallyDrop<T: ?Sized> {
-    value: T,
-}
-
-impl<T> ManuallyDrop<T> {
-    /// Wrap a value to be manually dropped.
-    ///
-    /// # Examples
-    ///
-    /// ```rust
-    /// use std::mem::ManuallyDrop;
-    /// ManuallyDrop::new(Box::new(()));
-    /// ```
-    #[stable(feature = "manually_drop", since = "1.20.0")]
-    #[inline(always)]
-    pub const fn new(value: T) -> ManuallyDrop<T> {
-        ManuallyDrop { value }
-    }
-
-    /// Extracts the value from the `ManuallyDrop` container.
-    ///
-    /// This allows the value to be dropped again.
-    ///
-    /// # Examples
-    ///
-    /// ```rust
-    /// use std::mem::ManuallyDrop;
-    /// let x = ManuallyDrop::new(Box::new(()));
-    /// let _: Box<()> = ManuallyDrop::into_inner(x); // This drops the `Box`.
-    /// ```
-    #[stable(feature = "manually_drop", since = "1.20.0")]
-    #[inline(always)]
-    pub const fn into_inner(slot: ManuallyDrop<T>) -> T {
-        slot.value
-    }
-
-    /// Takes the contained value out.
-    ///
-    /// This method is primarily intended for moving out values in drop.
-    /// Instead of using [`ManuallyDrop::drop`] to manually drop the value,
-    /// you can use this method to take the value and use it however desired.
-    /// `Drop` will be invoked on the returned value following normal end-of-scope rules.
-    ///
-    /// If you have ownership of the container, you can use [`ManuallyDrop::into_inner`] instead.
-    ///
-    /// # Safety
-    ///
-    /// This function semantically moves out the contained value without preventing further usage.
-    /// It is up to the user of this method to ensure that this container is not used again.
-    ///
-    /// [`ManuallyDrop::drop`]: #method.drop
-    /// [`ManuallyDrop::into_inner`]: #method.into_inner
-    #[must_use = "if you don't need the value, you can use `ManuallyDrop::drop` instead"]
-    #[unstable(feature = "manually_drop_take", issue = "55422")]
-    #[inline]
-    pub unsafe fn take(slot: &mut ManuallyDrop<T>) -> T {
-        ManuallyDrop::into_inner(ptr::read(slot))
-    }
-}
-
-impl<T: ?Sized> ManuallyDrop<T> {
-    /// Manually drops the contained value.
-    ///
-    /// If you have ownership of the value, you can use [`ManuallyDrop::into_inner`] instead.
-    ///
-    /// # Safety
-    ///
-    /// This function runs the destructor of the contained value and thus the wrapped value
-    /// now represents uninitialized data. It is up to the user of this method to ensure the
-    /// uninitialized data is not actually used.
-    ///
-    /// [`ManuallyDrop::into_inner`]: #method.into_inner
-    #[stable(feature = "manually_drop", since = "1.20.0")]
-    #[inline]
-    pub unsafe fn drop(slot: &mut ManuallyDrop<T>) {
-        ptr::drop_in_place(&mut slot.value)
-    }
-}
-
-#[stable(feature = "manually_drop", since = "1.20.0")]
-impl<T: ?Sized> Deref for ManuallyDrop<T> {
-    type Target = T;
-    #[inline(always)]
-    fn deref(&self) -> &T {
-        &self.value
-    }
-}
-
-#[stable(feature = "manually_drop", since = "1.20.0")]
-impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
-    #[inline(always)]
-    fn deref_mut(&mut self) -> &mut T {
-        &mut self.value
-    }
-}
-
-/// A wrapper type to construct uninitialized instances of `T`.
-///
-/// # Initialization invariant
-///
-/// The compiler, in general, assumes that variables are properly initialized
-/// at their respective type. For example, a variable of reference type must
-/// be aligned and non-NULL. This is an invariant that must *always* be upheld,
-/// even in unsafe code. As a consequence, zero-initializing a variable of reference
-/// type causes instantaneous [undefined behavior][ub], no matter whether that reference
-/// ever gets used to access memory:
-///
-/// ```rust,no_run
-/// use std::mem::{self, MaybeUninit};
-///
-/// let x: &i32 = unsafe { mem::zeroed() }; // undefined behavior!
-/// // The equivalent code with `MaybeUninit<&i32>`:
-/// let x: &i32 = unsafe { MaybeUninit::zeroed().assume_init() }; // undefined behavior!
-/// ```
-///
-/// This is exploited by the compiler for various optimizations, such as eliding
-/// run-time checks and optimizing `enum` layout.
-///
-/// Similarly, entirely uninitialized memory may have any content, while a `bool` must
-/// always be `true` or `false`. Hence, creating an uninitialized `bool` is undefined behavior:
-///
-/// ```rust,no_run
-/// use std::mem::{self, MaybeUninit};
-///
-/// let b: bool = unsafe { mem::uninitialized() }; // undefined behavior!
-/// // The equivalent code with `MaybeUninit<bool>`:
-/// let b: bool = unsafe { MaybeUninit::uninit().assume_init() }; // undefined behavior!
-/// ```
-///
-/// Moreover, uninitialized memory is special in that the compiler knows that
-/// it does not have a fixed value. This makes it undefined behavior to have
-/// uninitialized data in a variable even if that variable has an integer type,
-/// which otherwise can hold any *fixed* bit pattern:
-///
-/// ```rust,no_run
-/// use std::mem::{self, MaybeUninit};
-///
-/// let x: i32 = unsafe { mem::uninitialized() }; // undefined behavior!
-/// // The equivalent code with `MaybeUninit<i32>`:
-/// let x: i32 = unsafe { MaybeUninit::uninit().assume_init() }; // undefined behavior!
-/// ```
-/// (Notice that the rules around uninitialized integers are not finalized yet, but
-/// until they are, it is advisable to avoid them.)
-///
-/// On top of that, remember that most types have additional invariants beyond merely
-/// being considered initialized at the type level. For example, a `1`-initialized [`Vec<T>`]
-/// is considered initialized because the only requirement the compiler knows about it
-/// is that the data pointer must be non-null. Creating such a `Vec<T>` does not cause
-/// *immediate* undefined behavior, but will cause undefined behavior with most
-/// safe operations (including dropping it).
-///
-/// [`Vec<T>`]: ../../std/vec/struct.Vec.html
-///
-/// # Examples
-///
-/// `MaybeUninit<T>` serves to enable unsafe code to deal with uninitialized data.
-/// It is a signal to the compiler indicating that the data here might *not*
-/// be initialized:
-///
-/// ```rust
-/// use std::mem::MaybeUninit;
-///
-/// // Create an explicitly uninitialized reference. The compiler knows that data inside
-/// // a `MaybeUninit<T>` may be invalid, and hence this is not UB:
-/// let mut x = MaybeUninit::<&i32>::uninit();
-/// // Set it to a valid value.
-/// unsafe { x.as_mut_ptr().write(&0); }
-/// // Extract the initialized data -- this is only allowed *after* properly
-/// // initializing `x`!
-/// let x = unsafe { x.assume_init() };
-/// ```
-///
-/// The compiler then knows to not make any incorrect assumptions or optimizations on this code.
-///
-/// ## out-pointers
-///
-/// You can use `MaybeUninit<T>` to implement "out-pointers": instead of returning data
-/// from a function, pass it a pointer to some (uninitialized) memory to put the
-/// result into. This can be useful when it is important for the caller to control
-/// how the memory the result is stored in gets allocated, and you want to avoid
-/// unnecessary moves.
-///
-/// ```
-/// use std::mem::MaybeUninit;
-///
-/// unsafe fn make_vec(out: *mut Vec<i32>) {
-///     // `write` does not drop the old contents, which is important.
-///     out.write(vec![1, 2, 3]);
-/// }
-///
-/// let mut v = MaybeUninit::uninit();
-/// unsafe { make_vec(v.as_mut_ptr()); }
-/// // Now we know `v` is initialized! This also makes sure the vector gets
-/// // properly dropped.
-/// let v = unsafe { v.assume_init() };
-/// assert_eq!(&v, &[1, 2, 3]);
-/// ```
-///
-/// ## Initializing an array element-by-element
-///
-/// `MaybeUninit<T>` can be used to initialize a large array element-by-element:
-///
-/// ```
-/// use std::mem::{self, MaybeUninit};
-/// use std::ptr;
-///
-/// let data = {
-///     // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
-///     // safe because the type we are claiming to have initialized here is a
-///     // bunch of `MaybeUninit`s, which do not require initialization.
-///     let mut data: [MaybeUninit<Vec<u32>>; 1000] = unsafe {
-///         MaybeUninit::uninit().assume_init()
-///     };
-///
-///     // Dropping a `MaybeUninit` does nothing, so if there is a panic during this loop,
-///     // we have a memory leak, but there is no memory safety issue.
-///     for elem in &mut data[..] {
-///         unsafe { ptr::write(elem.as_mut_ptr(), vec![42]); }
-///     }
-///
-///     // Everything is initialized. Transmute the array to the
-///     // initialized type.
-///     unsafe { mem::transmute::<_, [Vec<u32>; 1000]>(data) }
-/// };
-///
-/// assert_eq!(&data[0], &[42]);
-/// ```
-///
-/// You can also work with partially initialized arrays, which could
-/// be found in low-level datastructures.
-///
-/// ```
-/// use std::mem::MaybeUninit;
-/// use std::ptr;
-///
-/// // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
-/// // safe because the type we are claiming to have initialized here is a
-/// // bunch of `MaybeUninit`s, which do not require initialization.
-/// let mut data: [MaybeUninit<String>; 1000] = unsafe { MaybeUninit::uninit().assume_init() };
-/// // Count the number of elements we have assigned.
-/// let mut data_len: usize = 0;
-///
-/// for elem in &mut data[0..500] {
-///     unsafe { ptr::write(elem.as_mut_ptr(), String::from("hello")); }
-///     data_len += 1;
-/// }
-///
-/// // For each item in the array, drop if we allocated it.
-/// for elem in &mut data[0..data_len] {
-///     unsafe { ptr::drop_in_place(elem.as_mut_ptr()); }
-/// }
-/// ```
-///
-/// ## Initializing a struct field-by-field
-///
-/// There is currently no supported way to create a raw pointer or reference
-/// to a field of a struct inside `MaybeUninit<Struct>`. That means it is not possible
-/// to create a struct by calling `MaybeUninit::uninit::<Struct>()` and then writing
-/// to its fields.
-///
-/// [ub]: ../../reference/behavior-considered-undefined.html
-///
-/// # Layout
-///
-/// `MaybeUninit<T>` is guaranteed to have the same size and alignment as `T`:
-///
-/// ```rust
-/// use std::mem::{MaybeUninit, size_of, align_of};
-/// assert_eq!(size_of::<MaybeUninit<u64>>(), size_of::<u64>());
-/// assert_eq!(align_of::<MaybeUninit<u64>>(), align_of::<u64>());
-/// ```
-///
-/// However remember that a type *containing* a `MaybeUninit<T>` is not necessarily the same
-/// layout; Rust does not in general guarantee that the fields of a `Foo<T>` have the same order as
-/// a `Foo<U>` even if `T` and `U` have the same size and alignment. Furthermore because any bit
-/// value is valid for a `MaybeUninit<T>` the compiler can't apply non-zero/niche-filling
-/// optimizations, potentially resulting in a larger size:
-///
-/// ```rust
-/// # use std::mem::{MaybeUninit, size_of};
-/// assert_eq!(size_of::<Option<bool>>(), 1);
-/// assert_eq!(size_of::<Option<MaybeUninit<bool>>>(), 2);
-/// ```
-#[allow(missing_debug_implementations)]
-#[stable(feature = "maybe_uninit", since = "1.36.0")]
-#[derive(Copy)]
-pub union MaybeUninit<T> {
-    uninit: (),
-    value: ManuallyDrop<T>,
-}
-
-#[stable(feature = "maybe_uninit", since = "1.36.0")]
-impl<T: Copy> Clone for MaybeUninit<T> {
-    #[inline(always)]
-    fn clone(&self) -> Self {
-        // Not calling `T::clone()`, we cannot know if we are initialized enough for that.
-        *self
-    }
-}
-
-impl<T> MaybeUninit<T> {
-    /// Creates a new `MaybeUninit<T>` initialized with the given value.
-    /// It is safe to call [`assume_init`] on the return value of this function.
-    ///
-    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
-    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
-    ///
-    /// [`assume_init`]: #method.assume_init
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline(always)]
-    pub const fn new(val: T) -> MaybeUninit<T> {
-        MaybeUninit { value: ManuallyDrop::new(val) }
-    }
-
-    /// Creates a new `MaybeUninit<T>` in an uninitialized state.
-    ///
-    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
-    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
-    ///
-    /// See the [type-level documentation][type] for some examples.
-    ///
-    /// [type]: union.MaybeUninit.html
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline(always)]
-    pub const fn uninit() -> MaybeUninit<T> {
-        MaybeUninit { uninit: () }
-    }
-
-    /// Creates a new `MaybeUninit<T>` in an uninitialized state, with the memory being
-    /// filled with `0` bytes. It depends on `T` whether that already makes for
-    /// proper initialization. For example, `MaybeUninit<usize>::zeroed()` is initialized,
-    /// but `MaybeUninit<&'static i32>::zeroed()` is not because references must not
-    /// be null.
-    ///
-    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
-    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
-    ///
-    /// # Example
-    ///
-    /// Correct usage of this function: initializing a struct with zero, where all
-    /// fields of the struct can hold the bit-pattern 0 as a valid value.
-    ///
-    /// ```rust
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let x = MaybeUninit::<(u8, bool)>::zeroed();
-    /// let x = unsafe { x.assume_init() };
-    /// assert_eq!(x, (0, false));
-    /// ```
-    ///
-    /// *Incorrect* usage of this function: initializing a struct with zero, where some fields
-    /// cannot hold 0 as a valid value.
-    ///
-    /// ```rust,no_run
-    /// use std::mem::MaybeUninit;
-    ///
-    /// enum NotZero { One = 1, Two = 2 };
-    ///
-    /// let x = MaybeUninit::<(u8, NotZero)>::zeroed();
-    /// let x = unsafe { x.assume_init() };
-    /// // Inside a pair, we create a `NotZero` that does not have a valid discriminant.
-    /// // This is undefined behavior.
-    /// ```
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline]
-    pub fn zeroed() -> MaybeUninit<T> {
-        let mut u = MaybeUninit::<T>::uninit();
-        unsafe {
-            u.as_mut_ptr().write_bytes(0u8, 1);
-        }
-        u
-    }
-
-    /// Sets the value of the `MaybeUninit<T>`. This overwrites any previous value
-    /// without dropping it, so be careful not to use this twice unless you want to
-    /// skip running the destructor. For your convenience, this also returns a mutable
-    /// reference to the (now safely initialized) contents of `self`.
-    #[unstable(feature = "maybe_uninit_extra", issue = "53491")]
-    #[inline(always)]
-    pub fn write(&mut self, val: T) -> &mut T {
-        unsafe {
-            self.value = ManuallyDrop::new(val);
-            self.get_mut()
-        }
-    }
-
-    /// Gets a pointer to the contained value. Reading from this pointer or turning it
-    /// into a reference is undefined behavior unless the `MaybeUninit<T>` is initialized.
-    /// Writing to memory that this pointer (non-transitively) points to is undefined behavior
-    /// (except inside an `UnsafeCell<T>`).
-    ///
-    /// # Examples
-    ///
-    /// Correct usage of this method:
-    ///
-    /// ```rust
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
-    /// unsafe { x.as_mut_ptr().write(vec![0,1,2]); }
-    /// // Create a reference into the `MaybeUninit<T>`. This is okay because we initialized it.
-    /// let x_vec = unsafe { &*x.as_ptr() };
-    /// assert_eq!(x_vec.len(), 3);
-    /// ```
-    ///
-    /// *Incorrect* usage of this method:
-    ///
-    /// ```rust,no_run
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let x = MaybeUninit::<Vec<u32>>::uninit();
-    /// let x_vec = unsafe { &*x.as_ptr() };
-    /// // We have created a reference to an uninitialized vector! This is undefined behavior.
-    /// ```
-    ///
-    /// (Notice that the rules around references to uninitialized data are not finalized yet, but
-    /// until they are, it is advisable to avoid them.)
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline(always)]
-    pub fn as_ptr(&self) -> *const T {
-        unsafe { &*self.value as *const T }
-    }
-
-    /// Gets a mutable pointer to the contained value. Reading from this pointer or turning it
-    /// into a reference is undefined behavior unless the `MaybeUninit<T>` is initialized.
-    ///
-    /// # Examples
-    ///
-    /// Correct usage of this method:
-    ///
-    /// ```rust
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
-    /// unsafe { x.as_mut_ptr().write(vec![0,1,2]); }
-    /// // Create a reference into the `MaybeUninit<Vec<u32>>`.
-    /// // This is okay because we initialized it.
-    /// let x_vec = unsafe { &mut *x.as_mut_ptr() };
-    /// x_vec.push(3);
-    /// assert_eq!(x_vec.len(), 4);
-    /// ```
-    ///
-    /// *Incorrect* usage of this method:
-    ///
-    /// ```rust,no_run
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
-    /// let x_vec = unsafe { &mut *x.as_mut_ptr() };
-    /// // We have created a reference to an uninitialized vector! This is undefined behavior.
-    /// ```
-    ///
-    /// (Notice that the rules around references to uninitialized data are not finalized yet, but
-    /// until they are, it is advisable to avoid them.)
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline(always)]
-    pub fn as_mut_ptr(&mut self) -> *mut T {
-        unsafe { &mut *self.value as *mut T }
-    }
-
-    /// Extracts the value from the `MaybeUninit<T>` container. This is a great way
-    /// to ensure that the data will get dropped, because the resulting `T` is
-    /// subject to the usual drop handling.
-    ///
-    /// # Safety
-    ///
-    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
-    /// state. Calling this when the content is not yet fully initialized causes immediate undefined
-    /// behavior. The [type-level documentation][inv] contains more information about
-    /// this initialization invariant.
-    ///
-    /// [inv]: #initialization-invariant
-    ///
-    /// # Examples
-    ///
-    /// Correct usage of this method:
-    ///
-    /// ```rust
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<bool>::uninit();
-    /// unsafe { x.as_mut_ptr().write(true); }
-    /// let x_init = unsafe { x.assume_init() };
-    /// assert_eq!(x_init, true);
-    /// ```
-    ///
-    /// *Incorrect* usage of this method:
-    ///
-    /// ```rust,no_run
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let x = MaybeUninit::<Vec<u32>>::uninit();
-    /// let x_init = unsafe { x.assume_init() };
-    /// // `x` had not been initialized yet, so this last line caused undefined behavior.
-    /// ```
-    #[stable(feature = "maybe_uninit", since = "1.36.0")]
-    #[inline(always)]
-    pub unsafe fn assume_init(self) -> T {
-        intrinsics::panic_if_uninhabited::<T>();
-        ManuallyDrop::into_inner(self.value)
-    }
-
-    /// Reads the value from the `MaybeUninit<T>` container. The resulting `T` is subject
-    /// to the usual drop handling.
-    ///
-    /// Whenever possible, it is preferrable to use [`assume_init`] instead, which
-    /// prevents duplicating the content of the `MaybeUninit<T>`.
-    ///
-    /// # Safety
-    ///
-    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
-    /// state. Calling this when the content is not yet fully initialized causes undefined
-    /// behavior. The [type-level documentation][inv] contains more information about
-    /// this initialization invariant.
-    ///
-    /// Moreover, this leaves a copy of the same data behind in the `MaybeUninit<T>`. When using
-    /// multiple copies of the data (by calling `read` multiple times, or first
-    /// calling `read` and then [`assume_init`]), it is your responsibility
-    /// to ensure that that data may indeed be duplicated.
-    ///
-    /// [inv]: #initialization-invariant
-    /// [`assume_init`]: #method.assume_init
-    ///
-    /// # Examples
-    ///
-    /// Correct usage of this method:
-    ///
-    /// ```rust
-    /// #![feature(maybe_uninit_extra)]
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<u32>::uninit();
-    /// x.write(13);
-    /// let x1 = unsafe { x.read() };
-    /// // `u32` is `Copy`, so we may read multiple times.
-    /// let x2 = unsafe { x.read() };
-    /// assert_eq!(x1, x2);
-    ///
-    /// let mut x = MaybeUninit::<Option<Vec<u32>>>::uninit();
-    /// x.write(None);
-    /// let x1 = unsafe { x.read() };
-    /// // Duplicating a `None` value is okay, so we may read multiple times.
-    /// let x2 = unsafe { x.read() };
-    /// assert_eq!(x1, x2);
-    /// ```
-    ///
-    /// *Incorrect* usage of this method:
-    ///
-    /// ```rust,no_run
-    /// #![feature(maybe_uninit_extra)]
-    /// use std::mem::MaybeUninit;
-    ///
-    /// let mut x = MaybeUninit::<Option<Vec<u32>>>::uninit();
-    /// x.write(Some(vec![0,1,2]));
-    /// let x1 = unsafe { x.read() };
-    /// let x2 = unsafe { x.read() };
-    /// // We now created two copies of the same vector, leading to a double-free when
-    /// // they both get dropped!
-    /// ```
-    #[unstable(feature = "maybe_uninit_extra", issue = "53491")]
-    #[inline(always)]
-    pub unsafe fn read(&self) -> T {
-        intrinsics::panic_if_uninhabited::<T>();
-        self.as_ptr().read()
-    }
-
-    /// Gets a reference to the contained value.
-    ///
-    /// # Safety
-    ///
-    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
-    /// state. Calling this when the content is not yet fully initialized causes undefined
-    /// behavior.
-    #[unstable(feature = "maybe_uninit_ref", issue = "53491")]
-    #[inline(always)]
-    pub unsafe fn get_ref(&self) -> &T {
-        &*self.value
-    }
-
-    /// Gets a mutable reference to the contained value.
-    ///
-    /// # Safety
-    ///
-    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
-    /// state. Calling this when the content is not yet fully initialized causes undefined
-    /// behavior.
-    // FIXME(#53491): We currently rely on the above being incorrect, i.e., we have references
-    // to uninitialized data (e.g., in `libcore/fmt/float.rs`).  We should make
-    // a final decision about the rules before stabilization.
-    #[unstable(feature = "maybe_uninit_ref", issue = "53491")]
-    #[inline(always)]
-    pub unsafe fn get_mut(&mut self) -> &mut T {
-        &mut *self.value
-    }
-
-    /// Gets a pointer to the first element of the array.
-    #[unstable(feature = "maybe_uninit_slice", issue = "53491")]
-    #[inline(always)]
-    pub fn first_ptr(this: &[MaybeUninit<T>]) -> *const T {
-        this as *const [MaybeUninit<T>] as *const T
-    }
-
-    /// Gets a mutable pointer to the first element of the array.
-    #[unstable(feature = "maybe_uninit_slice", issue = "53491")]
-    #[inline(always)]
-    pub fn first_ptr_mut(this: &mut [MaybeUninit<T>]) -> *mut T {
-        this as *mut [MaybeUninit<T>] as *mut T
-    }
-}
diff --git a/src/libcore/mem/manually_drop.rs b/src/libcore/mem/manually_drop.rs
new file mode 100644 (file)
index 0000000..3ad1223
--- /dev/null
@@ -0,0 +1,146 @@
+use crate::ptr;
+use crate::ops::{Deref, DerefMut};
+
+/// A wrapper to inhibit compiler from automatically calling `T`’s destructor.
+///
+/// This wrapper is 0-cost.
+///
+/// `ManuallyDrop<T>` is subject to the same layout optimizations as `T`.
+/// As a consequence, it has *no effect* on the assumptions that the compiler makes
+/// about all values being initialized at their type.  In particular, initializing
+/// a `ManuallyDrop<&mut T>` with [`mem::zeroed`] is undefined behavior.
+/// If you need to handle uninitialized data, use [`MaybeUninit<T>`] instead.
+///
+/// # Examples
+///
+/// This wrapper helps with explicitly documenting the drop order dependencies between fields of
+/// the type:
+///
+/// ```rust
+/// use std::mem::ManuallyDrop;
+/// struct Peach;
+/// struct Banana;
+/// struct Melon;
+/// struct FruitBox {
+///     // Immediately clear there’s something non-trivial going on with these fields.
+///     peach: ManuallyDrop<Peach>,
+///     melon: Melon, // Field that’s independent of the other two.
+///     banana: ManuallyDrop<Banana>,
+/// }
+///
+/// impl Drop for FruitBox {
+///     fn drop(&mut self) {
+///         unsafe {
+///             // Explicit ordering in which field destructors are run specified in the intuitive
+///             // location – the destructor of the structure containing the fields.
+///             // Moreover, one can now reorder fields within the struct however much they want.
+///             ManuallyDrop::drop(&mut self.peach);
+///             ManuallyDrop::drop(&mut self.banana);
+///         }
+///         // After destructor for `FruitBox` runs (this function), the destructor for Melon gets
+///         // invoked in the usual manner, as it is not wrapped in `ManuallyDrop`.
+///     }
+/// }
+/// ```
+///
+/// [`mem::zeroed`]: fn.zeroed.html
+/// [`MaybeUninit<T>`]: union.MaybeUninit.html
+#[stable(feature = "manually_drop", since = "1.20.0")]
+#[lang = "manually_drop"]
+#[derive(Copy, Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[repr(transparent)]
+pub struct ManuallyDrop<T: ?Sized> {
+    value: T,
+}
+
+impl<T> ManuallyDrop<T> {
+    /// Wrap a value to be manually dropped.
+    ///
+    /// # Examples
+    ///
+    /// ```rust
+    /// use std::mem::ManuallyDrop;
+    /// ManuallyDrop::new(Box::new(()));
+    /// ```
+    #[stable(feature = "manually_drop", since = "1.20.0")]
+    #[inline(always)]
+    pub const fn new(value: T) -> ManuallyDrop<T> {
+        ManuallyDrop { value }
+    }
+
+    /// Extracts the value from the `ManuallyDrop` container.
+    ///
+    /// This allows the value to be dropped again.
+    ///
+    /// # Examples
+    ///
+    /// ```rust
+    /// use std::mem::ManuallyDrop;
+    /// let x = ManuallyDrop::new(Box::new(()));
+    /// let _: Box<()> = ManuallyDrop::into_inner(x); // This drops the `Box`.
+    /// ```
+    #[stable(feature = "manually_drop", since = "1.20.0")]
+    #[inline(always)]
+    pub const fn into_inner(slot: ManuallyDrop<T>) -> T {
+        slot.value
+    }
+
+    /// Takes the contained value out.
+    ///
+    /// This method is primarily intended for moving out values in drop.
+    /// Instead of using [`ManuallyDrop::drop`] to manually drop the value,
+    /// you can use this method to take the value and use it however desired.
+    /// `Drop` will be invoked on the returned value following normal end-of-scope rules.
+    ///
+    /// If you have ownership of the container, you can use [`ManuallyDrop::into_inner`] instead.
+    ///
+    /// # Safety
+    ///
+    /// This function semantically moves out the contained value without preventing further usage.
+    /// It is up to the user of this method to ensure that this container is not used again.
+    ///
+    /// [`ManuallyDrop::drop`]: #method.drop
+    /// [`ManuallyDrop::into_inner`]: #method.into_inner
+    #[must_use = "if you don't need the value, you can use `ManuallyDrop::drop` instead"]
+    #[unstable(feature = "manually_drop_take", issue = "55422")]
+    #[inline]
+    pub unsafe fn take(slot: &mut ManuallyDrop<T>) -> T {
+        ManuallyDrop::into_inner(ptr::read(slot))
+    }
+}
+
+impl<T: ?Sized> ManuallyDrop<T> {
+    /// Manually drops the contained value.
+    ///
+    /// If you have ownership of the value, you can use [`ManuallyDrop::into_inner`] instead.
+    ///
+    /// # Safety
+    ///
+    /// This function runs the destructor of the contained value and thus the wrapped value
+    /// now represents uninitialized data. It is up to the user of this method to ensure the
+    /// uninitialized data is not actually used.
+    ///
+    /// [`ManuallyDrop::into_inner`]: #method.into_inner
+    #[stable(feature = "manually_drop", since = "1.20.0")]
+    #[inline]
+    pub unsafe fn drop(slot: &mut ManuallyDrop<T>) {
+        ptr::drop_in_place(&mut slot.value)
+    }
+}
+
+#[stable(feature = "manually_drop", since = "1.20.0")]
+impl<T: ?Sized> Deref for ManuallyDrop<T> {
+    type Target = T;
+    #[inline(always)]
+    fn deref(&self) -> &T {
+        &self.value
+    }
+}
+
+#[stable(feature = "manually_drop", since = "1.20.0")]
+impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
+    #[inline(always)]
+    fn deref_mut(&mut self) -> &mut T {
+        &mut self.value
+    }
+}
diff --git a/src/libcore/mem/maybe_uninit.rs b/src/libcore/mem/maybe_uninit.rs
new file mode 100644 (file)
index 0000000..eeff9d0
--- /dev/null
@@ -0,0 +1,519 @@
+use crate::intrinsics;
+use crate::mem::ManuallyDrop;
+
+/// A wrapper type to construct uninitialized instances of `T`.
+///
+/// # Initialization invariant
+///
+/// The compiler, in general, assumes that variables are properly initialized
+/// at their respective type. For example, a variable of reference type must
+/// be aligned and non-NULL. This is an invariant that must *always* be upheld,
+/// even in unsafe code. As a consequence, zero-initializing a variable of reference
+/// type causes instantaneous [undefined behavior][ub], no matter whether that reference
+/// ever gets used to access memory:
+///
+/// ```rust,no_run
+/// use std::mem::{self, MaybeUninit};
+///
+/// let x: &i32 = unsafe { mem::zeroed() }; // undefined behavior!
+/// // The equivalent code with `MaybeUninit<&i32>`:
+/// let x: &i32 = unsafe { MaybeUninit::zeroed().assume_init() }; // undefined behavior!
+/// ```
+///
+/// This is exploited by the compiler for various optimizations, such as eliding
+/// run-time checks and optimizing `enum` layout.
+///
+/// Similarly, entirely uninitialized memory may have any content, while a `bool` must
+/// always be `true` or `false`. Hence, creating an uninitialized `bool` is undefined behavior:
+///
+/// ```rust,no_run
+/// use std::mem::{self, MaybeUninit};
+///
+/// let b: bool = unsafe { mem::uninitialized() }; // undefined behavior!
+/// // The equivalent code with `MaybeUninit<bool>`:
+/// let b: bool = unsafe { MaybeUninit::uninit().assume_init() }; // undefined behavior!
+/// ```
+///
+/// Moreover, uninitialized memory is special in that the compiler knows that
+/// it does not have a fixed value. This makes it undefined behavior to have
+/// uninitialized data in a variable even if that variable has an integer type,
+/// which otherwise can hold any *fixed* bit pattern:
+///
+/// ```rust,no_run
+/// use std::mem::{self, MaybeUninit};
+///
+/// let x: i32 = unsafe { mem::uninitialized() }; // undefined behavior!
+/// // The equivalent code with `MaybeUninit<i32>`:
+/// let x: i32 = unsafe { MaybeUninit::uninit().assume_init() }; // undefined behavior!
+/// ```
+/// (Notice that the rules around uninitialized integers are not finalized yet, but
+/// until they are, it is advisable to avoid them.)
+///
+/// On top of that, remember that most types have additional invariants beyond merely
+/// being considered initialized at the type level. For example, a `1`-initialized [`Vec<T>`]
+/// is considered initialized because the only requirement the compiler knows about it
+/// is that the data pointer must be non-null. Creating such a `Vec<T>` does not cause
+/// *immediate* undefined behavior, but will cause undefined behavior with most
+/// safe operations (including dropping it).
+///
+/// [`Vec<T>`]: ../../std/vec/struct.Vec.html
+///
+/// # Examples
+///
+/// `MaybeUninit<T>` serves to enable unsafe code to deal with uninitialized data.
+/// It is a signal to the compiler indicating that the data here might *not*
+/// be initialized:
+///
+/// ```rust
+/// use std::mem::MaybeUninit;
+///
+/// // Create an explicitly uninitialized reference. The compiler knows that data inside
+/// // a `MaybeUninit<T>` may be invalid, and hence this is not UB:
+/// let mut x = MaybeUninit::<&i32>::uninit();
+/// // Set it to a valid value.
+/// unsafe { x.as_mut_ptr().write(&0); }
+/// // Extract the initialized data -- this is only allowed *after* properly
+/// // initializing `x`!
+/// let x = unsafe { x.assume_init() };
+/// ```
+///
+/// The compiler then knows to not make any incorrect assumptions or optimizations on this code.
+///
+/// You can think of `MaybeUninit<T>` as being a bit like `Option<T>` but without
+/// any of the run-time tracking and without any of the safety checks.
+///
+/// ## out-pointers
+///
+/// You can use `MaybeUninit<T>` to implement "out-pointers": instead of returning data
+/// from a function, pass it a pointer to some (uninitialized) memory to put the
+/// result into. This can be useful when it is important for the caller to control
+/// how the memory the result is stored in gets allocated, and you want to avoid
+/// unnecessary moves.
+///
+/// ```
+/// use std::mem::MaybeUninit;
+///
+/// unsafe fn make_vec(out: *mut Vec<i32>) {
+///     // `write` does not drop the old contents, which is important.
+///     out.write(vec![1, 2, 3]);
+/// }
+///
+/// let mut v = MaybeUninit::uninit();
+/// unsafe { make_vec(v.as_mut_ptr()); }
+/// // Now we know `v` is initialized! This also makes sure the vector gets
+/// // properly dropped.
+/// let v = unsafe { v.assume_init() };
+/// assert_eq!(&v, &[1, 2, 3]);
+/// ```
+///
+/// ## Initializing an array element-by-element
+///
+/// `MaybeUninit<T>` can be used to initialize a large array element-by-element:
+///
+/// ```
+/// use std::mem::{self, MaybeUninit};
+/// use std::ptr;
+///
+/// let data = {
+///     // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
+///     // safe because the type we are claiming to have initialized here is a
+///     // bunch of `MaybeUninit`s, which do not require initialization.
+///     let mut data: [MaybeUninit<Vec<u32>>; 1000] = unsafe {
+///         MaybeUninit::uninit().assume_init()
+///     };
+///
+///     // Dropping a `MaybeUninit` does nothing, so if there is a panic during this loop,
+///     // we have a memory leak, but there is no memory safety issue.
+///     for elem in &mut data[..] {
+///         unsafe { ptr::write(elem.as_mut_ptr(), vec![42]); }
+///     }
+///
+///     // Everything is initialized. Transmute the array to the
+///     // initialized type.
+///     unsafe { mem::transmute::<_, [Vec<u32>; 1000]>(data) }
+/// };
+///
+/// assert_eq!(&data[0], &[42]);
+/// ```
+///
+/// You can also work with partially initialized arrays, which could
+/// be found in low-level datastructures.
+///
+/// ```
+/// use std::mem::MaybeUninit;
+/// use std::ptr;
+///
+/// // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
+/// // safe because the type we are claiming to have initialized here is a
+/// // bunch of `MaybeUninit`s, which do not require initialization.
+/// let mut data: [MaybeUninit<String>; 1000] = unsafe { MaybeUninit::uninit().assume_init() };
+/// // Count the number of elements we have assigned.
+/// let mut data_len: usize = 0;
+///
+/// for elem in &mut data[0..500] {
+///     unsafe { ptr::write(elem.as_mut_ptr(), String::from("hello")); }
+///     data_len += 1;
+/// }
+///
+/// // For each item in the array, drop if we allocated it.
+/// for elem in &mut data[0..data_len] {
+///     unsafe { ptr::drop_in_place(elem.as_mut_ptr()); }
+/// }
+/// ```
+///
+/// ## Initializing a struct field-by-field
+///
+/// There is currently no supported way to create a raw pointer or reference
+/// to a field of a struct inside `MaybeUninit<Struct>`. That means it is not possible
+/// to create a struct by calling `MaybeUninit::uninit::<Struct>()` and then writing
+/// to its fields.
+///
+/// [ub]: ../../reference/behavior-considered-undefined.html
+///
+/// # Layout
+///
+/// `MaybeUninit<T>` is guaranteed to have the same size and alignment as `T`:
+///
+/// ```rust
+/// use std::mem::{MaybeUninit, size_of, align_of};
+/// assert_eq!(size_of::<MaybeUninit<u64>>(), size_of::<u64>());
+/// assert_eq!(align_of::<MaybeUninit<u64>>(), align_of::<u64>());
+/// ```
+///
+/// However remember that a type *containing* a `MaybeUninit<T>` is not necessarily the same
+/// layout; Rust does not in general guarantee that the fields of a `Foo<T>` have the same order as
+/// a `Foo<U>` even if `T` and `U` have the same size and alignment. Furthermore because any bit
+/// value is valid for a `MaybeUninit<T>` the compiler can't apply non-zero/niche-filling
+/// optimizations, potentially resulting in a larger size:
+///
+/// ```rust
+/// # use std::mem::{MaybeUninit, size_of};
+/// assert_eq!(size_of::<Option<bool>>(), 1);
+/// assert_eq!(size_of::<Option<MaybeUninit<bool>>>(), 2);
+/// ```
+#[allow(missing_debug_implementations)]
+#[stable(feature = "maybe_uninit", since = "1.36.0")]
+#[derive(Copy)]
+pub union MaybeUninit<T> {
+    uninit: (),
+    value: ManuallyDrop<T>,
+}
+
+#[stable(feature = "maybe_uninit", since = "1.36.0")]
+impl<T: Copy> Clone for MaybeUninit<T> {
+    #[inline(always)]
+    fn clone(&self) -> Self {
+        // Not calling `T::clone()`, we cannot know if we are initialized enough for that.
+        *self
+    }
+}
+
+impl<T> MaybeUninit<T> {
+    /// Creates a new `MaybeUninit<T>` initialized with the given value.
+    /// It is safe to call [`assume_init`] on the return value of this function.
+    ///
+    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
+    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
+    ///
+    /// [`assume_init`]: #method.assume_init
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline(always)]
+    pub const fn new(val: T) -> MaybeUninit<T> {
+        MaybeUninit { value: ManuallyDrop::new(val) }
+    }
+
+    /// Creates a new `MaybeUninit<T>` in an uninitialized state.
+    ///
+    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
+    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
+    ///
+    /// See the [type-level documentation][type] for some examples.
+    ///
+    /// [type]: union.MaybeUninit.html
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline(always)]
+    pub const fn uninit() -> MaybeUninit<T> {
+        MaybeUninit { uninit: () }
+    }
+
+    /// Creates a new `MaybeUninit<T>` in an uninitialized state, with the memory being
+    /// filled with `0` bytes. It depends on `T` whether that already makes for
+    /// proper initialization. For example, `MaybeUninit<usize>::zeroed()` is initialized,
+    /// but `MaybeUninit<&'static i32>::zeroed()` is not because references must not
+    /// be null.
+    ///
+    /// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
+    /// It is your responsibility to make sure `T` gets dropped if it got initialized.
+    ///
+    /// # Example
+    ///
+    /// Correct usage of this function: initializing a struct with zero, where all
+    /// fields of the struct can hold the bit-pattern 0 as a valid value.
+    ///
+    /// ```rust
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let x = MaybeUninit::<(u8, bool)>::zeroed();
+    /// let x = unsafe { x.assume_init() };
+    /// assert_eq!(x, (0, false));
+    /// ```
+    ///
+    /// *Incorrect* usage of this function: initializing a struct with zero, where some fields
+    /// cannot hold 0 as a valid value.
+    ///
+    /// ```rust,no_run
+    /// use std::mem::MaybeUninit;
+    ///
+    /// enum NotZero { One = 1, Two = 2 };
+    ///
+    /// let x = MaybeUninit::<(u8, NotZero)>::zeroed();
+    /// let x = unsafe { x.assume_init() };
+    /// // Inside a pair, we create a `NotZero` that does not have a valid discriminant.
+    /// // This is undefined behavior.
+    /// ```
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline]
+    pub fn zeroed() -> MaybeUninit<T> {
+        let mut u = MaybeUninit::<T>::uninit();
+        unsafe {
+            u.as_mut_ptr().write_bytes(0u8, 1);
+        }
+        u
+    }
+
+    /// Sets the value of the `MaybeUninit<T>`. This overwrites any previous value
+    /// without dropping it, so be careful not to use this twice unless you want to
+    /// skip running the destructor. For your convenience, this also returns a mutable
+    /// reference to the (now safely initialized) contents of `self`.
+    #[unstable(feature = "maybe_uninit_extra", issue = "53491")]
+    #[inline(always)]
+    pub fn write(&mut self, val: T) -> &mut T {
+        unsafe {
+            self.value = ManuallyDrop::new(val);
+            self.get_mut()
+        }
+    }
+
+    /// Gets a pointer to the contained value. Reading from this pointer or turning it
+    /// into a reference is undefined behavior unless the `MaybeUninit<T>` is initialized.
+    /// Writing to memory that this pointer (non-transitively) points to is undefined behavior
+    /// (except inside an `UnsafeCell<T>`).
+    ///
+    /// # Examples
+    ///
+    /// Correct usage of this method:
+    ///
+    /// ```rust
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
+    /// unsafe { x.as_mut_ptr().write(vec![0,1,2]); }
+    /// // Create a reference into the `MaybeUninit<T>`. This is okay because we initialized it.
+    /// let x_vec = unsafe { &*x.as_ptr() };
+    /// assert_eq!(x_vec.len(), 3);
+    /// ```
+    ///
+    /// *Incorrect* usage of this method:
+    ///
+    /// ```rust,no_run
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let x = MaybeUninit::<Vec<u32>>::uninit();
+    /// let x_vec = unsafe { &*x.as_ptr() };
+    /// // We have created a reference to an uninitialized vector! This is undefined behavior.
+    /// ```
+    ///
+    /// (Notice that the rules around references to uninitialized data are not finalized yet, but
+    /// until they are, it is advisable to avoid them.)
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline(always)]
+    pub fn as_ptr(&self) -> *const T {
+        unsafe { &*self.value as *const T }
+    }
+
+    /// Gets a mutable pointer to the contained value. Reading from this pointer or turning it
+    /// into a reference is undefined behavior unless the `MaybeUninit<T>` is initialized.
+    ///
+    /// # Examples
+    ///
+    /// Correct usage of this method:
+    ///
+    /// ```rust
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
+    /// unsafe { x.as_mut_ptr().write(vec![0,1,2]); }
+    /// // Create a reference into the `MaybeUninit<Vec<u32>>`.
+    /// // This is okay because we initialized it.
+    /// let x_vec = unsafe { &mut *x.as_mut_ptr() };
+    /// x_vec.push(3);
+    /// assert_eq!(x_vec.len(), 4);
+    /// ```
+    ///
+    /// *Incorrect* usage of this method:
+    ///
+    /// ```rust,no_run
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<Vec<u32>>::uninit();
+    /// let x_vec = unsafe { &mut *x.as_mut_ptr() };
+    /// // We have created a reference to an uninitialized vector! This is undefined behavior.
+    /// ```
+    ///
+    /// (Notice that the rules around references to uninitialized data are not finalized yet, but
+    /// until they are, it is advisable to avoid them.)
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline(always)]
+    pub fn as_mut_ptr(&mut self) -> *mut T {
+        unsafe { &mut *self.value as *mut T }
+    }
+
+    /// Extracts the value from the `MaybeUninit<T>` container. This is a great way
+    /// to ensure that the data will get dropped, because the resulting `T` is
+    /// subject to the usual drop handling.
+    ///
+    /// # Safety
+    ///
+    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
+    /// state. Calling this when the content is not yet fully initialized causes immediate undefined
+    /// behavior. The [type-level documentation][inv] contains more information about
+    /// this initialization invariant.
+    ///
+    /// [inv]: #initialization-invariant
+    ///
+    /// # Examples
+    ///
+    /// Correct usage of this method:
+    ///
+    /// ```rust
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<bool>::uninit();
+    /// unsafe { x.as_mut_ptr().write(true); }
+    /// let x_init = unsafe { x.assume_init() };
+    /// assert_eq!(x_init, true);
+    /// ```
+    ///
+    /// *Incorrect* usage of this method:
+    ///
+    /// ```rust,no_run
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let x = MaybeUninit::<Vec<u32>>::uninit();
+    /// let x_init = unsafe { x.assume_init() };
+    /// // `x` had not been initialized yet, so this last line caused undefined behavior.
+    /// ```
+    #[stable(feature = "maybe_uninit", since = "1.36.0")]
+    #[inline(always)]
+    pub unsafe fn assume_init(self) -> T {
+        intrinsics::panic_if_uninhabited::<T>();
+        ManuallyDrop::into_inner(self.value)
+    }
+
+    /// Reads the value from the `MaybeUninit<T>` container. The resulting `T` is subject
+    /// to the usual drop handling.
+    ///
+    /// Whenever possible, it is preferrable to use [`assume_init`] instead, which
+    /// prevents duplicating the content of the `MaybeUninit<T>`.
+    ///
+    /// # Safety
+    ///
+    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
+    /// state. Calling this when the content is not yet fully initialized causes undefined
+    /// behavior. The [type-level documentation][inv] contains more information about
+    /// this initialization invariant.
+    ///
+    /// Moreover, this leaves a copy of the same data behind in the `MaybeUninit<T>`. When using
+    /// multiple copies of the data (by calling `read` multiple times, or first
+    /// calling `read` and then [`assume_init`]), it is your responsibility
+    /// to ensure that that data may indeed be duplicated.
+    ///
+    /// [inv]: #initialization-invariant
+    /// [`assume_init`]: #method.assume_init
+    ///
+    /// # Examples
+    ///
+    /// Correct usage of this method:
+    ///
+    /// ```rust
+    /// #![feature(maybe_uninit_extra)]
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<u32>::uninit();
+    /// x.write(13);
+    /// let x1 = unsafe { x.read() };
+    /// // `u32` is `Copy`, so we may read multiple times.
+    /// let x2 = unsafe { x.read() };
+    /// assert_eq!(x1, x2);
+    ///
+    /// let mut x = MaybeUninit::<Option<Vec<u32>>>::uninit();
+    /// x.write(None);
+    /// let x1 = unsafe { x.read() };
+    /// // Duplicating a `None` value is okay, so we may read multiple times.
+    /// let x2 = unsafe { x.read() };
+    /// assert_eq!(x1, x2);
+    /// ```
+    ///
+    /// *Incorrect* usage of this method:
+    ///
+    /// ```rust,no_run
+    /// #![feature(maybe_uninit_extra)]
+    /// use std::mem::MaybeUninit;
+    ///
+    /// let mut x = MaybeUninit::<Option<Vec<u32>>>::uninit();
+    /// x.write(Some(vec![0,1,2]));
+    /// let x1 = unsafe { x.read() };
+    /// let x2 = unsafe { x.read() };
+    /// // We now created two copies of the same vector, leading to a double-free when
+    /// // they both get dropped!
+    /// ```
+    #[unstable(feature = "maybe_uninit_extra", issue = "53491")]
+    #[inline(always)]
+    pub unsafe fn read(&self) -> T {
+        intrinsics::panic_if_uninhabited::<T>();
+        self.as_ptr().read()
+    }
+
+    /// Gets a reference to the contained value.
+    ///
+    /// # Safety
+    ///
+    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
+    /// state. Calling this when the content is not yet fully initialized causes undefined
+    /// behavior.
+    #[unstable(feature = "maybe_uninit_ref", issue = "53491")]
+    #[inline(always)]
+    pub unsafe fn get_ref(&self) -> &T {
+        &*self.value
+    }
+
+    /// Gets a mutable reference to the contained value.
+    ///
+    /// # Safety
+    ///
+    /// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
+    /// state. Calling this when the content is not yet fully initialized causes undefined
+    /// behavior.
+    // FIXME(#53491): We currently rely on the above being incorrect, i.e., we have references
+    // to uninitialized data (e.g., in `libcore/fmt/float.rs`).  We should make
+    // a final decision about the rules before stabilization.
+    #[unstable(feature = "maybe_uninit_ref", issue = "53491")]
+    #[inline(always)]
+    pub unsafe fn get_mut(&mut self) -> &mut T {
+        &mut *self.value
+    }
+
+    /// Gets a pointer to the first element of the array.
+    #[unstable(feature = "maybe_uninit_slice", issue = "53491")]
+    #[inline(always)]
+    pub fn first_ptr(this: &[MaybeUninit<T>]) -> *const T {
+        this as *const [MaybeUninit<T>] as *const T
+    }
+
+    /// Gets a mutable pointer to the first element of the array.
+    #[unstable(feature = "maybe_uninit_slice", issue = "53491")]
+    #[inline(always)]
+    pub fn first_ptr_mut(this: &mut [MaybeUninit<T>]) -> *mut T {
+        this as *mut [MaybeUninit<T>] as *mut T
+    }
+}
diff --git a/src/libcore/mem/mod.rs b/src/libcore/mem/mod.rs
new file mode 100644 (file)
index 0000000..91449f0
--- /dev/null
@@ -0,0 +1,752 @@
+//! Basic functions for dealing with memory.
+//!
+//! This module contains functions for querying the size and alignment of
+//! types, initializing and manipulating memory.
+
+#![stable(feature = "rust1", since = "1.0.0")]
+
+use crate::clone;
+use crate::cmp;
+use crate::fmt;
+use crate::hash;
+use crate::intrinsics;
+use crate::marker::{Copy, PhantomData, Sized};
+use crate::ptr;
+
+mod manually_drop;
+#[stable(feature = "manually_drop", since = "1.20.0")]
+pub use manually_drop::ManuallyDrop;
+
+mod maybe_uninit;
+#[stable(feature = "maybe_uninit", since = "1.36.0")]
+pub use maybe_uninit::MaybeUninit;
+
+#[stable(feature = "rust1", since = "1.0.0")]
+#[doc(inline)]
+pub use crate::intrinsics::transmute;
+
+/// Takes ownership and "forgets" about the value **without running its destructor**.
+///
+/// Any resources the value manages, such as heap memory or a file handle, will linger
+/// forever in an unreachable state. However, it does not guarantee that pointers
+/// to this memory will remain valid.
+///
+/// * If you want to leak memory, see [`Box::leak`][leak].
+/// * If you want to obtain a raw pointer to the memory, see [`Box::into_raw`][into_raw].
+/// * If you want to dispose of a value properly, running its destructor, see
+/// [`mem::drop`][drop].
+///
+/// # Safety
+///
+/// `forget` is not marked as `unsafe`, because Rust's safety guarantees
+/// do not include a guarantee that destructors will always run. For example,
+/// a program can create a reference cycle using [`Rc`][rc], or call
+/// [`process::exit`][exit] to exit without running destructors. Thus, allowing
+/// `mem::forget` from safe code does not fundamentally change Rust's safety
+/// guarantees.
+///
+/// That said, leaking resources such as memory or I/O objects is usually undesirable,
+/// so `forget` is only recommended for specialized use cases like those shown below.
+///
+/// Because forgetting a value is allowed, any `unsafe` code you write must
+/// allow for this possibility. You cannot return a value and expect that the
+/// caller will necessarily run the value's destructor.
+///
+/// [rc]: ../../std/rc/struct.Rc.html
+/// [exit]: ../../std/process/fn.exit.html
+///
+/// # Examples
+///
+/// Leak an I/O object, never closing the file:
+///
+/// ```no_run
+/// use std::mem;
+/// use std::fs::File;
+///
+/// let file = File::open("foo.txt").unwrap();
+/// mem::forget(file);
+/// ```
+///
+/// The practical use cases for `forget` are rather specialized and mainly come
+/// up in unsafe or FFI code.
+///
+/// [drop]: fn.drop.html
+/// [uninit]: fn.uninitialized.html
+/// [clone]: ../clone/trait.Clone.html
+/// [swap]: fn.swap.html
+/// [box]: ../../std/boxed/struct.Box.html
+/// [leak]: ../../std/boxed/struct.Box.html#method.leak
+/// [into_raw]: ../../std/boxed/struct.Box.html#method.into_raw
+/// [ub]: ../../reference/behavior-considered-undefined.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn forget<T>(t: T) {
+    ManuallyDrop::new(t);
+}
+
+/// Like [`forget`], but also accepts unsized values.
+///
+/// This function is just a shim intended to be removed when the `unsized_locals` feature gets
+/// stabilized.
+///
+/// [`forget`]: fn.forget.html
+#[inline]
+#[unstable(feature = "forget_unsized", issue = "0")]
+pub fn forget_unsized<T: ?Sized>(t: T) {
+    unsafe { intrinsics::forget(t) }
+}
+
+/// Returns the size of a type in bytes.
+///
+/// More specifically, this is the offset in bytes between successive elements
+/// in an array with that item type including alignment padding. Thus, for any
+/// type `T` and length `n`, `[T; n]` has a size of `n * size_of::<T>()`.
+///
+/// In general, the size of a type is not stable across compilations, but
+/// specific types such as primitives are.
+///
+/// The following table gives the size for primitives.
+///
+/// Type | size_of::\<Type>()
+/// ---- | ---------------
+/// () | 0
+/// bool | 1
+/// u8 | 1
+/// u16 | 2
+/// u32 | 4
+/// u64 | 8
+/// u128 | 16
+/// i8 | 1
+/// i16 | 2
+/// i32 | 4
+/// i64 | 8
+/// i128 | 16
+/// f32 | 4
+/// f64 | 8
+/// char | 4
+///
+/// Furthermore, `usize` and `isize` have the same size.
+///
+/// The types `*const T`, `&T`, `Box<T>`, `Option<&T>`, and `Option<Box<T>>` all have
+/// the same size. If `T` is Sized, all of those types have the same size as `usize`.
+///
+/// The mutability of a pointer does not change its size. As such, `&T` and `&mut T`
+/// have the same size. Likewise for `*const T` and `*mut T`.
+///
+/// # Size of `#[repr(C)]` items
+///
+/// The `C` representation for items has a defined layout. With this layout,
+/// the size of items is also stable as long as all fields have a stable size.
+///
+/// ## Size of Structs
+///
+/// For `structs`, the size is determined by the following algorithm.
+///
+/// For each field in the struct ordered by declaration order:
+///
+/// 1. Add the size of the field.
+/// 2. Round up the current size to the nearest multiple of the next field's [alignment].
+///
+/// Finally, round the size of the struct to the nearest multiple of its [alignment].
+/// The alignment of the struct is usually the largest alignment of all its
+/// fields; this can be changed with the use of `repr(align(N))`.
+///
+/// Unlike `C`, zero sized structs are not rounded up to one byte in size.
+///
+/// ## Size of Enums
+///
+/// Enums that carry no data other than the discriminant have the same size as C enums
+/// on the platform they are compiled for.
+///
+/// ## Size of Unions
+///
+/// The size of a union is the size of its largest field.
+///
+/// Unlike `C`, zero sized unions are not rounded up to one byte in size.
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// // Some primitives
+/// assert_eq!(4, mem::size_of::<i32>());
+/// assert_eq!(8, mem::size_of::<f64>());
+/// assert_eq!(0, mem::size_of::<()>());
+///
+/// // Some arrays
+/// assert_eq!(8, mem::size_of::<[i32; 2]>());
+/// assert_eq!(12, mem::size_of::<[i32; 3]>());
+/// assert_eq!(0, mem::size_of::<[i32; 0]>());
+///
+///
+/// // Pointer size equality
+/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<*const i32>());
+/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<Box<i32>>());
+/// assert_eq!(mem::size_of::<&i32>(), mem::size_of::<Option<&i32>>());
+/// assert_eq!(mem::size_of::<Box<i32>>(), mem::size_of::<Option<Box<i32>>>());
+/// ```
+///
+/// Using `#[repr(C)]`.
+///
+/// ```
+/// use std::mem;
+///
+/// #[repr(C)]
+/// struct FieldStruct {
+///     first: u8,
+///     second: u16,
+///     third: u8
+/// }
+///
+/// // The size of the first field is 1, so add 1 to the size. Size is 1.
+/// // The alignment of the second field is 2, so add 1 to the size for padding. Size is 2.
+/// // The size of the second field is 2, so add 2 to the size. Size is 4.
+/// // The alignment of the third field is 1, so add 0 to the size for padding. Size is 4.
+/// // The size of the third field is 1, so add 1 to the size. Size is 5.
+/// // Finally, the alignment of the struct is 2 (because the largest alignment amongst its
+/// // fields is 2), so add 1 to the size for padding. Size is 6.
+/// assert_eq!(6, mem::size_of::<FieldStruct>());
+///
+/// #[repr(C)]
+/// struct TupleStruct(u8, u16, u8);
+///
+/// // Tuple structs follow the same rules.
+/// assert_eq!(6, mem::size_of::<TupleStruct>());
+///
+/// // Note that reordering the fields can lower the size. We can remove both padding bytes
+/// // by putting `third` before `second`.
+/// #[repr(C)]
+/// struct FieldStructOptimized {
+///     first: u8,
+///     third: u8,
+///     second: u16
+/// }
+///
+/// assert_eq!(4, mem::size_of::<FieldStructOptimized>());
+///
+/// // Union size is the size of the largest field.
+/// #[repr(C)]
+/// union ExampleUnion {
+///     smaller: u8,
+///     larger: u16
+/// }
+///
+/// assert_eq!(2, mem::size_of::<ExampleUnion>());
+/// ```
+///
+/// [alignment]: ./fn.align_of.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_promotable]
+pub const fn size_of<T>() -> usize {
+    intrinsics::size_of::<T>()
+}
+
+/// Returns the size of the pointed-to value in bytes.
+///
+/// This is usually the same as `size_of::<T>()`. However, when `T` *has* no
+/// statically-known size, e.g., a slice [`[T]`][slice] or a [trait object],
+/// then `size_of_val` can be used to get the dynamically-known size.
+///
+/// [slice]: ../../std/primitive.slice.html
+/// [trait object]: ../../book/ch17-02-trait-objects.html
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// assert_eq!(4, mem::size_of_val(&5i32));
+///
+/// let x: [u8; 13] = [0; 13];
+/// let y: &[u8] = &x;
+/// assert_eq!(13, mem::size_of_val(y));
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn size_of_val<T: ?Sized>(val: &T) -> usize {
+    unsafe { intrinsics::size_of_val(val) }
+}
+
+/// Returns the [ABI]-required minimum alignment of a type.
+///
+/// Every reference to a value of the type `T` must be a multiple of this number.
+///
+/// This is the alignment used for struct fields. It may be smaller than the preferred alignment.
+///
+/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
+///
+/// # Examples
+///
+/// ```
+/// # #![allow(deprecated)]
+/// use std::mem;
+///
+/// assert_eq!(4, mem::min_align_of::<i32>());
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_deprecated(reason = "use `align_of` instead", since = "1.2.0")]
+pub fn min_align_of<T>() -> usize {
+    intrinsics::min_align_of::<T>()
+}
+
+/// Returns the [ABI]-required minimum alignment of the type of the value that `val` points to.
+///
+/// Every reference to a value of the type `T` must be a multiple of this number.
+///
+/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
+///
+/// # Examples
+///
+/// ```
+/// # #![allow(deprecated)]
+/// use std::mem;
+///
+/// assert_eq!(4, mem::min_align_of_val(&5i32));
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_deprecated(reason = "use `align_of_val` instead", since = "1.2.0")]
+pub fn min_align_of_val<T: ?Sized>(val: &T) -> usize {
+    unsafe { intrinsics::min_align_of_val(val) }
+}
+
+/// Returns the [ABI]-required minimum alignment of a type.
+///
+/// Every reference to a value of the type `T` must be a multiple of this number.
+///
+/// This is the alignment used for struct fields. It may be smaller than the preferred alignment.
+///
+/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// assert_eq!(4, mem::align_of::<i32>());
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_promotable]
+pub const fn align_of<T>() -> usize {
+    intrinsics::min_align_of::<T>()
+}
+
+/// Returns the [ABI]-required minimum alignment of the type of the value that `val` points to.
+///
+/// Every reference to a value of the type `T` must be a multiple of this number.
+///
+/// [ABI]: https://en.wikipedia.org/wiki/Application_binary_interface
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// assert_eq!(4, mem::align_of_val(&5i32));
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn align_of_val<T: ?Sized>(val: &T) -> usize {
+    unsafe { intrinsics::min_align_of_val(val) }
+}
+
+/// Returns `true` if dropping values of type `T` matters.
+///
+/// This is purely an optimization hint, and may be implemented conservatively:
+/// it may return `true` for types that don't actually need to be dropped.
+/// As such always returning `true` would be a valid implementation of
+/// this function. However if this function actually returns `false`, then you
+/// can be certain dropping `T` has no side effect.
+///
+/// Low level implementations of things like collections, which need to manually
+/// drop their data, should use this function to avoid unnecessarily
+/// trying to drop all their contents when they are destroyed. This might not
+/// make a difference in release builds (where a loop that has no side-effects
+/// is easily detected and eliminated), but is often a big win for debug builds.
+///
+/// Note that `ptr::drop_in_place` already performs this check, so if your workload
+/// can be reduced to some small number of drop_in_place calls, using this is
+/// unnecessary. In particular note that you can drop_in_place a slice, and that
+/// will do a single needs_drop check for all the values.
+///
+/// Types like Vec therefore just `drop_in_place(&mut self[..])` without using
+/// needs_drop explicitly. Types like HashMap, on the other hand, have to drop
+/// values one at a time and should use this API.
+///
+///
+/// # Examples
+///
+/// Here's an example of how a collection might make use of needs_drop:
+///
+/// ```
+/// use std::{mem, ptr};
+///
+/// pub struct MyCollection<T> {
+/// #   data: [T; 1],
+///     /* ... */
+/// }
+/// # impl<T> MyCollection<T> {
+/// #   fn iter_mut(&mut self) -> &mut [T] { &mut self.data }
+/// #   fn free_buffer(&mut self) {}
+/// # }
+///
+/// impl<T> Drop for MyCollection<T> {
+///     fn drop(&mut self) {
+///         unsafe {
+///             // drop the data
+///             if mem::needs_drop::<T>() {
+///                 for x in self.iter_mut() {
+///                     ptr::drop_in_place(x);
+///                 }
+///             }
+///             self.free_buffer();
+///         }
+///     }
+/// }
+/// ```
+#[inline]
+#[stable(feature = "needs_drop", since = "1.21.0")]
+pub const fn needs_drop<T>() -> bool {
+    intrinsics::needs_drop::<T>()
+}
+
+/// Creates a value whose bytes are all zero.
+///
+/// This has the same effect as [`MaybeUninit::zeroed().assume_init()`][zeroed].
+/// It is useful for FFI sometimes, but should generally be avoided.
+///
+/// There is no guarantee that an all-zero byte-pattern represents a valid value of
+/// some type `T`. For example, the all-zero byte-pattern is not a valid value
+/// for reference types (`&T` and `&mut T`). Using `zeroed` on such types
+/// causes immediate [undefined behavior][ub] because [the Rust compiler assumes][inv]
+/// that there always is a valid value in a variable it considers initialized.
+///
+/// [zeroed]: union.MaybeUninit.html#method.zeroed
+/// [ub]: ../../reference/behavior-considered-undefined.html
+/// [inv]: union.MaybeUninit.html#initialization-invariant
+///
+/// # Examples
+///
+/// Correct usage of this function: initializing an integer with zero.
+///
+/// ```
+/// use std::mem;
+///
+/// let x: i32 = unsafe { mem::zeroed() };
+/// assert_eq!(0, x);
+/// ```
+///
+/// *Incorrect* usage of this function: initializing a reference with zero.
+///
+/// ```no_run
+/// use std::mem;
+///
+/// let _x: &i32 = unsafe { mem::zeroed() }; // Undefined behavior!
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn zeroed<T>() -> T {
+    intrinsics::panic_if_uninhabited::<T>();
+    intrinsics::init()
+}
+
+/// Bypasses Rust's normal memory-initialization checks by pretending to
+/// produce a value of type `T`, while doing nothing at all.
+///
+/// **This functon is deprecated.** Use [`MaybeUninit<T>`] instead.
+///
+/// The reason for deprecation is that the function basically cannot be used
+/// correctly: [the Rust compiler assumes][inv] that values are properly initialized.
+/// As a consequence, calling e.g. `mem::uninitialized::<bool>()` causes immediate
+/// undefined behavior for returning a `bool` that is not definitely either `true`
+/// or `false`. Worse, truly uninitialized memory like what gets returned here
+/// is special in that the compiler knows that it does not have a fixed value.
+/// This makes it undefined behavior to have uninitialized data in a variable even
+/// if that variable has an integer type.
+/// (Notice that the rules around uninitialized integers are not finalized yet, but
+/// until they are, it is advisable to avoid them.)
+///
+/// [`MaybeUninit<T>`]: union.MaybeUninit.html
+/// [inv]: union.MaybeUninit.html#initialization-invariant
+#[inline]
+#[rustc_deprecated(since = "1.38.0", reason = "use `mem::MaybeUninit` instead")]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn uninitialized<T>() -> T {
+    intrinsics::panic_if_uninhabited::<T>();
+    intrinsics::uninit()
+}
+
+/// Swaps the values at two mutable locations, without deinitializing either one.
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// let mut x = 5;
+/// let mut y = 42;
+///
+/// mem::swap(&mut x, &mut y);
+///
+/// assert_eq!(42, x);
+/// assert_eq!(5, y);
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn swap<T>(x: &mut T, y: &mut T) {
+    unsafe {
+        ptr::swap_nonoverlapping_one(x, y);
+    }
+}
+
+/// Moves `src` into the referenced `dest`, returning the previous `dest` value.
+///
+/// Neither value is dropped.
+///
+/// # Examples
+///
+/// A simple example:
+///
+/// ```
+/// use std::mem;
+///
+/// let mut v: Vec<i32> = vec![1, 2];
+///
+/// let old_v = mem::replace(&mut v, vec![3, 4, 5]);
+/// assert_eq!(vec![1, 2], old_v);
+/// assert_eq!(vec![3, 4, 5], v);
+/// ```
+///
+/// `replace` allows consumption of a struct field by replacing it with another value.
+/// Without `replace` you can run into issues like these:
+///
+/// ```compile_fail,E0507
+/// struct Buffer<T> { buf: Vec<T> }
+///
+/// impl<T> Buffer<T> {
+///     fn get_and_reset(&mut self) -> Vec<T> {
+///         // error: cannot move out of dereference of `&mut`-pointer
+///         let buf = self.buf;
+///         self.buf = Vec::new();
+///         buf
+///     }
+/// }
+/// ```
+///
+/// Note that `T` does not necessarily implement [`Clone`], so it can't even clone and reset
+/// `self.buf`. But `replace` can be used to disassociate the original value of `self.buf` from
+/// `self`, allowing it to be returned:
+///
+/// ```
+/// # #![allow(dead_code)]
+/// use std::mem;
+///
+/// # struct Buffer<T> { buf: Vec<T> }
+/// impl<T> Buffer<T> {
+///     fn get_and_reset(&mut self) -> Vec<T> {
+///         mem::replace(&mut self.buf, Vec::new())
+///     }
+/// }
+/// ```
+///
+/// [`Clone`]: ../../std/clone/trait.Clone.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn replace<T>(dest: &mut T, mut src: T) -> T {
+    swap(dest, &mut src);
+    src
+}
+
+/// Disposes of a value.
+///
+/// This does call the argument's implementation of [`Drop`][drop].
+///
+/// This effectively does nothing for types which implement `Copy`, e.g.
+/// integers. Such values are copied and _then_ moved into the function, so the
+/// value persists after this function call.
+///
+/// This function is not magic; it is literally defined as
+///
+/// ```
+/// pub fn drop<T>(_x: T) { }
+/// ```
+///
+/// Because `_x` is moved into the function, it is automatically dropped before
+/// the function returns.
+///
+/// [drop]: ../ops/trait.Drop.html
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// let v = vec![1, 2, 3];
+///
+/// drop(v); // explicitly drop the vector
+/// ```
+///
+/// Since [`RefCell`] enforces the borrow rules at runtime, `drop` can
+/// release a [`RefCell`] borrow:
+///
+/// ```
+/// use std::cell::RefCell;
+///
+/// let x = RefCell::new(1);
+///
+/// let mut mutable_borrow = x.borrow_mut();
+/// *mutable_borrow = 1;
+///
+/// drop(mutable_borrow); // relinquish the mutable borrow on this slot
+///
+/// let borrow = x.borrow();
+/// println!("{}", *borrow);
+/// ```
+///
+/// Integers and other types implementing [`Copy`] are unaffected by `drop`.
+///
+/// ```
+/// #[derive(Copy, Clone)]
+/// struct Foo(u8);
+///
+/// let x = 1;
+/// let y = Foo(2);
+/// drop(x); // a copy of `x` is moved and dropped
+/// drop(y); // a copy of `y` is moved and dropped
+///
+/// println!("x: {}, y: {}", x, y.0); // still available
+/// ```
+///
+/// [`RefCell`]: ../../std/cell/struct.RefCell.html
+/// [`Copy`]: ../../std/marker/trait.Copy.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub fn drop<T>(_x: T) { }
+
+/// Interprets `src` as having type `&U`, and then reads `src` without moving
+/// the contained value.
+///
+/// This function will unsafely assume the pointer `src` is valid for
+/// [`size_of::<U>`][size_of] bytes by transmuting `&T` to `&U` and then reading
+/// the `&U`. It will also unsafely create a copy of the contained value instead of
+/// moving out of `src`.
+///
+/// It is not a compile-time error if `T` and `U` have different sizes, but it
+/// is highly encouraged to only invoke this function where `T` and `U` have the
+/// same size. This function triggers [undefined behavior][ub] if `U` is larger than
+/// `T`.
+///
+/// [ub]: ../../reference/behavior-considered-undefined.html
+/// [size_of]: fn.size_of.html
+///
+/// # Examples
+///
+/// ```
+/// use std::mem;
+///
+/// #[repr(packed)]
+/// struct Foo {
+///     bar: u8,
+/// }
+///
+/// let foo_slice = [10u8];
+///
+/// unsafe {
+///     // Copy the data from 'foo_slice' and treat it as a 'Foo'
+///     let mut foo_struct: Foo = mem::transmute_copy(&foo_slice);
+///     assert_eq!(foo_struct.bar, 10);
+///
+///     // Modify the copied data
+///     foo_struct.bar = 20;
+///     assert_eq!(foo_struct.bar, 20);
+/// }
+///
+/// // The contents of 'foo_slice' should not have changed
+/// assert_eq!(foo_slice, [10]);
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn transmute_copy<T, U>(src: &T) -> U {
+    ptr::read_unaligned(src as *const T as *const U)
+}
+
+/// Opaque type representing the discriminant of an enum.
+///
+/// See the [`discriminant`] function in this module for more information.
+///
+/// [`discriminant`]: fn.discriminant.html
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+pub struct Discriminant<T>(u64, PhantomData<fn() -> T>);
+
+// N.B. These trait implementations cannot be derived because we don't want any bounds on T.
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> Copy for Discriminant<T> {}
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> clone::Clone for Discriminant<T> {
+    fn clone(&self) -> Self {
+        *self
+    }
+}
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> cmp::PartialEq for Discriminant<T> {
+    fn eq(&self, rhs: &Self) -> bool {
+        self.0 == rhs.0
+    }
+}
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> cmp::Eq for Discriminant<T> {}
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> hash::Hash for Discriminant<T> {
+    fn hash<H: hash::Hasher>(&self, state: &mut H) {
+        self.0.hash(state);
+    }
+}
+
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+impl<T> fmt::Debug for Discriminant<T> {
+    fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
+        fmt.debug_tuple("Discriminant")
+           .field(&self.0)
+           .finish()
+    }
+}
+
+/// Returns a value uniquely identifying the enum variant in `v`.
+///
+/// If `T` is not an enum, calling this function will not result in undefined behavior, but the
+/// return value is unspecified.
+///
+/// # Stability
+///
+/// The discriminant of an enum variant may change if the enum definition changes. A discriminant
+/// of some variant will not change between compilations with the same compiler.
+///
+/// # Examples
+///
+/// This can be used to compare enums that carry data, while disregarding
+/// the actual data:
+///
+/// ```
+/// use std::mem;
+///
+/// enum Foo { A(&'static str), B(i32), C(i32) }
+///
+/// assert!(mem::discriminant(&Foo::A("bar")) == mem::discriminant(&Foo::A("baz")));
+/// assert!(mem::discriminant(&Foo::B(1))     == mem::discriminant(&Foo::B(2)));
+/// assert!(mem::discriminant(&Foo::B(3))     != mem::discriminant(&Foo::C(3)));
+/// ```
+#[stable(feature = "discriminant_value", since = "1.21.0")]
+pub fn discriminant<T>(v: &T) -> Discriminant<T> {
+    unsafe {
+        Discriminant(intrinsics::discriminant_value(v), PhantomData)
+    }
+}
diff --git a/src/libcore/ptr.rs b/src/libcore/ptr.rs
deleted file mode 100644 (file)
index 4bb4d3e..0000000
+++ /dev/null
@@ -1,3125 +0,0 @@
-// ignore-tidy-filelength
-
-//! Manually manage memory through raw pointers.
-//!
-//! *[See also the pointer primitive types](../../std/primitive.pointer.html).*
-//!
-//! # Safety
-//!
-//! Many functions in this module take raw pointers as arguments and read from
-//! or write to them. For this to be safe, these pointers must be *valid*.
-//! Whether a pointer is valid depends on the operation it is used for
-//! (read or write), and the extent of the memory that is accessed (i.e.,
-//! how many bytes are read/written). Most functions use `*mut T` and `*const T`
-//! to access only a single value, in which case the documentation omits the size
-//! and implicitly assumes it to be `size_of::<T>()` bytes.
-//!
-//! The precise rules for validity are not determined yet. The guarantees that are
-//! provided at this point are very minimal:
-//!
-//! * A [null] pointer is *never* valid, not even for accesses of [size zero][zst].
-//! * All pointers (except for the null pointer) are valid for all operations of
-//!   [size zero][zst].
-//! * All accesses performed by functions in this module are *non-atomic* in the sense
-//!   of [atomic operations] used to synchronize between threads. This means it is
-//!   undefined behavior to perform two concurrent accesses to the same location from different
-//!   threads unless both accesses only read from memory. Notice that this explicitly
-//!   includes [`read_volatile`] and [`write_volatile`]: Volatile accesses cannot
-//!   be used for inter-thread synchronization.
-//! * The result of casting a reference to a pointer is valid for as long as the
-//!   underlying object is live and no reference (just raw pointers) is used to
-//!   access the same memory.
-//!
-//! These axioms, along with careful use of [`offset`] for pointer arithmetic,
-//! are enough to correctly implement many useful things in unsafe code. Stronger guarantees
-//! will be provided eventually, as the [aliasing] rules are being determined. For more
-//! information, see the [book] as well as the section in the reference devoted
-//! to [undefined behavior][ub].
-//!
-//! ## Alignment
-//!
-//! Valid raw pointers as defined above are not necessarily properly aligned (where
-//! "proper" alignment is defined by the pointee type, i.e., `*const T` must be
-//! aligned to `mem::align_of::<T>()`). However, most functions require their
-//! arguments to be properly aligned, and will explicitly state
-//! this requirement in their documentation. Notable exceptions to this are
-//! [`read_unaligned`] and [`write_unaligned`].
-//!
-//! When a function requires proper alignment, it does so even if the access
-//! has size 0, i.e., even if memory is not actually touched. Consider using
-//! [`NonNull::dangling`] in such cases.
-//!
-//! [aliasing]: ../../nomicon/aliasing.html
-//! [book]: ../../book/ch19-01-unsafe-rust.html#dereferencing-a-raw-pointer
-//! [ub]: ../../reference/behavior-considered-undefined.html
-//! [null]: ./fn.null.html
-//! [zst]: ../../nomicon/exotic-sizes.html#zero-sized-types-zsts
-//! [atomic operations]: ../../std/sync/atomic/index.html
-//! [`copy`]: ../../std/ptr/fn.copy.html
-//! [`offset`]: ../../std/primitive.pointer.html#method.offset
-//! [`read_unaligned`]: ./fn.read_unaligned.html
-//! [`write_unaligned`]: ./fn.write_unaligned.html
-//! [`read_volatile`]: ./fn.read_volatile.html
-//! [`write_volatile`]: ./fn.write_volatile.html
-//! [`NonNull::dangling`]: ./struct.NonNull.html#method.dangling
-
-#![stable(feature = "rust1", since = "1.0.0")]
-
-use crate::convert::From;
-use crate::intrinsics;
-use crate::ops::{CoerceUnsized, DispatchFromDyn};
-use crate::fmt;
-use crate::hash;
-use crate::marker::{PhantomData, Unsize};
-use crate::mem::{self, MaybeUninit};
-
-use crate::cmp::Ordering::{self, Less, Equal, Greater};
-
-#[stable(feature = "rust1", since = "1.0.0")]
-pub use crate::intrinsics::copy_nonoverlapping;
-
-#[stable(feature = "rust1", since = "1.0.0")]
-pub use crate::intrinsics::copy;
-
-#[stable(feature = "rust1", since = "1.0.0")]
-pub use crate::intrinsics::write_bytes;
-
-/// Executes the destructor (if any) of the pointed-to value.
-///
-/// This is semantically equivalent to calling [`ptr::read`] and discarding
-/// the result, but has the following advantages:
-///
-/// * It is *required* to use `drop_in_place` to drop unsized types like
-///   trait objects, because they can't be read out onto the stack and
-///   dropped normally.
-///
-/// * It is friendlier to the optimizer to do this over [`ptr::read`] when
-///   dropping manually allocated memory (e.g., when writing Box/Rc/Vec),
-///   as the compiler doesn't need to prove that it's sound to elide the
-///   copy.
-///
-/// [`ptr::read`]: ../ptr/fn.read.html
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `to_drop` must be [valid] for reads.
-///
-/// * `to_drop` must be properly aligned. See the example below for how to drop
-///   an unaligned pointer.
-///
-/// Additionally, if `T` is not [`Copy`], using the pointed-to value after
-/// calling `drop_in_place` can cause undefined behavior. Note that `*to_drop =
-/// foo` counts as a use because it will cause the value to be dropped
-/// again. [`write`] can be used to overwrite data without causing it to be
-/// dropped.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-/// [`Copy`]: ../marker/trait.Copy.html
-/// [`write`]: ../ptr/fn.write.html
-///
-/// # Examples
-///
-/// Manually remove the last item from a vector:
-///
-/// ```
-/// use std::ptr;
-/// use std::rc::Rc;
-///
-/// let last = Rc::new(1);
-/// let weak = Rc::downgrade(&last);
-///
-/// let mut v = vec![Rc::new(0), last];
-///
-/// unsafe {
-///     // Get a raw pointer to the last element in `v`.
-///     let ptr = &mut v[1] as *mut _;
-///     // Shorten `v` to prevent the last item from being dropped. We do that first,
-///     // to prevent issues if the `drop_in_place` below panics.
-///     v.set_len(1);
-///     // Without a call `drop_in_place`, the last item would never be dropped,
-///     // and the memory it manages would be leaked.
-///     ptr::drop_in_place(ptr);
-/// }
-///
-/// assert_eq!(v, &[0.into()]);
-///
-/// // Ensure that the last item was dropped.
-/// assert!(weak.upgrade().is_none());
-/// ```
-///
-/// Unaligned values cannot be dropped in place, they must be copied to an aligned
-/// location first:
-/// ```
-/// use std::ptr;
-/// use std::mem::{self, MaybeUninit};
-///
-/// unsafe fn drop_after_copy<T>(to_drop: *mut T) {
-///     let mut copy: MaybeUninit<T> = MaybeUninit::uninit();
-///     ptr::copy(to_drop, copy.as_mut_ptr(), 1);
-///     drop(copy.assume_init());
-/// }
-///
-/// #[repr(packed, C)]
-/// struct Packed {
-///     _padding: u8,
-///     unaligned: Vec<i32>,
-/// }
-///
-/// let mut p = Packed { _padding: 0, unaligned: vec![42] };
-/// unsafe {
-///     drop_after_copy(&mut p.unaligned as *mut _);
-///     mem::forget(p);
-/// }
-/// ```
-///
-/// Notice that the compiler performs this copy automatically when dropping packed structs,
-/// i.e., you do not usually have to worry about such issues unless you call `drop_in_place`
-/// manually.
-#[stable(feature = "drop_in_place", since = "1.8.0")]
-#[inline(always)]
-pub unsafe fn drop_in_place<T: ?Sized>(to_drop: *mut T) {
-    real_drop_in_place(&mut *to_drop)
-}
-
-// The real `drop_in_place` -- the one that gets called implicitly when variables go
-// out of scope -- should have a safe reference and not a raw pointer as argument
-// type.  When we drop a local variable, we access it with a pointer that behaves
-// like a safe reference; transmuting that to a raw pointer does not mean we can
-// actually access it with raw pointers.
-#[lang = "drop_in_place"]
-#[allow(unconditional_recursion)]
-unsafe fn real_drop_in_place<T: ?Sized>(to_drop: &mut T) {
-    // Code here does not matter - this is replaced by the
-    // real drop glue by the compiler.
-    real_drop_in_place(to_drop)
-}
-
-/// Creates a null raw pointer.
-///
-/// # Examples
-///
-/// ```
-/// use std::ptr;
-///
-/// let p: *const i32 = ptr::null();
-/// assert!(p.is_null());
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_promotable]
-pub const fn null<T>() -> *const T { 0 as *const T }
-
-/// Creates a null mutable raw pointer.
-///
-/// # Examples
-///
-/// ```
-/// use std::ptr;
-///
-/// let p: *mut i32 = ptr::null_mut();
-/// assert!(p.is_null());
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-#[rustc_promotable]
-pub const fn null_mut<T>() -> *mut T { 0 as *mut T }
-
-/// Swaps the values at two mutable locations of the same type, without
-/// deinitializing either.
-///
-/// But for the following two exceptions, this function is semantically
-/// equivalent to [`mem::swap`]:
-///
-/// * It operates on raw pointers instead of references. When references are
-///   available, [`mem::swap`] should be preferred.
-///
-/// * The two pointed-to values may overlap. If the values do overlap, then the
-///   overlapping region of memory from `x` will be used. This is demonstrated
-///   in the second example below.
-///
-/// [`mem::swap`]: ../mem/fn.swap.html
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * Both `x` and `y` must be [valid] for reads and writes.
-///
-/// * Both `x` and `y` must be properly aligned.
-///
-/// Note that even if `T` has size `0`, the pointers must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-///
-/// # Examples
-///
-/// Swapping two non-overlapping regions:
-///
-/// ```
-/// use std::ptr;
-///
-/// let mut array = [0, 1, 2, 3];
-///
-/// let x = array[0..].as_mut_ptr() as *mut [u32; 2]; // this is `array[0..2]`
-/// let y = array[2..].as_mut_ptr() as *mut [u32; 2]; // this is `array[2..4]`
-///
-/// unsafe {
-///     ptr::swap(x, y);
-///     assert_eq!([2, 3, 0, 1], array);
-/// }
-/// ```
-///
-/// Swapping two overlapping regions:
-///
-/// ```
-/// use std::ptr;
-///
-/// let mut array = [0, 1, 2, 3];
-///
-/// let x = array[0..].as_mut_ptr() as *mut [u32; 3]; // this is `array[0..3]`
-/// let y = array[1..].as_mut_ptr() as *mut [u32; 3]; // this is `array[1..4]`
-///
-/// unsafe {
-///     ptr::swap(x, y);
-///     // The indices `1..3` of the slice overlap between `x` and `y`.
-///     // Reasonable results would be for to them be `[2, 3]`, so that indices `0..3` are
-///     // `[1, 2, 3]` (matching `y` before the `swap`); or for them to be `[0, 1]`
-///     // so that indices `1..4` are `[0, 1, 2]` (matching `x` before the `swap`).
-///     // This implementation is defined to make the latter choice.
-///     assert_eq!([1, 0, 1, 2], array);
-/// }
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn swap<T>(x: *mut T, y: *mut T) {
-    // Give ourselves some scratch space to work with.
-    // We do not have to worry about drops: `MaybeUninit` does nothing when dropped.
-    let mut tmp = MaybeUninit::<T>::uninit();
-
-    // Perform the swap
-    copy_nonoverlapping(x, tmp.as_mut_ptr(), 1);
-    copy(y, x, 1); // `x` and `y` may overlap
-    copy_nonoverlapping(tmp.as_ptr(), y, 1);
-}
-
-/// Swaps `count * size_of::<T>()` bytes between the two regions of memory
-/// beginning at `x` and `y`. The two regions must *not* overlap.
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * Both `x` and `y` must be [valid] for reads and writes of `count *
-///   size_of::<T>()` bytes.
-///
-/// * Both `x` and `y` must be properly aligned.
-///
-/// * The region of memory beginning at `x` with a size of `count *
-///   size_of::<T>()` bytes must *not* overlap with the region of memory
-///   beginning at `y` with the same size.
-///
-/// Note that even if the effectively copied size (`count * size_of::<T>()`) is `0`,
-/// the pointers must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// use std::ptr;
-///
-/// let mut x = [1, 2, 3, 4];
-/// let mut y = [7, 8, 9];
-///
-/// unsafe {
-///     ptr::swap_nonoverlapping(x.as_mut_ptr(), y.as_mut_ptr(), 2);
-/// }
-///
-/// assert_eq!(x, [7, 8, 3, 4]);
-/// assert_eq!(y, [1, 2, 9]);
-/// ```
-#[inline]
-#[stable(feature = "swap_nonoverlapping", since = "1.27.0")]
-pub unsafe fn swap_nonoverlapping<T>(x: *mut T, y: *mut T, count: usize) {
-    let x = x as *mut u8;
-    let y = y as *mut u8;
-    let len = mem::size_of::<T>() * count;
-    swap_nonoverlapping_bytes(x, y, len)
-}
-
-#[inline]
-pub(crate) unsafe fn swap_nonoverlapping_one<T>(x: *mut T, y: *mut T) {
-    // For types smaller than the block optimization below,
-    // just swap directly to avoid pessimizing codegen.
-    if mem::size_of::<T>() < 32 {
-        let z = read(x);
-        copy_nonoverlapping(y, x, 1);
-        write(y, z);
-    } else {
-        swap_nonoverlapping(x, y, 1);
-    }
-}
-
-#[inline]
-unsafe fn swap_nonoverlapping_bytes(x: *mut u8, y: *mut u8, len: usize) {
-    // The approach here is to utilize simd to swap x & y efficiently. Testing reveals
-    // that swapping either 32 bytes or 64 bytes at a time is most efficient for Intel
-    // Haswell E processors. LLVM is more able to optimize if we give a struct a
-    // #[repr(simd)], even if we don't actually use this struct directly.
-    //
-    // FIXME repr(simd) broken on emscripten and redox
-    #[cfg_attr(not(any(target_os = "emscripten", target_os = "redox")), repr(simd))]
-    struct Block(u64, u64, u64, u64);
-    struct UnalignedBlock(u64, u64, u64, u64);
-
-    let block_size = mem::size_of::<Block>();
-
-    // Loop through x & y, copying them `Block` at a time
-    // The optimizer should unroll the loop fully for most types
-    // N.B. We can't use a for loop as the `range` impl calls `mem::swap` recursively
-    let mut i = 0;
-    while i + block_size <= len {
-        // Create some uninitialized memory as scratch space
-        // Declaring `t` here avoids aligning the stack when this loop is unused
-        let mut t = mem::MaybeUninit::<Block>::uninit();
-        let t = t.as_mut_ptr() as *mut u8;
-        let x = x.add(i);
-        let y = y.add(i);
-
-        // Swap a block of bytes of x & y, using t as a temporary buffer
-        // This should be optimized into efficient SIMD operations where available
-        copy_nonoverlapping(x, t, block_size);
-        copy_nonoverlapping(y, x, block_size);
-        copy_nonoverlapping(t, y, block_size);
-        i += block_size;
-    }
-
-    if i < len {
-        // Swap any remaining bytes
-        let mut t = mem::MaybeUninit::<UnalignedBlock>::uninit();
-        let rem = len - i;
-
-        let t = t.as_mut_ptr() as *mut u8;
-        let x = x.add(i);
-        let y = y.add(i);
-
-        copy_nonoverlapping(x, t, rem);
-        copy_nonoverlapping(y, x, rem);
-        copy_nonoverlapping(t, y, rem);
-    }
-}
-
-/// Moves `src` into the pointed `dst`, returning the previous `dst` value.
-///
-/// Neither value is dropped.
-///
-/// This function is semantically equivalent to [`mem::replace`] except that it
-/// operates on raw pointers instead of references. When references are
-/// available, [`mem::replace`] should be preferred.
-///
-/// [`mem::replace`]: ../mem/fn.replace.html
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `dst` must be [valid] for writes.
-///
-/// * `dst` must be properly aligned.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-///
-/// # Examples
-///
-/// ```
-/// use std::ptr;
-///
-/// let mut rust = vec!['b', 'u', 's', 't'];
-///
-/// // `mem::replace` would have the same effect without requiring the unsafe
-/// // block.
-/// let b = unsafe {
-///     ptr::replace(&mut rust[0], 'r')
-/// };
-///
-/// assert_eq!(b, 'b');
-/// assert_eq!(rust, &['r', 'u', 's', 't']);
-/// ```
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn replace<T>(dst: *mut T, mut src: T) -> T {
-    mem::swap(&mut *dst, &mut src); // cannot overlap
-    src
-}
-
-/// Reads the value from `src` without moving it. This leaves the
-/// memory in `src` unchanged.
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `src` must be [valid] for reads.
-///
-/// * `src` must be properly aligned. Use [`read_unaligned`] if this is not the
-///   case.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// let x = 12;
-/// let y = &x as *const i32;
-///
-/// unsafe {
-///     assert_eq!(std::ptr::read(y), 12);
-/// }
-/// ```
-///
-/// Manually implement [`mem::swap`]:
-///
-/// ```
-/// use std::ptr;
-///
-/// fn swap<T>(a: &mut T, b: &mut T) {
-///     unsafe {
-///         // Create a bitwise copy of the value at `a` in `tmp`.
-///         let tmp = ptr::read(a);
-///
-///         // Exiting at this point (either by explicitly returning or by
-///         // calling a function which panics) would cause the value in `tmp` to
-///         // be dropped while the same value is still referenced by `a`. This
-///         // could trigger undefined behavior if `T` is not `Copy`.
-///
-///         // Create a bitwise copy of the value at `b` in `a`.
-///         // This is safe because mutable references cannot alias.
-///         ptr::copy_nonoverlapping(b, a, 1);
-///
-///         // As above, exiting here could trigger undefined behavior because
-///         // the same value is referenced by `a` and `b`.
-///
-///         // Move `tmp` into `b`.
-///         ptr::write(b, tmp);
-///
-///         // `tmp` has been moved (`write` takes ownership of its second argument),
-///         // so nothing is dropped implicitly here.
-///     }
-/// }
-///
-/// let mut foo = "foo".to_owned();
-/// let mut bar = "bar".to_owned();
-///
-/// swap(&mut foo, &mut bar);
-///
-/// assert_eq!(foo, "bar");
-/// assert_eq!(bar, "foo");
-/// ```
-///
-/// ## Ownership of the Returned Value
-///
-/// `read` creates a bitwise copy of `T`, regardless of whether `T` is [`Copy`].
-/// If `T` is not [`Copy`], using both the returned value and the value at
-/// `*src` can violate memory safety. Note that assigning to `*src` counts as a
-/// use because it will attempt to drop the value at `*src`.
-///
-/// [`write`] can be used to overwrite data without causing it to be dropped.
-///
-/// ```
-/// use std::ptr;
-///
-/// let mut s = String::from("foo");
-/// unsafe {
-///     // `s2` now points to the same underlying memory as `s`.
-///     let mut s2: String = ptr::read(&s);
-///
-///     assert_eq!(s2, "foo");
-///
-///     // Assigning to `s2` causes its original value to be dropped. Beyond
-///     // this point, `s` must no longer be used, as the underlying memory has
-///     // been freed.
-///     s2 = String::default();
-///     assert_eq!(s2, "");
-///
-///     // Assigning to `s` would cause the old value to be dropped again,
-///     // resulting in undefined behavior.
-///     // s = String::from("bar"); // ERROR
-///
-///     // `ptr::write` can be used to overwrite a value without dropping it.
-///     ptr::write(&mut s, String::from("bar"));
-/// }
-///
-/// assert_eq!(s, "bar");
-/// ```
-///
-/// [`mem::swap`]: ../mem/fn.swap.html
-/// [valid]: ../ptr/index.html#safety
-/// [`Copy`]: ../marker/trait.Copy.html
-/// [`read_unaligned`]: ./fn.read_unaligned.html
-/// [`write`]: ./fn.write.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn read<T>(src: *const T) -> T {
-    let mut tmp = MaybeUninit::<T>::uninit();
-    copy_nonoverlapping(src, tmp.as_mut_ptr(), 1);
-    tmp.assume_init()
-}
-
-/// Reads the value from `src` without moving it. This leaves the
-/// memory in `src` unchanged.
-///
-/// Unlike [`read`], `read_unaligned` works with unaligned pointers.
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `src` must be [valid] for reads.
-///
-/// Like [`read`], `read_unaligned` creates a bitwise copy of `T`, regardless of
-/// whether `T` is [`Copy`]. If `T` is not [`Copy`], using both the returned
-/// value and the value at `*src` can [violate memory safety][read-ownership].
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL.
-///
-/// [`Copy`]: ../marker/trait.Copy.html
-/// [`read`]: ./fn.read.html
-/// [`write_unaligned`]: ./fn.write_unaligned.html
-/// [read-ownership]: ./fn.read.html#ownership-of-the-returned-value
-/// [valid]: ../ptr/index.html#safety
-///
-/// # Examples
-///
-/// Access members of a packed struct by reference:
-///
-/// ```
-/// use std::ptr;
-///
-/// #[repr(packed, C)]
-/// struct Packed {
-///     _padding: u8,
-///     unaligned: u32,
-/// }
-///
-/// let x = Packed {
-///     _padding: 0x00,
-///     unaligned: 0x01020304,
-/// };
-///
-/// let v = unsafe {
-///     // Take the address of a 32-bit integer which is not aligned.
-///     // This must be done as a raw pointer; unaligned references are invalid.
-///     let unaligned = &x.unaligned as *const u32;
-///
-///     // Dereferencing normally will emit an aligned load instruction,
-///     // causing undefined behavior.
-///     // let v = *unaligned; // ERROR
-///
-///     // Instead, use `read_unaligned` to read improperly aligned values.
-///     let v = ptr::read_unaligned(unaligned);
-///
-///     v
-/// };
-///
-/// // Accessing unaligned values directly is safe.
-/// assert!(x.unaligned == v);
-/// ```
-#[inline]
-#[stable(feature = "ptr_unaligned", since = "1.17.0")]
-pub unsafe fn read_unaligned<T>(src: *const T) -> T {
-    let mut tmp = MaybeUninit::<T>::uninit();
-    copy_nonoverlapping(src as *const u8,
-                        tmp.as_mut_ptr() as *mut u8,
-                        mem::size_of::<T>());
-    tmp.assume_init()
-}
-
-/// Overwrites a memory location with the given value without reading or
-/// dropping the old value.
-///
-/// `write` does not drop the contents of `dst`. This is safe, but it could leak
-/// allocations or resources, so care should be taken not to overwrite an object
-/// that should be dropped.
-///
-/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
-/// location pointed to by `dst`.
-///
-/// This is appropriate for initializing uninitialized memory, or overwriting
-/// memory that has previously been [`read`] from.
-///
-/// [`read`]: ./fn.read.html
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `dst` must be [valid] for writes.
-///
-/// * `dst` must be properly aligned. Use [`write_unaligned`] if this is not the
-///   case.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-/// [`write_unaligned`]: ./fn.write_unaligned.html
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// let mut x = 0;
-/// let y = &mut x as *mut i32;
-/// let z = 12;
-///
-/// unsafe {
-///     std::ptr::write(y, z);
-///     assert_eq!(std::ptr::read(y), 12);
-/// }
-/// ```
-///
-/// Manually implement [`mem::swap`]:
-///
-/// ```
-/// use std::ptr;
-///
-/// fn swap<T>(a: &mut T, b: &mut T) {
-///     unsafe {
-///         // Create a bitwise copy of the value at `a` in `tmp`.
-///         let tmp = ptr::read(a);
-///
-///         // Exiting at this point (either by explicitly returning or by
-///         // calling a function which panics) would cause the value in `tmp` to
-///         // be dropped while the same value is still referenced by `a`. This
-///         // could trigger undefined behavior if `T` is not `Copy`.
-///
-///         // Create a bitwise copy of the value at `b` in `a`.
-///         // This is safe because mutable references cannot alias.
-///         ptr::copy_nonoverlapping(b, a, 1);
-///
-///         // As above, exiting here could trigger undefined behavior because
-///         // the same value is referenced by `a` and `b`.
-///
-///         // Move `tmp` into `b`.
-///         ptr::write(b, tmp);
-///
-///         // `tmp` has been moved (`write` takes ownership of its second argument),
-///         // so nothing is dropped implicitly here.
-///     }
-/// }
-///
-/// let mut foo = "foo".to_owned();
-/// let mut bar = "bar".to_owned();
-///
-/// swap(&mut foo, &mut bar);
-///
-/// assert_eq!(foo, "bar");
-/// assert_eq!(bar, "foo");
-/// ```
-///
-/// [`mem::swap`]: ../mem/fn.swap.html
-#[inline]
-#[stable(feature = "rust1", since = "1.0.0")]
-pub unsafe fn write<T>(dst: *mut T, src: T) {
-    intrinsics::move_val_init(&mut *dst, src)
-}
-
-/// Overwrites a memory location with the given value without reading or
-/// dropping the old value.
-///
-/// Unlike [`write`], the pointer may be unaligned.
-///
-/// `write_unaligned` does not drop the contents of `dst`. This is safe, but it
-/// could leak allocations or resources, so care should be taken not to overwrite
-/// an object that should be dropped.
-///
-/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
-/// location pointed to by `dst`.
-///
-/// This is appropriate for initializing uninitialized memory, or overwriting
-/// memory that has previously been read with [`read_unaligned`].
-///
-/// [`write`]: ./fn.write.html
-/// [`read_unaligned`]: ./fn.read_unaligned.html
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `dst` must be [valid] for writes.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL.
-///
-/// [valid]: ../ptr/index.html#safety
-///
-/// # Examples
-///
-/// Access fields in a packed struct:
-///
-/// ```
-/// use std::{mem, ptr};
-///
-/// #[repr(packed, C)]
-/// #[derive(Default)]
-/// struct Packed {
-///     _padding: u8,
-///     unaligned: u32,
-/// }
-///
-/// let v = 0x01020304;
-/// let mut x: Packed = unsafe { mem::zeroed() };
-///
-/// unsafe {
-///     // Take a reference to a 32-bit integer which is not aligned.
-///     let unaligned = &mut x.unaligned as *mut u32;
-///
-///     // Dereferencing normally will emit an aligned store instruction,
-///     // causing undefined behavior because the pointer is not aligned.
-///     // *unaligned = v; // ERROR
-///
-///     // Instead, use `write_unaligned` to write improperly aligned values.
-///     ptr::write_unaligned(unaligned, v);
-/// }
-///
-/// // Accessing unaligned values directly is safe.
-/// assert!(x.unaligned == v);
-/// ```
-#[inline]
-#[stable(feature = "ptr_unaligned", since = "1.17.0")]
-pub unsafe fn write_unaligned<T>(dst: *mut T, src: T) {
-    copy_nonoverlapping(&src as *const T as *const u8,
-                        dst as *mut u8,
-                        mem::size_of::<T>());
-    mem::forget(src);
-}
-
-/// Performs a volatile read of the value from `src` without moving it. This
-/// leaves the memory in `src` unchanged.
-///
-/// Volatile operations are intended to act on I/O memory, and are guaranteed
-/// to not be elided or reordered by the compiler across other volatile
-/// operations.
-///
-/// [`write_volatile`]: ./fn.write_volatile.html
-///
-/// # Notes
-///
-/// Rust does not currently have a rigorously and formally defined memory model,
-/// so the precise semantics of what "volatile" means here is subject to change
-/// over time. That being said, the semantics will almost always end up pretty
-/// similar to [C11's definition of volatile][c11].
-///
-/// The compiler shouldn't change the relative order or number of volatile
-/// memory operations. However, volatile memory operations on zero-sized types
-/// (e.g., if a zero-sized type is passed to `read_volatile`) are noops
-/// and may be ignored.
-///
-/// [c11]: http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `src` must be [valid] for reads.
-///
-/// * `src` must be properly aligned.
-///
-/// Like [`read`], `read_volatile` creates a bitwise copy of `T`, regardless of
-/// whether `T` is [`Copy`]. If `T` is not [`Copy`], using both the returned
-/// value and the value at `*src` can [violate memory safety][read-ownership].
-/// However, storing non-[`Copy`] types in volatile memory is almost certainly
-/// incorrect.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-/// [`Copy`]: ../marker/trait.Copy.html
-/// [`read`]: ./fn.read.html
-/// [read-ownership]: ./fn.read.html#ownership-of-the-returned-value
-///
-/// Just like in C, whether an operation is volatile has no bearing whatsoever
-/// on questions involving concurrent access from multiple threads. Volatile
-/// accesses behave exactly like non-atomic accesses in that regard. In particular,
-/// a race between a `read_volatile` and any write operation to the same location
-/// is undefined behavior.
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// let x = 12;
-/// let y = &x as *const i32;
-///
-/// unsafe {
-///     assert_eq!(std::ptr::read_volatile(y), 12);
-/// }
-/// ```
-#[inline]
-#[stable(feature = "volatile", since = "1.9.0")]
-pub unsafe fn read_volatile<T>(src: *const T) -> T {
-    intrinsics::volatile_load(src)
-}
-
-/// Performs a volatile write of a memory location with the given value without
-/// reading or dropping the old value.
-///
-/// Volatile operations are intended to act on I/O memory, and are guaranteed
-/// to not be elided or reordered by the compiler across other volatile
-/// operations.
-///
-/// `write_volatile` does not drop the contents of `dst`. This is safe, but it
-/// could leak allocations or resources, so care should be taken not to overwrite
-/// an object that should be dropped.
-///
-/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
-/// location pointed to by `dst`.
-///
-/// [`read_volatile`]: ./fn.read_volatile.html
-///
-/// # Notes
-///
-/// Rust does not currently have a rigorously and formally defined memory model,
-/// so the precise semantics of what "volatile" means here is subject to change
-/// over time. That being said, the semantics will almost always end up pretty
-/// similar to [C11's definition of volatile][c11].
-///
-/// The compiler shouldn't change the relative order or number of volatile
-/// memory operations. However, volatile memory operations on zero-sized types
-/// (e.g., if a zero-sized type is passed to `write_volatile`) are noops
-/// and may be ignored.
-///
-/// [c11]: http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf
-///
-/// # Safety
-///
-/// Behavior is undefined if any of the following conditions are violated:
-///
-/// * `dst` must be [valid] for writes.
-///
-/// * `dst` must be properly aligned.
-///
-/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
-///
-/// [valid]: ../ptr/index.html#safety
-///
-/// Just like in C, whether an operation is volatile has no bearing whatsoever
-/// on questions involving concurrent access from multiple threads. Volatile
-/// accesses behave exactly like non-atomic accesses in that regard. In particular,
-/// a race between a `write_volatile` and any other operation (reading or writing)
-/// on the same location is undefined behavior.
-///
-/// # Examples
-///
-/// Basic usage:
-///
-/// ```
-/// let mut x = 0;
-/// let y = &mut x as *mut i32;
-/// let z = 12;
-///
-/// unsafe {
-///     std::ptr::write_volatile(y, z);
-///     assert_eq!(std::ptr::read_volatile(y), 12);
-/// }
-/// ```
-#[inline]
-#[stable(feature = "volatile", since = "1.9.0")]
-pub unsafe fn write_volatile<T>(dst: *mut T, src: T) {
-    intrinsics::volatile_store(dst, src);
-}
-
-#[lang = "const_ptr"]
-impl<T: ?Sized> *const T {
-    /// Returns `true` if the pointer is null.
-    ///
-    /// Note that unsized types have many possible null pointers, as only the
-    /// raw data pointer is considered, not their length, vtable, etc.
-    /// Therefore, two pointers that are null may still not compare equal to
-    /// each other.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "Follow the rabbit";
-    /// let ptr: *const u8 = s.as_ptr();
-    /// assert!(!ptr.is_null());
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
-    #[inline]
-    pub fn is_null(self) -> bool {
-        // Compare via a cast to a thin pointer, so fat pointers are only
-        // considering their "data" part for null-ness.
-        (self as *const u8) == null()
-    }
-
-    /// Cast to a pointer to a different type
-    #[unstable(feature = "ptr_cast", issue = "60602")]
-    #[inline]
-    pub const fn cast<U>(self) -> *const U {
-        self as _
-    }
-
-    /// Returns `None` if the pointer is null, or else returns a reference to
-    /// the value wrapped in `Some`.
-    ///
-    /// # Safety
-    ///
-    /// While this method and its mutable counterpart are useful for
-    /// null-safety, it is important to note that this is still an unsafe
-    /// operation because the returned value could be pointing to invalid
-    /// memory.
-    ///
-    /// Additionally, the lifetime `'a` returned is arbitrarily chosen and does
-    /// not necessarily reflect the actual lifetime of the data.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let ptr: *const u8 = &10u8 as *const u8;
-    ///
-    /// unsafe {
-    ///     if let Some(val_back) = ptr.as_ref() {
-    ///         println!("We got back the value: {}!", val_back);
-    ///     }
-    /// }
-    /// ```
-    ///
-    /// # Null-unchecked version
-    ///
-    /// If you are sure the pointer can never be null and are looking for some kind of
-    /// `as_ref_unchecked` that returns the `&T` instead of `Option<&T>`, know that you can
-    /// dereference the pointer directly.
-    ///
-    /// ```
-    /// let ptr: *const u8 = &10u8 as *const u8;
-    ///
-    /// unsafe {
-    ///     let val_back = &*ptr;
-    ///     println!("We got back the value: {}!", val_back);
-    /// }
-    /// ```
-    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
-    #[inline]
-    pub unsafe fn as_ref<'a>(self) -> Option<&'a T> {
-        if self.is_null() {
-            None
-        } else {
-            Some(&*self)
-        }
-    }
-
-    /// Calculates the offset from a pointer.
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum, **in bytes** must fit in a usize.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "123";
-    /// let ptr: *const u8 = s.as_ptr();
-    ///
-    /// unsafe {
-    ///     println!("{}", *ptr.offset(1) as char);
-    ///     println!("{}", *ptr.offset(2) as char);
-    /// }
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
-    #[inline]
-    pub unsafe fn offset(self, count: isize) -> *const T where T: Sized {
-        intrinsics::offset(self, count)
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    /// In particular, the resulting pointer may *not* be used to access a
-    /// different allocated object than the one `self` points to. In other
-    /// words, `x.wrapping_offset(y.wrapping_offset_from(x))` is
-    /// *not* the same as `y`, and dereferencing it is undefined behavior
-    /// unless `x` and `y` point into the same allocated object.
-    ///
-    /// Always use `.offset(count)` instead when possible, because `offset`
-    /// allows the compiler to optimize better. If you need to cross object
-    /// boundaries, cast the pointer to an integer and do the arithmetic there.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements
-    /// let data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *const u8 = data.as_ptr();
-    /// let step = 2;
-    /// let end_rounded_up = ptr.wrapping_offset(6);
-    ///
-    /// // This loop prints "1, 3, 5, "
-    /// while ptr != end_rounded_up {
-    ///     unsafe {
-    ///         print!("{}, ", *ptr);
-    ///     }
-    ///     ptr = ptr.wrapping_offset(step);
-    /// }
-    /// ```
-    #[stable(feature = "ptr_wrapping_offset", since = "1.16.0")]
-    #[inline]
-    pub fn wrapping_offset(self, count: isize) -> *const T where T: Sized {
-        unsafe {
-            intrinsics::arith_offset(self, count)
-        }
-    }
-
-    /// Calculates the distance between two pointers. The returned value is in
-    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
-    ///
-    /// This function is the inverse of [`offset`].
-    ///
-    /// [`offset`]: #method.offset
-    /// [`wrapping_offset_from`]: #method.wrapping_offset_from
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and other pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The distance between the pointers, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The distance between the pointers, in bytes, must be an exact multiple
-    ///   of the size of `T`.
-    ///
-    /// * The distance being in bounds cannot rely on "wrapping around" the address space.
-    ///
-    /// The compiler and standard library generally try to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `ptr_into_vec.offset_from(vec.as_ptr())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using [`wrapping_offset_from`] instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Panics
-    ///
-    /// This function panics if `T` is a Zero-Sized Type ("ZST").
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// #![feature(ptr_offset_from)]
-    ///
-    /// let a = [0; 5];
-    /// let ptr1: *const i32 = &a[1];
-    /// let ptr2: *const i32 = &a[3];
-    /// unsafe {
-    ///     assert_eq!(ptr2.offset_from(ptr1), 2);
-    ///     assert_eq!(ptr1.offset_from(ptr2), -2);
-    ///     assert_eq!(ptr1.offset(2), ptr2);
-    ///     assert_eq!(ptr2.offset(-2), ptr1);
-    /// }
-    /// ```
-    #[unstable(feature = "ptr_offset_from", issue = "41079")]
-    #[inline]
-    pub unsafe fn offset_from(self, origin: *const T) -> isize where T: Sized {
-        let pointee_size = mem::size_of::<T>();
-        assert!(0 < pointee_size && pointee_size <= isize::max_value() as usize);
-
-        // This is the same sequence that Clang emits for pointer subtraction.
-        // It can be neither `nsw` nor `nuw` because the input is treated as
-        // unsigned but then the output is treated as signed, so neither works.
-        let d = isize::wrapping_sub(self as _, origin as _);
-        intrinsics::exact_div(d, pointee_size as _)
-    }
-
-    /// Calculates the distance between two pointers. The returned value is in
-    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
-    ///
-    /// If the address different between the two pointers is not a multiple of
-    /// `mem::size_of::<T>()` then the result of the division is rounded towards
-    /// zero.
-    ///
-    /// Though this method is safe for any two pointers, note that its result
-    /// will be mostly useless if the two pointers aren't into the same allocated
-    /// object, for example if they point to two different local variables.
-    ///
-    /// # Panics
-    ///
-    /// This function panics if `T` is a zero-sized type.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// #![feature(ptr_wrapping_offset_from)]
-    ///
-    /// let a = [0; 5];
-    /// let ptr1: *const i32 = &a[1];
-    /// let ptr2: *const i32 = &a[3];
-    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
-    /// assert_eq!(ptr1.wrapping_offset_from(ptr2), -2);
-    /// assert_eq!(ptr1.wrapping_offset(2), ptr2);
-    /// assert_eq!(ptr2.wrapping_offset(-2), ptr1);
-    ///
-    /// let ptr1: *const i32 = 3 as _;
-    /// let ptr2: *const i32 = 13 as _;
-    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
-    /// ```
-    #[unstable(feature = "ptr_wrapping_offset_from", issue = "41079")]
-    #[inline]
-    pub fn wrapping_offset_from(self, origin: *const T) -> isize where T: Sized {
-        let pointee_size = mem::size_of::<T>();
-        assert!(0 < pointee_size && pointee_size <= isize::max_value() as usize);
-
-        let d = isize::wrapping_sub(self as _, origin as _);
-        d.wrapping_div(pointee_size as _)
-    }
-
-    /// Calculates the offset from a pointer (convenience for `.offset(count as isize)`).
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum must fit in a `usize`.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "123";
-    /// let ptr: *const u8 = s.as_ptr();
-    ///
-    /// unsafe {
-    ///     println!("{}", *ptr.add(1) as char);
-    ///     println!("{}", *ptr.add(2) as char);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn add(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.offset(count as isize)
-    }
-
-    /// Calculates the offset from a pointer (convenience for
-    /// `.offset((count as isize).wrapping_neg())`).
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset cannot exceed `isize::MAX` **bytes**.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum must fit in a usize.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len()).sub(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "123";
-    ///
-    /// unsafe {
-    ///     let end: *const u8 = s.as_ptr().add(3);
-    ///     println!("{}", *end.sub(1) as char);
-    ///     println!("{}", *end.sub(2) as char);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn sub(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.offset((count as isize).wrapping_neg())
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    /// (convenience for `.wrapping_offset(count as isize)`)
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    ///
-    /// Always use `.add(count)` instead when possible, because `add`
-    /// allows the compiler to optimize better.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements
-    /// let data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *const u8 = data.as_ptr();
-    /// let step = 2;
-    /// let end_rounded_up = ptr.wrapping_add(6);
-    ///
-    /// // This loop prints "1, 3, 5, "
-    /// while ptr != end_rounded_up {
-    ///     unsafe {
-    ///         print!("{}, ", *ptr);
-    ///     }
-    ///     ptr = ptr.wrapping_add(step);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub fn wrapping_add(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.wrapping_offset(count as isize)
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    /// (convenience for `.wrapping_offset((count as isize).wrapping_sub())`)
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    ///
-    /// Always use `.sub(count)` instead when possible, because `sub`
-    /// allows the compiler to optimize better.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements (backwards)
-    /// let data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *const u8 = data.as_ptr();
-    /// let start_rounded_down = ptr.wrapping_sub(2);
-    /// ptr = ptr.wrapping_add(4);
-    /// let step = 2;
-    /// // This loop prints "5, 3, 1, "
-    /// while ptr != start_rounded_down {
-    ///     unsafe {
-    ///         print!("{}, ", *ptr);
-    ///     }
-    ///     ptr = ptr.wrapping_sub(step);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub fn wrapping_sub(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.wrapping_offset((count as isize).wrapping_neg())
-    }
-
-    /// Reads the value from `self` without moving it. This leaves the
-    /// memory in `self` unchanged.
-    ///
-    /// See [`ptr::read`] for safety concerns and examples.
-    ///
-    /// [`ptr::read`]: ./ptr/fn.read.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read(self) -> T
-        where T: Sized,
-    {
-        read(self)
-    }
-
-    /// Performs a volatile read of the value from `self` without moving it. This
-    /// leaves the memory in `self` unchanged.
-    ///
-    /// Volatile operations are intended to act on I/O memory, and are guaranteed
-    /// to not be elided or reordered by the compiler across other volatile
-    /// operations.
-    ///
-    /// See [`ptr::read_volatile`] for safety concerns and examples.
-    ///
-    /// [`ptr::read_volatile`]: ./ptr/fn.read_volatile.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read_volatile(self) -> T
-        where T: Sized,
-    {
-        read_volatile(self)
-    }
-
-    /// Reads the value from `self` without moving it. This leaves the
-    /// memory in `self` unchanged.
-    ///
-    /// Unlike `read`, the pointer may be unaligned.
-    ///
-    /// See [`ptr::read_unaligned`] for safety concerns and examples.
-    ///
-    /// [`ptr::read_unaligned`]: ./ptr/fn.read_unaligned.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read_unaligned(self) -> T
-        where T: Sized,
-    {
-        read_unaligned(self)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
-    /// and destination may overlap.
-    ///
-    /// NOTE: this has the *same* argument order as [`ptr::copy`].
-    ///
-    /// See [`ptr::copy`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy`]: ./ptr/fn.copy.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_to(self, dest: *mut T, count: usize)
-        where T: Sized,
-    {
-        copy(self, dest, count)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
-    /// and destination may *not* overlap.
-    ///
-    /// NOTE: this has the *same* argument order as [`ptr::copy_nonoverlapping`].
-    ///
-    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_to_nonoverlapping(self, dest: *mut T, count: usize)
-        where T: Sized,
-    {
-        copy_nonoverlapping(self, dest, count)
-    }
-
-    /// Computes the offset that needs to be applied to the pointer in order to make it aligned to
-    /// `align`.
-    ///
-    /// If it is not possible to align the pointer, the implementation returns
-    /// `usize::max_value()`.
-    ///
-    /// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
-    /// used with the `offset` or `offset_to` methods.
-    ///
-    /// There are no guarantees whatsover that offsetting the pointer will not overflow or go
-    /// beyond the allocation that the pointer points into. It is up to the caller to ensure that
-    /// the returned offset is correct in all terms other than alignment.
-    ///
-    /// # Panics
-    ///
-    /// The function panics if `align` is not a power-of-two.
-    ///
-    /// # Examples
-    ///
-    /// Accessing adjacent `u8` as `u16`
-    ///
-    /// ```
-    /// # fn foo(n: usize) {
-    /// # use std::mem::align_of;
-    /// # unsafe {
-    /// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
-    /// let ptr = &x[n] as *const u8;
-    /// let offset = ptr.align_offset(align_of::<u16>());
-    /// if offset < x.len() - n - 1 {
-    ///     let u16_ptr = ptr.add(offset) as *const u16;
-    ///     assert_ne!(*u16_ptr, 500);
-    /// } else {
-    ///     // while the pointer can be aligned via `offset`, it would point
-    ///     // outside the allocation
-    /// }
-    /// # } }
-    /// ```
-    #[stable(feature = "align_offset", since = "1.36.0")]
-    pub fn align_offset(self, align: usize) -> usize where T: Sized {
-        if !align.is_power_of_two() {
-            panic!("align_offset: align is not a power-of-two");
-        }
-        unsafe {
-            align_offset(self, align)
-        }
-    }
-}
-
-
-#[lang = "mut_ptr"]
-impl<T: ?Sized> *mut T {
-    /// Returns `true` if the pointer is null.
-    ///
-    /// Note that unsized types have many possible null pointers, as only the
-    /// raw data pointer is considered, not their length, vtable, etc.
-    /// Therefore, two pointers that are null may still not compare equal to
-    /// each other.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let mut s = [1, 2, 3];
-    /// let ptr: *mut u32 = s.as_mut_ptr();
-    /// assert!(!ptr.is_null());
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
-    #[inline]
-    pub fn is_null(self) -> bool {
-        // Compare via a cast to a thin pointer, so fat pointers are only
-        // considering their "data" part for null-ness.
-        (self as *mut u8) == null_mut()
-    }
-
-    /// Cast to a pointer to a different type
-    #[unstable(feature = "ptr_cast", issue = "60602")]
-    #[inline]
-    pub const fn cast<U>(self) -> *mut U {
-        self as _
-    }
-
-    /// Returns `None` if the pointer is null, or else returns a reference to
-    /// the value wrapped in `Some`.
-    ///
-    /// # Safety
-    ///
-    /// While this method and its mutable counterpart are useful for
-    /// null-safety, it is important to note that this is still an unsafe
-    /// operation because the returned value could be pointing to invalid
-    /// memory.
-    ///
-    /// Additionally, the lifetime `'a` returned is arbitrarily chosen and does
-    /// not necessarily reflect the actual lifetime of the data.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let ptr: *mut u8 = &mut 10u8 as *mut u8;
-    ///
-    /// unsafe {
-    ///     if let Some(val_back) = ptr.as_ref() {
-    ///         println!("We got back the value: {}!", val_back);
-    ///     }
-    /// }
-    /// ```
-    ///
-    /// # Null-unchecked version
-    ///
-    /// If you are sure the pointer can never be null and are looking for some kind of
-    /// `as_ref_unchecked` that returns the `&T` instead of `Option<&T>`, know that you can
-    /// dereference the pointer directly.
-    ///
-    /// ```
-    /// let ptr: *mut u8 = &mut 10u8 as *mut u8;
-    ///
-    /// unsafe {
-    ///     let val_back = &*ptr;
-    ///     println!("We got back the value: {}!", val_back);
-    /// }
-    /// ```
-    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
-    #[inline]
-    pub unsafe fn as_ref<'a>(self) -> Option<&'a T> {
-        if self.is_null() {
-            None
-        } else {
-            Some(&*self)
-        }
-    }
-
-    /// Calculates the offset from a pointer.
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum, **in bytes** must fit in a usize.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let mut s = [1, 2, 3];
-    /// let ptr: *mut u32 = s.as_mut_ptr();
-    ///
-    /// unsafe {
-    ///     println!("{}", *ptr.offset(1));
-    ///     println!("{}", *ptr.offset(2));
-    /// }
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
-    #[inline]
-    pub unsafe fn offset(self, count: isize) -> *mut T where T: Sized {
-        intrinsics::offset(self, count) as *mut T
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    /// In particular, the resulting pointer may *not* be used to access a
-    /// different allocated object than the one `self` points to. In other
-    /// words, `x.wrapping_offset(y.wrapping_offset_from(x))` is
-    /// *not* the same as `y`, and dereferencing it is undefined behavior
-    /// unless `x` and `y` point into the same allocated object.
-    ///
-    /// Always use `.offset(count)` instead when possible, because `offset`
-    /// allows the compiler to optimize better. If you need to cross object
-    /// boundaries, cast the pointer to an integer and do the arithmetic there.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements
-    /// let mut data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *mut u8 = data.as_mut_ptr();
-    /// let step = 2;
-    /// let end_rounded_up = ptr.wrapping_offset(6);
-    ///
-    /// while ptr != end_rounded_up {
-    ///     unsafe {
-    ///         *ptr = 0;
-    ///     }
-    ///     ptr = ptr.wrapping_offset(step);
-    /// }
-    /// assert_eq!(&data, &[0, 2, 0, 4, 0]);
-    /// ```
-    #[stable(feature = "ptr_wrapping_offset", since = "1.16.0")]
-    #[inline]
-    pub fn wrapping_offset(self, count: isize) -> *mut T where T: Sized {
-        unsafe {
-            intrinsics::arith_offset(self, count) as *mut T
-        }
-    }
-
-    /// Returns `None` if the pointer is null, or else returns a mutable
-    /// reference to the value wrapped in `Some`.
-    ///
-    /// # Safety
-    ///
-    /// As with `as_ref`, this is unsafe because it cannot verify the validity
-    /// of the returned pointer, nor can it ensure that the lifetime `'a`
-    /// returned is indeed a valid lifetime for the contained data.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let mut s = [1, 2, 3];
-    /// let ptr: *mut u32 = s.as_mut_ptr();
-    /// let first_value = unsafe { ptr.as_mut().unwrap() };
-    /// *first_value = 4;
-    /// println!("{:?}", s); // It'll print: "[4, 2, 3]".
-    /// ```
-    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
-    #[inline]
-    pub unsafe fn as_mut<'a>(self) -> Option<&'a mut T> {
-        if self.is_null() {
-            None
-        } else {
-            Some(&mut *self)
-        }
-    }
-
-    /// Calculates the distance between two pointers. The returned value is in
-    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
-    ///
-    /// This function is the inverse of [`offset`].
-    ///
-    /// [`offset`]: #method.offset-1
-    /// [`wrapping_offset_from`]: #method.wrapping_offset_from-1
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and other pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The distance between the pointers, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The distance between the pointers, in bytes, must be an exact multiple
-    ///   of the size of `T`.
-    ///
-    /// * The distance being in bounds cannot rely on "wrapping around" the address space.
-    ///
-    /// The compiler and standard library generally try to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `ptr_into_vec.offset_from(vec.as_ptr())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using [`wrapping_offset_from`] instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Panics
-    ///
-    /// This function panics if `T` is a Zero-Sized Type ("ZST").
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// #![feature(ptr_offset_from)]
-    ///
-    /// let mut a = [0; 5];
-    /// let ptr1: *mut i32 = &mut a[1];
-    /// let ptr2: *mut i32 = &mut a[3];
-    /// unsafe {
-    ///     assert_eq!(ptr2.offset_from(ptr1), 2);
-    ///     assert_eq!(ptr1.offset_from(ptr2), -2);
-    ///     assert_eq!(ptr1.offset(2), ptr2);
-    ///     assert_eq!(ptr2.offset(-2), ptr1);
-    /// }
-    /// ```
-    #[unstable(feature = "ptr_offset_from", issue = "41079")]
-    #[inline]
-    pub unsafe fn offset_from(self, origin: *const T) -> isize where T: Sized {
-        (self as *const T).offset_from(origin)
-    }
-
-    /// Calculates the distance between two pointers. The returned value is in
-    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
-    ///
-    /// If the address different between the two pointers is not a multiple of
-    /// `mem::size_of::<T>()` then the result of the division is rounded towards
-    /// zero.
-    ///
-    /// Though this method is safe for any two pointers, note that its result
-    /// will be mostly useless if the two pointers aren't into the same allocated
-    /// object, for example if they point to two different local variables.
-    ///
-    /// # Panics
-    ///
-    /// This function panics if `T` is a zero-sized type.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// #![feature(ptr_wrapping_offset_from)]
-    ///
-    /// let mut a = [0; 5];
-    /// let ptr1: *mut i32 = &mut a[1];
-    /// let ptr2: *mut i32 = &mut a[3];
-    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
-    /// assert_eq!(ptr1.wrapping_offset_from(ptr2), -2);
-    /// assert_eq!(ptr1.wrapping_offset(2), ptr2);
-    /// assert_eq!(ptr2.wrapping_offset(-2), ptr1);
-    ///
-    /// let ptr1: *mut i32 = 3 as _;
-    /// let ptr2: *mut i32 = 13 as _;
-    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
-    /// ```
-    #[unstable(feature = "ptr_wrapping_offset_from", issue = "41079")]
-    #[inline]
-    pub fn wrapping_offset_from(self, origin: *const T) -> isize where T: Sized {
-        (self as *const T).wrapping_offset_from(origin)
-    }
-
-    /// Calculates the offset from a pointer (convenience for `.offset(count as isize)`).
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum must fit in a `usize`.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "123";
-    /// let ptr: *const u8 = s.as_ptr();
-    ///
-    /// unsafe {
-    ///     println!("{}", *ptr.add(1) as char);
-    ///     println!("{}", *ptr.add(2) as char);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn add(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.offset(count as isize)
-    }
-
-    /// Calculates the offset from a pointer (convenience for
-    /// `.offset((count as isize).wrapping_neg())`).
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// If any of the following conditions are violated, the result is Undefined
-    /// Behavior:
-    ///
-    /// * Both the starting and resulting pointer must be either in bounds or one
-    ///   byte past the end of the same allocated object.
-    ///
-    /// * The computed offset cannot exceed `isize::MAX` **bytes**.
-    ///
-    /// * The offset being in bounds cannot rely on "wrapping around" the address
-    ///   space. That is, the infinite-precision sum must fit in a usize.
-    ///
-    /// The compiler and standard library generally tries to ensure allocations
-    /// never reach a size where an offset is a concern. For instance, `Vec`
-    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
-    /// `vec.as_ptr().add(vec.len()).sub(vec.len())` is always safe.
-    ///
-    /// Most platforms fundamentally can't even construct such an allocation.
-    /// For instance, no known 64-bit platform can ever serve a request
-    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
-    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
-    /// more than `isize::MAX` bytes with things like Physical Address
-    /// Extension. As such, memory acquired directly from allocators or memory
-    /// mapped files *may* be too large to handle with this function.
-    ///
-    /// Consider using `wrapping_offset` instead if these constraints are
-    /// difficult to satisfy. The only advantage of this method is that it
-    /// enables more aggressive compiler optimizations.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// let s: &str = "123";
-    ///
-    /// unsafe {
-    ///     let end: *const u8 = s.as_ptr().add(3);
-    ///     println!("{}", *end.sub(1) as char);
-    ///     println!("{}", *end.sub(2) as char);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn sub(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.offset((count as isize).wrapping_neg())
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    /// (convenience for `.wrapping_offset(count as isize)`)
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    ///
-    /// Always use `.add(count)` instead when possible, because `add`
-    /// allows the compiler to optimize better.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements
-    /// let data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *const u8 = data.as_ptr();
-    /// let step = 2;
-    /// let end_rounded_up = ptr.wrapping_add(6);
-    ///
-    /// // This loop prints "1, 3, 5, "
-    /// while ptr != end_rounded_up {
-    ///     unsafe {
-    ///         print!("{}, ", *ptr);
-    ///     }
-    ///     ptr = ptr.wrapping_add(step);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub fn wrapping_add(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.wrapping_offset(count as isize)
-    }
-
-    /// Calculates the offset from a pointer using wrapping arithmetic.
-    /// (convenience for `.wrapping_offset((count as isize).wrapping_sub())`)
-    ///
-    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
-    /// offset of `3 * size_of::<T>()` bytes.
-    ///
-    /// # Safety
-    ///
-    /// The resulting pointer does not need to be in bounds, but it is
-    /// potentially hazardous to dereference (which requires `unsafe`).
-    ///
-    /// Always use `.sub(count)` instead when possible, because `sub`
-    /// allows the compiler to optimize better.
-    ///
-    /// # Examples
-    ///
-    /// Basic usage:
-    ///
-    /// ```
-    /// // Iterate using a raw pointer in increments of two elements (backwards)
-    /// let data = [1u8, 2, 3, 4, 5];
-    /// let mut ptr: *const u8 = data.as_ptr();
-    /// let start_rounded_down = ptr.wrapping_sub(2);
-    /// ptr = ptr.wrapping_add(4);
-    /// let step = 2;
-    /// // This loop prints "5, 3, 1, "
-    /// while ptr != start_rounded_down {
-    ///     unsafe {
-    ///         print!("{}, ", *ptr);
-    ///     }
-    ///     ptr = ptr.wrapping_sub(step);
-    /// }
-    /// ```
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub fn wrapping_sub(self, count: usize) -> Self
-        where T: Sized,
-    {
-        self.wrapping_offset((count as isize).wrapping_neg())
-    }
-
-    /// Reads the value from `self` without moving it. This leaves the
-    /// memory in `self` unchanged.
-    ///
-    /// See [`ptr::read`] for safety concerns and examples.
-    ///
-    /// [`ptr::read`]: ./ptr/fn.read.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read(self) -> T
-        where T: Sized,
-    {
-        read(self)
-    }
-
-    /// Performs a volatile read of the value from `self` without moving it. This
-    /// leaves the memory in `self` unchanged.
-    ///
-    /// Volatile operations are intended to act on I/O memory, and are guaranteed
-    /// to not be elided or reordered by the compiler across other volatile
-    /// operations.
-    ///
-    /// See [`ptr::read_volatile`] for safety concerns and examples.
-    ///
-    /// [`ptr::read_volatile`]: ./ptr/fn.read_volatile.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read_volatile(self) -> T
-        where T: Sized,
-    {
-        read_volatile(self)
-    }
-
-    /// Reads the value from `self` without moving it. This leaves the
-    /// memory in `self` unchanged.
-    ///
-    /// Unlike `read`, the pointer may be unaligned.
-    ///
-    /// See [`ptr::read_unaligned`] for safety concerns and examples.
-    ///
-    /// [`ptr::read_unaligned`]: ./ptr/fn.read_unaligned.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn read_unaligned(self) -> T
-        where T: Sized,
-    {
-        read_unaligned(self)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
-    /// and destination may overlap.
-    ///
-    /// NOTE: this has the *same* argument order as [`ptr::copy`].
-    ///
-    /// See [`ptr::copy`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy`]: ./ptr/fn.copy.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_to(self, dest: *mut T, count: usize)
-        where T: Sized,
-    {
-        copy(self, dest, count)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
-    /// and destination may *not* overlap.
-    ///
-    /// NOTE: this has the *same* argument order as [`ptr::copy_nonoverlapping`].
-    ///
-    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_to_nonoverlapping(self, dest: *mut T, count: usize)
-        where T: Sized,
-    {
-        copy_nonoverlapping(self, dest, count)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `src` to `self`. The source
-    /// and destination may overlap.
-    ///
-    /// NOTE: this has the *opposite* argument order of [`ptr::copy`].
-    ///
-    /// See [`ptr::copy`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy`]: ./ptr/fn.copy.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_from(self, src: *const T, count: usize)
-        where T: Sized,
-    {
-        copy(src, self, count)
-    }
-
-    /// Copies `count * size_of<T>` bytes from `src` to `self`. The source
-    /// and destination may *not* overlap.
-    ///
-    /// NOTE: this has the *opposite* argument order of [`ptr::copy_nonoverlapping`].
-    ///
-    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
-    ///
-    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn copy_from_nonoverlapping(self, src: *const T, count: usize)
-        where T: Sized,
-    {
-        copy_nonoverlapping(src, self, count)
-    }
-
-    /// Executes the destructor (if any) of the pointed-to value.
-    ///
-    /// See [`ptr::drop_in_place`] for safety concerns and examples.
-    ///
-    /// [`ptr::drop_in_place`]: ./ptr/fn.drop_in_place.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn drop_in_place(self) {
-        drop_in_place(self)
-    }
-
-    /// Overwrites a memory location with the given value without reading or
-    /// dropping the old value.
-    ///
-    /// See [`ptr::write`] for safety concerns and examples.
-    ///
-    /// [`ptr::write`]: ./ptr/fn.write.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn write(self, val: T)
-        where T: Sized,
-    {
-        write(self, val)
-    }
-
-    /// Invokes memset on the specified pointer, setting `count * size_of::<T>()`
-    /// bytes of memory starting at `self` to `val`.
-    ///
-    /// See [`ptr::write_bytes`] for safety concerns and examples.
-    ///
-    /// [`ptr::write_bytes`]: ./ptr/fn.write_bytes.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn write_bytes(self, val: u8, count: usize)
-        where T: Sized,
-    {
-        write_bytes(self, val, count)
-    }
-
-    /// Performs a volatile write of a memory location with the given value without
-    /// reading or dropping the old value.
-    ///
-    /// Volatile operations are intended to act on I/O memory, and are guaranteed
-    /// to not be elided or reordered by the compiler across other volatile
-    /// operations.
-    ///
-    /// See [`ptr::write_volatile`] for safety concerns and examples.
-    ///
-    /// [`ptr::write_volatile`]: ./ptr/fn.write_volatile.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn write_volatile(self, val: T)
-        where T: Sized,
-    {
-        write_volatile(self, val)
-    }
-
-    /// Overwrites a memory location with the given value without reading or
-    /// dropping the old value.
-    ///
-    /// Unlike `write`, the pointer may be unaligned.
-    ///
-    /// See [`ptr::write_unaligned`] for safety concerns and examples.
-    ///
-    /// [`ptr::write_unaligned`]: ./ptr/fn.write_unaligned.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn write_unaligned(self, val: T)
-        where T: Sized,
-    {
-        write_unaligned(self, val)
-    }
-
-    /// Replaces the value at `self` with `src`, returning the old
-    /// value, without dropping either.
-    ///
-    /// See [`ptr::replace`] for safety concerns and examples.
-    ///
-    /// [`ptr::replace`]: ./ptr/fn.replace.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn replace(self, src: T) -> T
-        where T: Sized,
-    {
-        replace(self, src)
-    }
-
-    /// Swaps the values at two mutable locations of the same type, without
-    /// deinitializing either. They may overlap, unlike `mem::swap` which is
-    /// otherwise equivalent.
-    ///
-    /// See [`ptr::swap`] for safety concerns and examples.
-    ///
-    /// [`ptr::swap`]: ./ptr/fn.swap.html
-    #[stable(feature = "pointer_methods", since = "1.26.0")]
-    #[inline]
-    pub unsafe fn swap(self, with: *mut T)
-        where T: Sized,
-    {
-        swap(self, with)
-    }
-
-    /// Computes the offset that needs to be applied to the pointer in order to make it aligned to
-    /// `align`.
-    ///
-    /// If it is not possible to align the pointer, the implementation returns
-    /// `usize::max_value()`.
-    ///
-    /// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
-    /// used with the `offset` or `offset_to` methods.
-    ///
-    /// There are no guarantees whatsover that offsetting the pointer will not overflow or go
-    /// beyond the allocation that the pointer points into. It is up to the caller to ensure that
-    /// the returned offset is correct in all terms other than alignment.
-    ///
-    /// # Panics
-    ///
-    /// The function panics if `align` is not a power-of-two.
-    ///
-    /// # Examples
-    ///
-    /// Accessing adjacent `u8` as `u16`
-    ///
-    /// ```
-    /// # fn foo(n: usize) {
-    /// # use std::mem::align_of;
-    /// # unsafe {
-    /// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
-    /// let ptr = &x[n] as *const u8;
-    /// let offset = ptr.align_offset(align_of::<u16>());
-    /// if offset < x.len() - n - 1 {
-    ///     let u16_ptr = ptr.add(offset) as *const u16;
-    ///     assert_ne!(*u16_ptr, 500);
-    /// } else {
-    ///     // while the pointer can be aligned via `offset`, it would point
-    ///     // outside the allocation
-    /// }
-    /// # } }
-    /// ```
-    #[stable(feature = "align_offset", since = "1.36.0")]
-    pub fn align_offset(self, align: usize) -> usize where T: Sized {
-        if !align.is_power_of_two() {
-            panic!("align_offset: align is not a power-of-two");
-        }
-        unsafe {
-            align_offset(self, align)
-        }
-    }
-}
-
-/// Align pointer `p`.
-///
-/// Calculate offset (in terms of elements of `stride` stride) that has to be applied
-/// to pointer `p` so that pointer `p` would get aligned to `a`.
-///
-/// Note: This implementation has been carefully tailored to not panic. It is UB for this to panic.
-/// The only real change that can be made here is change of `INV_TABLE_MOD_16` and associated
-/// constants.
-///
-/// If we ever decide to make it possible to call the intrinsic with `a` that is not a
-/// power-of-two, it will probably be more prudent to just change to a naive implementation rather
-/// than trying to adapt this to accommodate that change.
-///
-/// Any questions go to @nagisa.
-#[lang="align_offset"]
-pub(crate) unsafe fn align_offset<T: Sized>(p: *const T, a: usize) -> usize {
-    /// Calculate multiplicative modular inverse of `x` modulo `m`.
-    ///
-    /// This implementation is tailored for align_offset and has following preconditions:
-    ///
-    /// * `m` is a power-of-two;
-    /// * `x < m`; (if `x ≥ m`, pass in `x % m` instead)
-    ///
-    /// Implementation of this function shall not panic. Ever.
-    #[inline]
-    fn mod_inv(x: usize, m: usize) -> usize {
-        /// Multiplicative modular inverse table modulo 2⁴ = 16.
-        ///
-        /// Note, that this table does not contain values where inverse does not exist (i.e., for
-        /// `0⁻¹ mod 16`, `2⁻¹ mod 16`, etc.)
-        const INV_TABLE_MOD_16: [u8; 8] = [1, 11, 13, 7, 9, 3, 5, 15];
-        /// Modulo for which the `INV_TABLE_MOD_16` is intended.
-        const INV_TABLE_MOD: usize = 16;
-        /// INV_TABLE_MOD²
-        const INV_TABLE_MOD_SQUARED: usize = INV_TABLE_MOD * INV_TABLE_MOD;
-
-        let table_inverse = INV_TABLE_MOD_16[(x & (INV_TABLE_MOD - 1)) >> 1] as usize;
-        if m <= INV_TABLE_MOD {
-            table_inverse & (m - 1)
-        } else {
-            // We iterate "up" using the following formula:
-            //
-            // $$ xy ≡ 1 (mod 2ⁿ) → xy (2 - xy) ≡ 1 (mod 2²ⁿ) $$
-            //
-            // until 2²ⁿ ≥ m. Then we can reduce to our desired `m` by taking the result `mod m`.
-            let mut inverse = table_inverse;
-            let mut going_mod = INV_TABLE_MOD_SQUARED;
-            loop {
-                // y = y * (2 - xy) mod n
-                //
-                // Note, that we use wrapping operations here intentionally – the original formula
-                // uses e.g., subtraction `mod n`. It is entirely fine to do them `mod
-                // usize::max_value()` instead, because we take the result `mod n` at the end
-                // anyway.
-                inverse = inverse.wrapping_mul(
-                    2usize.wrapping_sub(x.wrapping_mul(inverse))
-                ) & (going_mod - 1);
-                if going_mod > m {
-                    return inverse & (m - 1);
-                }
-                going_mod = going_mod.wrapping_mul(going_mod);
-            }
-        }
-    }
-
-    let stride = mem::size_of::<T>();
-    let a_minus_one = a.wrapping_sub(1);
-    let pmoda = p as usize & a_minus_one;
-
-    if pmoda == 0 {
-        // Already aligned. Yay!
-        return 0;
-    }
-
-    if stride <= 1 {
-        return if stride == 0 {
-            // If the pointer is not aligned, and the element is zero-sized, then no amount of
-            // elements will ever align the pointer.
-            !0
-        } else {
-            a.wrapping_sub(pmoda)
-        };
-    }
-
-    let smoda = stride & a_minus_one;
-    // a is power-of-two so cannot be 0. stride = 0 is handled above.
-    let gcdpow = intrinsics::cttz_nonzero(stride).min(intrinsics::cttz_nonzero(a));
-    let gcd = 1usize << gcdpow;
-
-    if p as usize & (gcd - 1) == 0 {
-        // This branch solves for the following linear congruence equation:
-        //
-        // $$ p + so ≡ 0 mod a $$
-        //
-        // $p$ here is the pointer value, $s$ – stride of `T`, $o$ offset in `T`s, and $a$ – the
-        // requested alignment.
-        //
-        // g = gcd(a, s)
-        // o = (a - (p mod a))/g * ((s/g)⁻¹ mod a)
-        //
-        // The first term is “the relative alignment of p to a”, the second term is “how does
-        // incrementing p by s bytes change the relative alignment of p”. Division by `g` is
-        // necessary to make this equation well formed if $a$ and $s$ are not co-prime.
-        //
-        // Furthermore, the result produced by this solution is not “minimal”, so it is necessary
-        // to take the result $o mod lcm(s, a)$. We can replace $lcm(s, a)$ with just a $a / g$.
-        let j = a.wrapping_sub(pmoda) >> gcdpow;
-        let k = smoda >> gcdpow;
-        return intrinsics::unchecked_rem(j.wrapping_mul(mod_inv(k, a)), a >> gcdpow);
-    }
-
-    // Cannot be aligned at all.
-    usize::max_value()
-}
-
-
-
-// Equality for pointers
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> PartialEq for *const T {
-    #[inline]
-    fn eq(&self, other: &*const T) -> bool { *self == *other }
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> Eq for *const T {}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> PartialEq for *mut T {
-    #[inline]
-    fn eq(&self, other: &*mut T) -> bool { *self == *other }
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> Eq for *mut T {}
-
-/// Compares raw pointers for equality.
-///
-/// This is the same as using the `==` operator, but less generic:
-/// the arguments have to be `*const T` raw pointers,
-/// not anything that implements `PartialEq`.
-///
-/// This can be used to compare `&T` references (which coerce to `*const T` implicitly)
-/// by their address rather than comparing the values they point to
-/// (which is what the `PartialEq for &T` implementation does).
-///
-/// # Examples
-///
-/// ```
-/// use std::ptr;
-///
-/// let five = 5;
-/// let other_five = 5;
-/// let five_ref = &five;
-/// let same_five_ref = &five;
-/// let other_five_ref = &other_five;
-///
-/// assert!(five_ref == same_five_ref);
-/// assert!(ptr::eq(five_ref, same_five_ref));
-///
-/// assert!(five_ref == other_five_ref);
-/// assert!(!ptr::eq(five_ref, other_five_ref));
-/// ```
-///
-/// Slices are also compared by their length (fat pointers):
-///
-/// ```
-/// let a = [1, 2, 3];
-/// assert!(std::ptr::eq(&a[..3], &a[..3]));
-/// assert!(!std::ptr::eq(&a[..2], &a[..3]));
-/// assert!(!std::ptr::eq(&a[0..2], &a[1..3]));
-/// ```
-///
-/// Traits are also compared by their implementation:
-///
-/// ```
-/// #[repr(transparent)]
-/// struct Wrapper { member: i32 }
-///
-/// trait Trait {}
-/// impl Trait for Wrapper {}
-/// impl Trait for i32 {}
-///
-/// fn main() {
-///     let wrapper = Wrapper { member: 10 };
-///
-///     // Pointers have equal addresses.
-///     assert!(std::ptr::eq(
-///         &wrapper as *const Wrapper as *const u8,
-///         &wrapper.member as *const i32 as *const u8
-///     ));
-///
-///     // Objects have equal addresses, but `Trait` has different implementations.
-///     assert!(!std::ptr::eq(
-///         &wrapper as &dyn Trait,
-///         &wrapper.member as &dyn Trait,
-///     ));
-///     assert!(!std::ptr::eq(
-///         &wrapper as &dyn Trait as *const dyn Trait,
-///         &wrapper.member as &dyn Trait as *const dyn Trait,
-///     ));
-///
-///     // Converting the reference to a `*const u8` compares by address.
-///     assert!(std::ptr::eq(
-///         &wrapper as &dyn Trait as *const dyn Trait as *const u8,
-///         &wrapper.member as &dyn Trait as *const dyn Trait as *const u8,
-///     ));
-/// }
-/// ```
-#[stable(feature = "ptr_eq", since = "1.17.0")]
-#[inline]
-pub fn eq<T: ?Sized>(a: *const T, b: *const T) -> bool {
-    a == b
-}
-
-/// Hash a raw pointer.
-///
-/// This can be used to hash a `&T` reference (which coerces to `*const T` implicitly)
-/// by its address rather than the value it points to
-/// (which is what the `Hash for &T` implementation does).
-///
-/// # Examples
-///
-/// ```
-/// use std::collections::hash_map::DefaultHasher;
-/// use std::hash::{Hash, Hasher};
-/// use std::ptr;
-///
-/// let five = 5;
-/// let five_ref = &five;
-///
-/// let mut hasher = DefaultHasher::new();
-/// ptr::hash(five_ref, &mut hasher);
-/// let actual = hasher.finish();
-///
-/// let mut hasher = DefaultHasher::new();
-/// (five_ref as *const i32).hash(&mut hasher);
-/// let expected = hasher.finish();
-///
-/// assert_eq!(actual, expected);
-/// ```
-#[stable(feature = "ptr_hash", since = "1.35.0")]
-pub fn hash<T: ?Sized, S: hash::Hasher>(hashee: *const T, into: &mut S) {
-    use crate::hash::Hash;
-    hashee.hash(into);
-}
-
-// Impls for function pointers
-macro_rules! fnptr_impls_safety_abi {
-    ($FnTy: ty, $($Arg: ident),*) => {
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> PartialEq for $FnTy {
-            #[inline]
-            fn eq(&self, other: &Self) -> bool {
-                *self as usize == *other as usize
-            }
-        }
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> Eq for $FnTy {}
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> PartialOrd for $FnTy {
-            #[inline]
-            fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
-                (*self as usize).partial_cmp(&(*other as usize))
-            }
-        }
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> Ord for $FnTy {
-            #[inline]
-            fn cmp(&self, other: &Self) -> Ordering {
-                (*self as usize).cmp(&(*other as usize))
-            }
-        }
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> hash::Hash for $FnTy {
-            fn hash<HH: hash::Hasher>(&self, state: &mut HH) {
-                state.write_usize(*self as usize)
-            }
-        }
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> fmt::Pointer for $FnTy {
-            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-                fmt::Pointer::fmt(&(*self as *const ()), f)
-            }
-        }
-
-        #[stable(feature = "fnptr_impls", since = "1.4.0")]
-        impl<Ret, $($Arg),*> fmt::Debug for $FnTy {
-            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-                fmt::Pointer::fmt(&(*self as *const ()), f)
-            }
-        }
-    }
-}
-
-macro_rules! fnptr_impls_args {
-    ($($Arg: ident),+) => {
-        fnptr_impls_safety_abi! { extern "Rust" fn($($Arg),*) -> Ret, $($Arg),* }
-        fnptr_impls_safety_abi! { extern "C" fn($($Arg),*) -> Ret, $($Arg),* }
-        fnptr_impls_safety_abi! { extern "C" fn($($Arg),* , ...) -> Ret, $($Arg),* }
-        fnptr_impls_safety_abi! { unsafe extern "Rust" fn($($Arg),*) -> Ret, $($Arg),* }
-        fnptr_impls_safety_abi! { unsafe extern "C" fn($($Arg),*) -> Ret, $($Arg),* }
-        fnptr_impls_safety_abi! { unsafe extern "C" fn($($Arg),* , ...) -> Ret, $($Arg),* }
-    };
-    () => {
-        // No variadic functions with 0 parameters
-        fnptr_impls_safety_abi! { extern "Rust" fn() -> Ret, }
-        fnptr_impls_safety_abi! { extern "C" fn() -> Ret, }
-        fnptr_impls_safety_abi! { unsafe extern "Rust" fn() -> Ret, }
-        fnptr_impls_safety_abi! { unsafe extern "C" fn() -> Ret, }
-    };
-}
-
-fnptr_impls_args! { }
-fnptr_impls_args! { A }
-fnptr_impls_args! { A, B }
-fnptr_impls_args! { A, B, C }
-fnptr_impls_args! { A, B, C, D }
-fnptr_impls_args! { A, B, C, D, E }
-fnptr_impls_args! { A, B, C, D, E, F }
-fnptr_impls_args! { A, B, C, D, E, F, G }
-fnptr_impls_args! { A, B, C, D, E, F, G, H }
-fnptr_impls_args! { A, B, C, D, E, F, G, H, I }
-fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J }
-fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J, K }
-fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J, K, L }
-
-// Comparison for pointers
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> Ord for *const T {
-    #[inline]
-    fn cmp(&self, other: &*const T) -> Ordering {
-        if self < other {
-            Less
-        } else if self == other {
-            Equal
-        } else {
-            Greater
-        }
-    }
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> PartialOrd for *const T {
-    #[inline]
-    fn partial_cmp(&self, other: &*const T) -> Option<Ordering> {
-        Some(self.cmp(other))
-    }
-
-    #[inline]
-    fn lt(&self, other: &*const T) -> bool { *self < *other }
-
-    #[inline]
-    fn le(&self, other: &*const T) -> bool { *self <= *other }
-
-    #[inline]
-    fn gt(&self, other: &*const T) -> bool { *self > *other }
-
-    #[inline]
-    fn ge(&self, other: &*const T) -> bool { *self >= *other }
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> Ord for *mut T {
-    #[inline]
-    fn cmp(&self, other: &*mut T) -> Ordering {
-        if self < other {
-            Less
-        } else if self == other {
-            Equal
-        } else {
-            Greater
-        }
-    }
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> PartialOrd for *mut T {
-    #[inline]
-    fn partial_cmp(&self, other: &*mut T) -> Option<Ordering> {
-        Some(self.cmp(other))
-    }
-
-    #[inline]
-    fn lt(&self, other: &*mut T) -> bool { *self < *other }
-
-    #[inline]
-    fn le(&self, other: &*mut T) -> bool { *self <= *other }
-
-    #[inline]
-    fn gt(&self, other: &*mut T) -> bool { *self > *other }
-
-    #[inline]
-    fn ge(&self, other: &*mut T) -> bool { *self >= *other }
-}
-
-/// A wrapper around a raw non-null `*mut T` that indicates that the possessor
-/// of this wrapper owns the referent. Useful for building abstractions like
-/// `Box<T>`, `Vec<T>`, `String`, and `HashMap<K, V>`.
-///
-/// Unlike `*mut T`, `Unique<T>` behaves "as if" it were an instance of `T`.
-/// It implements `Send`/`Sync` if `T` is `Send`/`Sync`. It also implies
-/// the kind of strong aliasing guarantees an instance of `T` can expect:
-/// the referent of the pointer should not be modified without a unique path to
-/// its owning Unique.
-///
-/// If you're uncertain of whether it's correct to use `Unique` for your purposes,
-/// consider using `NonNull`, which has weaker semantics.
-///
-/// Unlike `*mut T`, the pointer must always be non-null, even if the pointer
-/// is never dereferenced. This is so that enums may use this forbidden value
-/// as a discriminant -- `Option<Unique<T>>` has the same size as `Unique<T>`.
-/// However the pointer may still dangle if it isn't dereferenced.
-///
-/// Unlike `*mut T`, `Unique<T>` is covariant over `T`. This should always be correct
-/// for any type which upholds Unique's aliasing requirements.
-#[unstable(feature = "ptr_internals", issue = "0",
-           reason = "use NonNull instead and consider PhantomData<T> \
-                     (if you also use #[may_dangle]), Send, and/or Sync")]
-#[doc(hidden)]
-#[repr(transparent)]
-#[rustc_layout_scalar_valid_range_start(1)]
-pub struct Unique<T: ?Sized> {
-    pointer: *const T,
-    // NOTE: this marker has no consequences for variance, but is necessary
-    // for dropck to understand that we logically own a `T`.
-    //
-    // For details, see:
-    // https://github.com/rust-lang/rfcs/blob/master/text/0769-sound-generic-drop.md#phantom-data
-    _marker: PhantomData<T>,
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> fmt::Debug for Unique<T> {
-    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        fmt::Pointer::fmt(&self.as_ptr(), f)
-    }
-}
-
-/// `Unique` pointers are `Send` if `T` is `Send` because the data they
-/// reference is unaliased. Note that this aliasing invariant is
-/// unenforced by the type system; the abstraction using the
-/// `Unique` must enforce it.
-#[unstable(feature = "ptr_internals", issue = "0")]
-unsafe impl<T: Send + ?Sized> Send for Unique<T> { }
-
-/// `Unique` pointers are `Sync` if `T` is `Sync` because the data they
-/// reference is unaliased. Note that this aliasing invariant is
-/// unenforced by the type system; the abstraction using the
-/// `Unique` must enforce it.
-#[unstable(feature = "ptr_internals", issue = "0")]
-unsafe impl<T: Sync + ?Sized> Sync for Unique<T> { }
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: Sized> Unique<T> {
-    /// Creates a new `Unique` that is dangling, but well-aligned.
-    ///
-    /// This is useful for initializing types which lazily allocate, like
-    /// `Vec::new` does.
-    ///
-    /// Note that the pointer value may potentially represent a valid pointer to
-    /// a `T`, which means this must not be used as a "not yet initialized"
-    /// sentinel value. Types that lazily allocate must track initialization by
-    /// some other means.
-    // FIXME: rename to dangling() to match NonNull?
-    pub const fn empty() -> Self {
-        unsafe {
-            Unique::new_unchecked(mem::align_of::<T>() as *mut T)
-        }
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> Unique<T> {
-    /// Creates a new `Unique`.
-    ///
-    /// # Safety
-    ///
-    /// `ptr` must be non-null.
-    pub const unsafe fn new_unchecked(ptr: *mut T) -> Self {
-        Unique { pointer: ptr as _, _marker: PhantomData }
-    }
-
-    /// Creates a new `Unique` if `ptr` is non-null.
-    pub fn new(ptr: *mut T) -> Option<Self> {
-        if !ptr.is_null() {
-            Some(unsafe { Unique { pointer: ptr as _, _marker: PhantomData } })
-        } else {
-            None
-        }
-    }
-
-    /// Acquires the underlying `*mut` pointer.
-    pub const fn as_ptr(self) -> *mut T {
-        self.pointer as *mut T
-    }
-
-    /// Dereferences the content.
-    ///
-    /// The resulting lifetime is bound to self so this behaves "as if"
-    /// it were actually an instance of T that is getting borrowed. If a longer
-    /// (unbound) lifetime is needed, use `&*my_ptr.as_ptr()`.
-    pub unsafe fn as_ref(&self) -> &T {
-        &*self.as_ptr()
-    }
-
-    /// Mutably dereferences the content.
-    ///
-    /// The resulting lifetime is bound to self so this behaves "as if"
-    /// it were actually an instance of T that is getting borrowed. If a longer
-    /// (unbound) lifetime is needed, use `&mut *my_ptr.as_ptr()`.
-    pub unsafe fn as_mut(&mut self) -> &mut T {
-        &mut *self.as_ptr()
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> Clone for Unique<T> {
-    fn clone(&self) -> Self {
-        *self
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> Copy for Unique<T> { }
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized, U: ?Sized> CoerceUnsized<Unique<U>> for Unique<T> where T: Unsize<U> { }
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized, U: ?Sized> DispatchFromDyn<Unique<U>> for Unique<T> where T: Unsize<U> { }
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> fmt::Pointer for Unique<T> {
-    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        fmt::Pointer::fmt(&self.as_ptr(), f)
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> From<&mut T> for Unique<T> {
-    fn from(reference: &mut T) -> Self {
-        unsafe { Unique { pointer: reference as *mut T, _marker: PhantomData } }
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> From<&T> for Unique<T> {
-    fn from(reference: &T) -> Self {
-        unsafe { Unique { pointer: reference as *const T, _marker: PhantomData } }
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<'a, T: ?Sized> From<NonNull<T>> for Unique<T> {
-    fn from(p: NonNull<T>) -> Self {
-        unsafe { Unique { pointer: p.pointer, _marker: PhantomData } }
-    }
-}
-
-/// `*mut T` but non-zero and covariant.
-///
-/// This is often the correct thing to use when building data structures using
-/// raw pointers, but is ultimately more dangerous to use because of its additional
-/// properties. If you're not sure if you should use `NonNull<T>`, just use `*mut T`!
-///
-/// Unlike `*mut T`, the pointer must always be non-null, even if the pointer
-/// is never dereferenced. This is so that enums may use this forbidden value
-/// as a discriminant -- `Option<NonNull<T>>` has the same size as `*mut T`.
-/// However the pointer may still dangle if it isn't dereferenced.
-///
-/// Unlike `*mut T`, `NonNull<T>` is covariant over `T`. If this is incorrect
-/// for your use case, you should include some [`PhantomData`] in your type to
-/// provide invariance, such as `PhantomData<Cell<T>>` or `PhantomData<&'a mut T>`.
-/// Usually this won't be necessary; covariance is correct for most safe abstractions,
-/// such as `Box`, `Rc`, `Arc`, `Vec`, and `LinkedList`. This is the case because they
-/// provide a public API that follows the normal shared XOR mutable rules of Rust.
-///
-/// Notice that `NonNull<T>` has a `From` instance for `&T`. However, this does
-/// not change the fact that mutating through a (pointer derived from a) shared
-/// reference is undefined behavior unless the mutation happens inside an
-/// [`UnsafeCell<T>`]. The same goes for creating a mutable reference from a shared
-/// reference. When using this `From` instance without an `UnsafeCell<T>`,
-/// it is your responsibility to ensure that `as_mut` is never called, and `as_ptr`
-/// is never used for mutation.
-///
-/// [`PhantomData`]: ../marker/struct.PhantomData.html
-/// [`UnsafeCell<T>`]: ../cell/struct.UnsafeCell.html
-#[stable(feature = "nonnull", since = "1.25.0")]
-#[repr(transparent)]
-#[rustc_layout_scalar_valid_range_start(1)]
-#[cfg_attr(not(stage0), rustc_nonnull_optimization_guaranteed)]
-pub struct NonNull<T: ?Sized> {
-    pointer: *const T,
-}
-
-/// `NonNull` pointers are not `Send` because the data they reference may be aliased.
-// N.B., this impl is unnecessary, but should provide better error messages.
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> !Send for NonNull<T> { }
-
-/// `NonNull` pointers are not `Sync` because the data they reference may be aliased.
-// N.B., this impl is unnecessary, but should provide better error messages.
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> !Sync for NonNull<T> { }
-
-impl<T: Sized> NonNull<T> {
-    /// Creates a new `NonNull` that is dangling, but well-aligned.
-    ///
-    /// This is useful for initializing types which lazily allocate, like
-    /// `Vec::new` does.
-    ///
-    /// Note that the pointer value may potentially represent a valid pointer to
-    /// a `T`, which means this must not be used as a "not yet initialized"
-    /// sentinel value. Types that lazily allocate must track initialization by
-    /// some other means.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub const fn dangling() -> Self {
-        unsafe {
-            let ptr = mem::align_of::<T>() as *mut T;
-            NonNull::new_unchecked(ptr)
-        }
-    }
-}
-
-impl<T: ?Sized> NonNull<T> {
-    /// Creates a new `NonNull`.
-    ///
-    /// # Safety
-    ///
-    /// `ptr` must be non-null.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub const unsafe fn new_unchecked(ptr: *mut T) -> Self {
-        NonNull { pointer: ptr as _ }
-    }
-
-    /// Creates a new `NonNull` if `ptr` is non-null.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub fn new(ptr: *mut T) -> Option<Self> {
-        if !ptr.is_null() {
-            Some(unsafe { Self::new_unchecked(ptr) })
-        } else {
-            None
-        }
-    }
-
-    /// Acquires the underlying `*mut` pointer.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub const fn as_ptr(self) -> *mut T {
-        self.pointer as *mut T
-    }
-
-    /// Dereferences the content.
-    ///
-    /// The resulting lifetime is bound to self so this behaves "as if"
-    /// it were actually an instance of T that is getting borrowed. If a longer
-    /// (unbound) lifetime is needed, use `&*my_ptr.as_ptr()`.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub unsafe fn as_ref(&self) -> &T {
-        &*self.as_ptr()
-    }
-
-    /// Mutably dereferences the content.
-    ///
-    /// The resulting lifetime is bound to self so this behaves "as if"
-    /// it were actually an instance of T that is getting borrowed. If a longer
-    /// (unbound) lifetime is needed, use `&mut *my_ptr.as_ptr()`.
-    #[stable(feature = "nonnull", since = "1.25.0")]
-    #[inline]
-    pub unsafe fn as_mut(&mut self) -> &mut T {
-        &mut *self.as_ptr()
-    }
-
-    /// Cast to a pointer of another type
-    #[stable(feature = "nonnull_cast", since = "1.27.0")]
-    #[inline]
-    pub const fn cast<U>(self) -> NonNull<U> {
-        unsafe {
-            NonNull::new_unchecked(self.as_ptr() as *mut U)
-        }
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> Clone for NonNull<T> {
-    fn clone(&self) -> Self {
-        *self
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> Copy for NonNull<T> { }
-
-#[unstable(feature = "coerce_unsized", issue = "27732")]
-impl<T: ?Sized, U: ?Sized> CoerceUnsized<NonNull<U>> for NonNull<T> where T: Unsize<U> { }
-
-#[unstable(feature = "dispatch_from_dyn", issue = "0")]
-impl<T: ?Sized, U: ?Sized> DispatchFromDyn<NonNull<U>> for NonNull<T> where T: Unsize<U> { }
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> fmt::Debug for NonNull<T> {
-    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        fmt::Pointer::fmt(&self.as_ptr(), f)
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> fmt::Pointer for NonNull<T> {
-    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        fmt::Pointer::fmt(&self.as_ptr(), f)
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> Eq for NonNull<T> {}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> PartialEq for NonNull<T> {
-    #[inline]
-    fn eq(&self, other: &Self) -> bool {
-        self.as_ptr() == other.as_ptr()
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> Ord for NonNull<T> {
-    #[inline]
-    fn cmp(&self, other: &Self) -> Ordering {
-        self.as_ptr().cmp(&other.as_ptr())
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> PartialOrd for NonNull<T> {
-    #[inline]
-    fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
-        self.as_ptr().partial_cmp(&other.as_ptr())
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> hash::Hash for NonNull<T> {
-    #[inline]
-    fn hash<H: hash::Hasher>(&self, state: &mut H) {
-        self.as_ptr().hash(state)
-    }
-}
-
-#[unstable(feature = "ptr_internals", issue = "0")]
-impl<T: ?Sized> From<Unique<T>> for NonNull<T> {
-    #[inline]
-    fn from(unique: Unique<T>) -> Self {
-        unsafe { NonNull { pointer: unique.pointer } }
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> From<&mut T> for NonNull<T> {
-    #[inline]
-    fn from(reference: &mut T) -> Self {
-        unsafe { NonNull { pointer: reference as *mut T } }
-    }
-}
-
-#[stable(feature = "nonnull", since = "1.25.0")]
-impl<T: ?Sized> From<&T> for NonNull<T> {
-    #[inline]
-    fn from(reference: &T) -> Self {
-        unsafe { NonNull { pointer: reference as *const T } }
-    }
-}
diff --git a/src/libcore/ptr/mod.rs b/src/libcore/ptr/mod.rs
new file mode 100644 (file)
index 0000000..80ac67d
--- /dev/null
@@ -0,0 +1,2746 @@
+//! Manually manage memory through raw pointers.
+//!
+//! *[See also the pointer primitive types](../../std/primitive.pointer.html).*
+//!
+//! # Safety
+//!
+//! Many functions in this module take raw pointers as arguments and read from
+//! or write to them. For this to be safe, these pointers must be *valid*.
+//! Whether a pointer is valid depends on the operation it is used for
+//! (read or write), and the extent of the memory that is accessed (i.e.,
+//! how many bytes are read/written). Most functions use `*mut T` and `*const T`
+//! to access only a single value, in which case the documentation omits the size
+//! and implicitly assumes it to be `size_of::<T>()` bytes.
+//!
+//! The precise rules for validity are not determined yet. The guarantees that are
+//! provided at this point are very minimal:
+//!
+//! * A [null] pointer is *never* valid, not even for accesses of [size zero][zst].
+//! * All pointers (except for the null pointer) are valid for all operations of
+//!   [size zero][zst].
+//! * All accesses performed by functions in this module are *non-atomic* in the sense
+//!   of [atomic operations] used to synchronize between threads. This means it is
+//!   undefined behavior to perform two concurrent accesses to the same location from different
+//!   threads unless both accesses only read from memory. Notice that this explicitly
+//!   includes [`read_volatile`] and [`write_volatile`]: Volatile accesses cannot
+//!   be used for inter-thread synchronization.
+//! * The result of casting a reference to a pointer is valid for as long as the
+//!   underlying object is live and no reference (just raw pointers) is used to
+//!   access the same memory.
+//!
+//! These axioms, along with careful use of [`offset`] for pointer arithmetic,
+//! are enough to correctly implement many useful things in unsafe code. Stronger guarantees
+//! will be provided eventually, as the [aliasing] rules are being determined. For more
+//! information, see the [book] as well as the section in the reference devoted
+//! to [undefined behavior][ub].
+//!
+//! ## Alignment
+//!
+//! Valid raw pointers as defined above are not necessarily properly aligned (where
+//! "proper" alignment is defined by the pointee type, i.e., `*const T` must be
+//! aligned to `mem::align_of::<T>()`). However, most functions require their
+//! arguments to be properly aligned, and will explicitly state
+//! this requirement in their documentation. Notable exceptions to this are
+//! [`read_unaligned`] and [`write_unaligned`].
+//!
+//! When a function requires proper alignment, it does so even if the access
+//! has size 0, i.e., even if memory is not actually touched. Consider using
+//! [`NonNull::dangling`] in such cases.
+//!
+//! [aliasing]: ../../nomicon/aliasing.html
+//! [book]: ../../book/ch19-01-unsafe-rust.html#dereferencing-a-raw-pointer
+//! [ub]: ../../reference/behavior-considered-undefined.html
+//! [null]: ./fn.null.html
+//! [zst]: ../../nomicon/exotic-sizes.html#zero-sized-types-zsts
+//! [atomic operations]: ../../std/sync/atomic/index.html
+//! [`copy`]: ../../std/ptr/fn.copy.html
+//! [`offset`]: ../../std/primitive.pointer.html#method.offset
+//! [`read_unaligned`]: ./fn.read_unaligned.html
+//! [`write_unaligned`]: ./fn.write_unaligned.html
+//! [`read_volatile`]: ./fn.read_volatile.html
+//! [`write_volatile`]: ./fn.write_volatile.html
+//! [`NonNull::dangling`]: ./struct.NonNull.html#method.dangling
+
+#![stable(feature = "rust1", since = "1.0.0")]
+
+use crate::intrinsics;
+use crate::fmt;
+use crate::hash;
+use crate::mem::{self, MaybeUninit};
+use crate::cmp::Ordering::{self, Less, Equal, Greater};
+
+#[stable(feature = "rust1", since = "1.0.0")]
+pub use crate::intrinsics::copy_nonoverlapping;
+
+#[stable(feature = "rust1", since = "1.0.0")]
+pub use crate::intrinsics::copy;
+
+#[stable(feature = "rust1", since = "1.0.0")]
+pub use crate::intrinsics::write_bytes;
+
+mod non_null;
+#[stable(feature = "nonnull", since = "1.25.0")]
+pub use non_null::NonNull;
+
+mod unique;
+#[unstable(feature = "ptr_internals", issue = "0")]
+pub use unique::Unique;
+
+/// Executes the destructor (if any) of the pointed-to value.
+///
+/// This is semantically equivalent to calling [`ptr::read`] and discarding
+/// the result, but has the following advantages:
+///
+/// * It is *required* to use `drop_in_place` to drop unsized types like
+///   trait objects, because they can't be read out onto the stack and
+///   dropped normally.
+///
+/// * It is friendlier to the optimizer to do this over [`ptr::read`] when
+///   dropping manually allocated memory (e.g., when writing Box/Rc/Vec),
+///   as the compiler doesn't need to prove that it's sound to elide the
+///   copy.
+///
+/// [`ptr::read`]: ../ptr/fn.read.html
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `to_drop` must be [valid] for reads.
+///
+/// * `to_drop` must be properly aligned. See the example below for how to drop
+///   an unaligned pointer.
+///
+/// Additionally, if `T` is not [`Copy`], using the pointed-to value after
+/// calling `drop_in_place` can cause undefined behavior. Note that `*to_drop =
+/// foo` counts as a use because it will cause the value to be dropped
+/// again. [`write`] can be used to overwrite data without causing it to be
+/// dropped.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+/// [`Copy`]: ../marker/trait.Copy.html
+/// [`write`]: ../ptr/fn.write.html
+///
+/// # Examples
+///
+/// Manually remove the last item from a vector:
+///
+/// ```
+/// use std::ptr;
+/// use std::rc::Rc;
+///
+/// let last = Rc::new(1);
+/// let weak = Rc::downgrade(&last);
+///
+/// let mut v = vec![Rc::new(0), last];
+///
+/// unsafe {
+///     // Get a raw pointer to the last element in `v`.
+///     let ptr = &mut v[1] as *mut _;
+///     // Shorten `v` to prevent the last item from being dropped. We do that first,
+///     // to prevent issues if the `drop_in_place` below panics.
+///     v.set_len(1);
+///     // Without a call `drop_in_place`, the last item would never be dropped,
+///     // and the memory it manages would be leaked.
+///     ptr::drop_in_place(ptr);
+/// }
+///
+/// assert_eq!(v, &[0.into()]);
+///
+/// // Ensure that the last item was dropped.
+/// assert!(weak.upgrade().is_none());
+/// ```
+///
+/// Unaligned values cannot be dropped in place, they must be copied to an aligned
+/// location first:
+/// ```
+/// use std::ptr;
+/// use std::mem::{self, MaybeUninit};
+///
+/// unsafe fn drop_after_copy<T>(to_drop: *mut T) {
+///     let mut copy: MaybeUninit<T> = MaybeUninit::uninit();
+///     ptr::copy(to_drop, copy.as_mut_ptr(), 1);
+///     drop(copy.assume_init());
+/// }
+///
+/// #[repr(packed, C)]
+/// struct Packed {
+///     _padding: u8,
+///     unaligned: Vec<i32>,
+/// }
+///
+/// let mut p = Packed { _padding: 0, unaligned: vec![42] };
+/// unsafe {
+///     drop_after_copy(&mut p.unaligned as *mut _);
+///     mem::forget(p);
+/// }
+/// ```
+///
+/// Notice that the compiler performs this copy automatically when dropping packed structs,
+/// i.e., you do not usually have to worry about such issues unless you call `drop_in_place`
+/// manually.
+#[stable(feature = "drop_in_place", since = "1.8.0")]
+#[inline(always)]
+pub unsafe fn drop_in_place<T: ?Sized>(to_drop: *mut T) {
+    real_drop_in_place(&mut *to_drop)
+}
+
+// The real `drop_in_place` -- the one that gets called implicitly when variables go
+// out of scope -- should have a safe reference and not a raw pointer as argument
+// type.  When we drop a local variable, we access it with a pointer that behaves
+// like a safe reference; transmuting that to a raw pointer does not mean we can
+// actually access it with raw pointers.
+#[lang = "drop_in_place"]
+#[allow(unconditional_recursion)]
+unsafe fn real_drop_in_place<T: ?Sized>(to_drop: &mut T) {
+    // Code here does not matter - this is replaced by the
+    // real drop glue by the compiler.
+    real_drop_in_place(to_drop)
+}
+
+/// Creates a null raw pointer.
+///
+/// # Examples
+///
+/// ```
+/// use std::ptr;
+///
+/// let p: *const i32 = ptr::null();
+/// assert!(p.is_null());
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_promotable]
+pub const fn null<T>() -> *const T { 0 as *const T }
+
+/// Creates a null mutable raw pointer.
+///
+/// # Examples
+///
+/// ```
+/// use std::ptr;
+///
+/// let p: *mut i32 = ptr::null_mut();
+/// assert!(p.is_null());
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+#[rustc_promotable]
+pub const fn null_mut<T>() -> *mut T { 0 as *mut T }
+
+/// Swaps the values at two mutable locations of the same type, without
+/// deinitializing either.
+///
+/// But for the following two exceptions, this function is semantically
+/// equivalent to [`mem::swap`]:
+///
+/// * It operates on raw pointers instead of references. When references are
+///   available, [`mem::swap`] should be preferred.
+///
+/// * The two pointed-to values may overlap. If the values do overlap, then the
+///   overlapping region of memory from `x` will be used. This is demonstrated
+///   in the second example below.
+///
+/// [`mem::swap`]: ../mem/fn.swap.html
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * Both `x` and `y` must be [valid] for reads and writes.
+///
+/// * Both `x` and `y` must be properly aligned.
+///
+/// Note that even if `T` has size `0`, the pointers must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+///
+/// # Examples
+///
+/// Swapping two non-overlapping regions:
+///
+/// ```
+/// use std::ptr;
+///
+/// let mut array = [0, 1, 2, 3];
+///
+/// let x = array[0..].as_mut_ptr() as *mut [u32; 2]; // this is `array[0..2]`
+/// let y = array[2..].as_mut_ptr() as *mut [u32; 2]; // this is `array[2..4]`
+///
+/// unsafe {
+///     ptr::swap(x, y);
+///     assert_eq!([2, 3, 0, 1], array);
+/// }
+/// ```
+///
+/// Swapping two overlapping regions:
+///
+/// ```
+/// use std::ptr;
+///
+/// let mut array = [0, 1, 2, 3];
+///
+/// let x = array[0..].as_mut_ptr() as *mut [u32; 3]; // this is `array[0..3]`
+/// let y = array[1..].as_mut_ptr() as *mut [u32; 3]; // this is `array[1..4]`
+///
+/// unsafe {
+///     ptr::swap(x, y);
+///     // The indices `1..3` of the slice overlap between `x` and `y`.
+///     // Reasonable results would be for to them be `[2, 3]`, so that indices `0..3` are
+///     // `[1, 2, 3]` (matching `y` before the `swap`); or for them to be `[0, 1]`
+///     // so that indices `1..4` are `[0, 1, 2]` (matching `x` before the `swap`).
+///     // This implementation is defined to make the latter choice.
+///     assert_eq!([1, 0, 1, 2], array);
+/// }
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn swap<T>(x: *mut T, y: *mut T) {
+    // Give ourselves some scratch space to work with.
+    // We do not have to worry about drops: `MaybeUninit` does nothing when dropped.
+    let mut tmp = MaybeUninit::<T>::uninit();
+
+    // Perform the swap
+    copy_nonoverlapping(x, tmp.as_mut_ptr(), 1);
+    copy(y, x, 1); // `x` and `y` may overlap
+    copy_nonoverlapping(tmp.as_ptr(), y, 1);
+}
+
+/// Swaps `count * size_of::<T>()` bytes between the two regions of memory
+/// beginning at `x` and `y`. The two regions must *not* overlap.
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * Both `x` and `y` must be [valid] for reads and writes of `count *
+///   size_of::<T>()` bytes.
+///
+/// * Both `x` and `y` must be properly aligned.
+///
+/// * The region of memory beginning at `x` with a size of `count *
+///   size_of::<T>()` bytes must *not* overlap with the region of memory
+///   beginning at `y` with the same size.
+///
+/// Note that even if the effectively copied size (`count * size_of::<T>()`) is `0`,
+/// the pointers must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// use std::ptr;
+///
+/// let mut x = [1, 2, 3, 4];
+/// let mut y = [7, 8, 9];
+///
+/// unsafe {
+///     ptr::swap_nonoverlapping(x.as_mut_ptr(), y.as_mut_ptr(), 2);
+/// }
+///
+/// assert_eq!(x, [7, 8, 3, 4]);
+/// assert_eq!(y, [1, 2, 9]);
+/// ```
+#[inline]
+#[stable(feature = "swap_nonoverlapping", since = "1.27.0")]
+pub unsafe fn swap_nonoverlapping<T>(x: *mut T, y: *mut T, count: usize) {
+    let x = x as *mut u8;
+    let y = y as *mut u8;
+    let len = mem::size_of::<T>() * count;
+    swap_nonoverlapping_bytes(x, y, len)
+}
+
+#[inline]
+pub(crate) unsafe fn swap_nonoverlapping_one<T>(x: *mut T, y: *mut T) {
+    // For types smaller than the block optimization below,
+    // just swap directly to avoid pessimizing codegen.
+    if mem::size_of::<T>() < 32 {
+        let z = read(x);
+        copy_nonoverlapping(y, x, 1);
+        write(y, z);
+    } else {
+        swap_nonoverlapping(x, y, 1);
+    }
+}
+
+#[inline]
+unsafe fn swap_nonoverlapping_bytes(x: *mut u8, y: *mut u8, len: usize) {
+    // The approach here is to utilize simd to swap x & y efficiently. Testing reveals
+    // that swapping either 32 bytes or 64 bytes at a time is most efficient for Intel
+    // Haswell E processors. LLVM is more able to optimize if we give a struct a
+    // #[repr(simd)], even if we don't actually use this struct directly.
+    //
+    // FIXME repr(simd) broken on emscripten and redox
+    #[cfg_attr(not(any(target_os = "emscripten", target_os = "redox")), repr(simd))]
+    struct Block(u64, u64, u64, u64);
+    struct UnalignedBlock(u64, u64, u64, u64);
+
+    let block_size = mem::size_of::<Block>();
+
+    // Loop through x & y, copying them `Block` at a time
+    // The optimizer should unroll the loop fully for most types
+    // N.B. We can't use a for loop as the `range` impl calls `mem::swap` recursively
+    let mut i = 0;
+    while i + block_size <= len {
+        // Create some uninitialized memory as scratch space
+        // Declaring `t` here avoids aligning the stack when this loop is unused
+        let mut t = mem::MaybeUninit::<Block>::uninit();
+        let t = t.as_mut_ptr() as *mut u8;
+        let x = x.add(i);
+        let y = y.add(i);
+
+        // Swap a block of bytes of x & y, using t as a temporary buffer
+        // This should be optimized into efficient SIMD operations where available
+        copy_nonoverlapping(x, t, block_size);
+        copy_nonoverlapping(y, x, block_size);
+        copy_nonoverlapping(t, y, block_size);
+        i += block_size;
+    }
+
+    if i < len {
+        // Swap any remaining bytes
+        let mut t = mem::MaybeUninit::<UnalignedBlock>::uninit();
+        let rem = len - i;
+
+        let t = t.as_mut_ptr() as *mut u8;
+        let x = x.add(i);
+        let y = y.add(i);
+
+        copy_nonoverlapping(x, t, rem);
+        copy_nonoverlapping(y, x, rem);
+        copy_nonoverlapping(t, y, rem);
+    }
+}
+
+/// Moves `src` into the pointed `dst`, returning the previous `dst` value.
+///
+/// Neither value is dropped.
+///
+/// This function is semantically equivalent to [`mem::replace`] except that it
+/// operates on raw pointers instead of references. When references are
+/// available, [`mem::replace`] should be preferred.
+///
+/// [`mem::replace`]: ../mem/fn.replace.html
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `dst` must be [valid] for writes.
+///
+/// * `dst` must be properly aligned.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+///
+/// # Examples
+///
+/// ```
+/// use std::ptr;
+///
+/// let mut rust = vec!['b', 'u', 's', 't'];
+///
+/// // `mem::replace` would have the same effect without requiring the unsafe
+/// // block.
+/// let b = unsafe {
+///     ptr::replace(&mut rust[0], 'r')
+/// };
+///
+/// assert_eq!(b, 'b');
+/// assert_eq!(rust, &['r', 'u', 's', 't']);
+/// ```
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn replace<T>(dst: *mut T, mut src: T) -> T {
+    mem::swap(&mut *dst, &mut src); // cannot overlap
+    src
+}
+
+/// Reads the value from `src` without moving it. This leaves the
+/// memory in `src` unchanged.
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `src` must be [valid] for reads.
+///
+/// * `src` must be properly aligned. Use [`read_unaligned`] if this is not the
+///   case.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// let x = 12;
+/// let y = &x as *const i32;
+///
+/// unsafe {
+///     assert_eq!(std::ptr::read(y), 12);
+/// }
+/// ```
+///
+/// Manually implement [`mem::swap`]:
+///
+/// ```
+/// use std::ptr;
+///
+/// fn swap<T>(a: &mut T, b: &mut T) {
+///     unsafe {
+///         // Create a bitwise copy of the value at `a` in `tmp`.
+///         let tmp = ptr::read(a);
+///
+///         // Exiting at this point (either by explicitly returning or by
+///         // calling a function which panics) would cause the value in `tmp` to
+///         // be dropped while the same value is still referenced by `a`. This
+///         // could trigger undefined behavior if `T` is not `Copy`.
+///
+///         // Create a bitwise copy of the value at `b` in `a`.
+///         // This is safe because mutable references cannot alias.
+///         ptr::copy_nonoverlapping(b, a, 1);
+///
+///         // As above, exiting here could trigger undefined behavior because
+///         // the same value is referenced by `a` and `b`.
+///
+///         // Move `tmp` into `b`.
+///         ptr::write(b, tmp);
+///
+///         // `tmp` has been moved (`write` takes ownership of its second argument),
+///         // so nothing is dropped implicitly here.
+///     }
+/// }
+///
+/// let mut foo = "foo".to_owned();
+/// let mut bar = "bar".to_owned();
+///
+/// swap(&mut foo, &mut bar);
+///
+/// assert_eq!(foo, "bar");
+/// assert_eq!(bar, "foo");
+/// ```
+///
+/// ## Ownership of the Returned Value
+///
+/// `read` creates a bitwise copy of `T`, regardless of whether `T` is [`Copy`].
+/// If `T` is not [`Copy`], using both the returned value and the value at
+/// `*src` can violate memory safety. Note that assigning to `*src` counts as a
+/// use because it will attempt to drop the value at `*src`.
+///
+/// [`write`] can be used to overwrite data without causing it to be dropped.
+///
+/// ```
+/// use std::ptr;
+///
+/// let mut s = String::from("foo");
+/// unsafe {
+///     // `s2` now points to the same underlying memory as `s`.
+///     let mut s2: String = ptr::read(&s);
+///
+///     assert_eq!(s2, "foo");
+///
+///     // Assigning to `s2` causes its original value to be dropped. Beyond
+///     // this point, `s` must no longer be used, as the underlying memory has
+///     // been freed.
+///     s2 = String::default();
+///     assert_eq!(s2, "");
+///
+///     // Assigning to `s` would cause the old value to be dropped again,
+///     // resulting in undefined behavior.
+///     // s = String::from("bar"); // ERROR
+///
+///     // `ptr::write` can be used to overwrite a value without dropping it.
+///     ptr::write(&mut s, String::from("bar"));
+/// }
+///
+/// assert_eq!(s, "bar");
+/// ```
+///
+/// [`mem::swap`]: ../mem/fn.swap.html
+/// [valid]: ../ptr/index.html#safety
+/// [`Copy`]: ../marker/trait.Copy.html
+/// [`read_unaligned`]: ./fn.read_unaligned.html
+/// [`write`]: ./fn.write.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn read<T>(src: *const T) -> T {
+    let mut tmp = MaybeUninit::<T>::uninit();
+    copy_nonoverlapping(src, tmp.as_mut_ptr(), 1);
+    tmp.assume_init()
+}
+
+/// Reads the value from `src` without moving it. This leaves the
+/// memory in `src` unchanged.
+///
+/// Unlike [`read`], `read_unaligned` works with unaligned pointers.
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `src` must be [valid] for reads.
+///
+/// Like [`read`], `read_unaligned` creates a bitwise copy of `T`, regardless of
+/// whether `T` is [`Copy`]. If `T` is not [`Copy`], using both the returned
+/// value and the value at `*src` can [violate memory safety][read-ownership].
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL.
+///
+/// [`Copy`]: ../marker/trait.Copy.html
+/// [`read`]: ./fn.read.html
+/// [`write_unaligned`]: ./fn.write_unaligned.html
+/// [read-ownership]: ./fn.read.html#ownership-of-the-returned-value
+/// [valid]: ../ptr/index.html#safety
+///
+/// # Examples
+///
+/// Access members of a packed struct by reference:
+///
+/// ```
+/// use std::ptr;
+///
+/// #[repr(packed, C)]
+/// struct Packed {
+///     _padding: u8,
+///     unaligned: u32,
+/// }
+///
+/// let x = Packed {
+///     _padding: 0x00,
+///     unaligned: 0x01020304,
+/// };
+///
+/// let v = unsafe {
+///     // Take the address of a 32-bit integer which is not aligned.
+///     // This must be done as a raw pointer; unaligned references are invalid.
+///     let unaligned = &x.unaligned as *const u32;
+///
+///     // Dereferencing normally will emit an aligned load instruction,
+///     // causing undefined behavior.
+///     // let v = *unaligned; // ERROR
+///
+///     // Instead, use `read_unaligned` to read improperly aligned values.
+///     let v = ptr::read_unaligned(unaligned);
+///
+///     v
+/// };
+///
+/// // Accessing unaligned values directly is safe.
+/// assert!(x.unaligned == v);
+/// ```
+#[inline]
+#[stable(feature = "ptr_unaligned", since = "1.17.0")]
+pub unsafe fn read_unaligned<T>(src: *const T) -> T {
+    let mut tmp = MaybeUninit::<T>::uninit();
+    copy_nonoverlapping(src as *const u8,
+                        tmp.as_mut_ptr() as *mut u8,
+                        mem::size_of::<T>());
+    tmp.assume_init()
+}
+
+/// Overwrites a memory location with the given value without reading or
+/// dropping the old value.
+///
+/// `write` does not drop the contents of `dst`. This is safe, but it could leak
+/// allocations or resources, so care should be taken not to overwrite an object
+/// that should be dropped.
+///
+/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
+/// location pointed to by `dst`.
+///
+/// This is appropriate for initializing uninitialized memory, or overwriting
+/// memory that has previously been [`read`] from.
+///
+/// [`read`]: ./fn.read.html
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `dst` must be [valid] for writes.
+///
+/// * `dst` must be properly aligned. Use [`write_unaligned`] if this is not the
+///   case.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+/// [`write_unaligned`]: ./fn.write_unaligned.html
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// let mut x = 0;
+/// let y = &mut x as *mut i32;
+/// let z = 12;
+///
+/// unsafe {
+///     std::ptr::write(y, z);
+///     assert_eq!(std::ptr::read(y), 12);
+/// }
+/// ```
+///
+/// Manually implement [`mem::swap`]:
+///
+/// ```
+/// use std::ptr;
+///
+/// fn swap<T>(a: &mut T, b: &mut T) {
+///     unsafe {
+///         // Create a bitwise copy of the value at `a` in `tmp`.
+///         let tmp = ptr::read(a);
+///
+///         // Exiting at this point (either by explicitly returning or by
+///         // calling a function which panics) would cause the value in `tmp` to
+///         // be dropped while the same value is still referenced by `a`. This
+///         // could trigger undefined behavior if `T` is not `Copy`.
+///
+///         // Create a bitwise copy of the value at `b` in `a`.
+///         // This is safe because mutable references cannot alias.
+///         ptr::copy_nonoverlapping(b, a, 1);
+///
+///         // As above, exiting here could trigger undefined behavior because
+///         // the same value is referenced by `a` and `b`.
+///
+///         // Move `tmp` into `b`.
+///         ptr::write(b, tmp);
+///
+///         // `tmp` has been moved (`write` takes ownership of its second argument),
+///         // so nothing is dropped implicitly here.
+///     }
+/// }
+///
+/// let mut foo = "foo".to_owned();
+/// let mut bar = "bar".to_owned();
+///
+/// swap(&mut foo, &mut bar);
+///
+/// assert_eq!(foo, "bar");
+/// assert_eq!(bar, "foo");
+/// ```
+///
+/// [`mem::swap`]: ../mem/fn.swap.html
+#[inline]
+#[stable(feature = "rust1", since = "1.0.0")]
+pub unsafe fn write<T>(dst: *mut T, src: T) {
+    intrinsics::move_val_init(&mut *dst, src)
+}
+
+/// Overwrites a memory location with the given value without reading or
+/// dropping the old value.
+///
+/// Unlike [`write`], the pointer may be unaligned.
+///
+/// `write_unaligned` does not drop the contents of `dst`. This is safe, but it
+/// could leak allocations or resources, so care should be taken not to overwrite
+/// an object that should be dropped.
+///
+/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
+/// location pointed to by `dst`.
+///
+/// This is appropriate for initializing uninitialized memory, or overwriting
+/// memory that has previously been read with [`read_unaligned`].
+///
+/// [`write`]: ./fn.write.html
+/// [`read_unaligned`]: ./fn.read_unaligned.html
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `dst` must be [valid] for writes.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL.
+///
+/// [valid]: ../ptr/index.html#safety
+///
+/// # Examples
+///
+/// Access fields in a packed struct:
+///
+/// ```
+/// use std::{mem, ptr};
+///
+/// #[repr(packed, C)]
+/// #[derive(Default)]
+/// struct Packed {
+///     _padding: u8,
+///     unaligned: u32,
+/// }
+///
+/// let v = 0x01020304;
+/// let mut x: Packed = unsafe { mem::zeroed() };
+///
+/// unsafe {
+///     // Take a reference to a 32-bit integer which is not aligned.
+///     let unaligned = &mut x.unaligned as *mut u32;
+///
+///     // Dereferencing normally will emit an aligned store instruction,
+///     // causing undefined behavior because the pointer is not aligned.
+///     // *unaligned = v; // ERROR
+///
+///     // Instead, use `write_unaligned` to write improperly aligned values.
+///     ptr::write_unaligned(unaligned, v);
+/// }
+///
+/// // Accessing unaligned values directly is safe.
+/// assert!(x.unaligned == v);
+/// ```
+#[inline]
+#[stable(feature = "ptr_unaligned", since = "1.17.0")]
+pub unsafe fn write_unaligned<T>(dst: *mut T, src: T) {
+    copy_nonoverlapping(&src as *const T as *const u8,
+                        dst as *mut u8,
+                        mem::size_of::<T>());
+    mem::forget(src);
+}
+
+/// Performs a volatile read of the value from `src` without moving it. This
+/// leaves the memory in `src` unchanged.
+///
+/// Volatile operations are intended to act on I/O memory, and are guaranteed
+/// to not be elided or reordered by the compiler across other volatile
+/// operations.
+///
+/// [`write_volatile`]: ./fn.write_volatile.html
+///
+/// # Notes
+///
+/// Rust does not currently have a rigorously and formally defined memory model,
+/// so the precise semantics of what "volatile" means here is subject to change
+/// over time. That being said, the semantics will almost always end up pretty
+/// similar to [C11's definition of volatile][c11].
+///
+/// The compiler shouldn't change the relative order or number of volatile
+/// memory operations. However, volatile memory operations on zero-sized types
+/// (e.g., if a zero-sized type is passed to `read_volatile`) are noops
+/// and may be ignored.
+///
+/// [c11]: http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `src` must be [valid] for reads.
+///
+/// * `src` must be properly aligned.
+///
+/// Like [`read`], `read_volatile` creates a bitwise copy of `T`, regardless of
+/// whether `T` is [`Copy`]. If `T` is not [`Copy`], using both the returned
+/// value and the value at `*src` can [violate memory safety][read-ownership].
+/// However, storing non-[`Copy`] types in volatile memory is almost certainly
+/// incorrect.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+/// [`Copy`]: ../marker/trait.Copy.html
+/// [`read`]: ./fn.read.html
+/// [read-ownership]: ./fn.read.html#ownership-of-the-returned-value
+///
+/// Just like in C, whether an operation is volatile has no bearing whatsoever
+/// on questions involving concurrent access from multiple threads. Volatile
+/// accesses behave exactly like non-atomic accesses in that regard. In particular,
+/// a race between a `read_volatile` and any write operation to the same location
+/// is undefined behavior.
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// let x = 12;
+/// let y = &x as *const i32;
+///
+/// unsafe {
+///     assert_eq!(std::ptr::read_volatile(y), 12);
+/// }
+/// ```
+#[inline]
+#[stable(feature = "volatile", since = "1.9.0")]
+pub unsafe fn read_volatile<T>(src: *const T) -> T {
+    intrinsics::volatile_load(src)
+}
+
+/// Performs a volatile write of a memory location with the given value without
+/// reading or dropping the old value.
+///
+/// Volatile operations are intended to act on I/O memory, and are guaranteed
+/// to not be elided or reordered by the compiler across other volatile
+/// operations.
+///
+/// `write_volatile` does not drop the contents of `dst`. This is safe, but it
+/// could leak allocations or resources, so care should be taken not to overwrite
+/// an object that should be dropped.
+///
+/// Additionally, it does not drop `src`. Semantically, `src` is moved into the
+/// location pointed to by `dst`.
+///
+/// [`read_volatile`]: ./fn.read_volatile.html
+///
+/// # Notes
+///
+/// Rust does not currently have a rigorously and formally defined memory model,
+/// so the precise semantics of what "volatile" means here is subject to change
+/// over time. That being said, the semantics will almost always end up pretty
+/// similar to [C11's definition of volatile][c11].
+///
+/// The compiler shouldn't change the relative order or number of volatile
+/// memory operations. However, volatile memory operations on zero-sized types
+/// (e.g., if a zero-sized type is passed to `write_volatile`) are noops
+/// and may be ignored.
+///
+/// [c11]: http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf
+///
+/// # Safety
+///
+/// Behavior is undefined if any of the following conditions are violated:
+///
+/// * `dst` must be [valid] for writes.
+///
+/// * `dst` must be properly aligned.
+///
+/// Note that even if `T` has size `0`, the pointer must be non-NULL and properly aligned.
+///
+/// [valid]: ../ptr/index.html#safety
+///
+/// Just like in C, whether an operation is volatile has no bearing whatsoever
+/// on questions involving concurrent access from multiple threads. Volatile
+/// accesses behave exactly like non-atomic accesses in that regard. In particular,
+/// a race between a `write_volatile` and any other operation (reading or writing)
+/// on the same location is undefined behavior.
+///
+/// # Examples
+///
+/// Basic usage:
+///
+/// ```
+/// let mut x = 0;
+/// let y = &mut x as *mut i32;
+/// let z = 12;
+///
+/// unsafe {
+///     std::ptr::write_volatile(y, z);
+///     assert_eq!(std::ptr::read_volatile(y), 12);
+/// }
+/// ```
+#[inline]
+#[stable(feature = "volatile", since = "1.9.0")]
+pub unsafe fn write_volatile<T>(dst: *mut T, src: T) {
+    intrinsics::volatile_store(dst, src);
+}
+
+#[lang = "const_ptr"]
+impl<T: ?Sized> *const T {
+    /// Returns `true` if the pointer is null.
+    ///
+    /// Note that unsized types have many possible null pointers, as only the
+    /// raw data pointer is considered, not their length, vtable, etc.
+    /// Therefore, two pointers that are null may still not compare equal to
+    /// each other.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "Follow the rabbit";
+    /// let ptr: *const u8 = s.as_ptr();
+    /// assert!(!ptr.is_null());
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    #[inline]
+    pub fn is_null(self) -> bool {
+        // Compare via a cast to a thin pointer, so fat pointers are only
+        // considering their "data" part for null-ness.
+        (self as *const u8) == null()
+    }
+
+    /// Cast to a pointer to a different type
+    #[unstable(feature = "ptr_cast", issue = "60602")]
+    #[inline]
+    pub const fn cast<U>(self) -> *const U {
+        self as _
+    }
+
+    /// Returns `None` if the pointer is null, or else returns a reference to
+    /// the value wrapped in `Some`.
+    ///
+    /// # Safety
+    ///
+    /// While this method and its mutable counterpart are useful for
+    /// null-safety, it is important to note that this is still an unsafe
+    /// operation because the returned value could be pointing to invalid
+    /// memory.
+    ///
+    /// Additionally, the lifetime `'a` returned is arbitrarily chosen and does
+    /// not necessarily reflect the actual lifetime of the data.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let ptr: *const u8 = &10u8 as *const u8;
+    ///
+    /// unsafe {
+    ///     if let Some(val_back) = ptr.as_ref() {
+    ///         println!("We got back the value: {}!", val_back);
+    ///     }
+    /// }
+    /// ```
+    ///
+    /// # Null-unchecked version
+    ///
+    /// If you are sure the pointer can never be null and are looking for some kind of
+    /// `as_ref_unchecked` that returns the `&T` instead of `Option<&T>`, know that you can
+    /// dereference the pointer directly.
+    ///
+    /// ```
+    /// let ptr: *const u8 = &10u8 as *const u8;
+    ///
+    /// unsafe {
+    ///     let val_back = &*ptr;
+    ///     println!("We got back the value: {}!", val_back);
+    /// }
+    /// ```
+    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
+    #[inline]
+    pub unsafe fn as_ref<'a>(self) -> Option<&'a T> {
+        if self.is_null() {
+            None
+        } else {
+            Some(&*self)
+        }
+    }
+
+    /// Calculates the offset from a pointer.
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum, **in bytes** must fit in a usize.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "123";
+    /// let ptr: *const u8 = s.as_ptr();
+    ///
+    /// unsafe {
+    ///     println!("{}", *ptr.offset(1) as char);
+    ///     println!("{}", *ptr.offset(2) as char);
+    /// }
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    #[inline]
+    pub unsafe fn offset(self, count: isize) -> *const T where T: Sized {
+        intrinsics::offset(self, count)
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    /// In particular, the resulting pointer may *not* be used to access a
+    /// different allocated object than the one `self` points to. In other
+    /// words, `x.wrapping_offset(y.wrapping_offset_from(x))` is
+    /// *not* the same as `y`, and dereferencing it is undefined behavior
+    /// unless `x` and `y` point into the same allocated object.
+    ///
+    /// Always use `.offset(count)` instead when possible, because `offset`
+    /// allows the compiler to optimize better. If you need to cross object
+    /// boundaries, cast the pointer to an integer and do the arithmetic there.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements
+    /// let data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *const u8 = data.as_ptr();
+    /// let step = 2;
+    /// let end_rounded_up = ptr.wrapping_offset(6);
+    ///
+    /// // This loop prints "1, 3, 5, "
+    /// while ptr != end_rounded_up {
+    ///     unsafe {
+    ///         print!("{}, ", *ptr);
+    ///     }
+    ///     ptr = ptr.wrapping_offset(step);
+    /// }
+    /// ```
+    #[stable(feature = "ptr_wrapping_offset", since = "1.16.0")]
+    #[inline]
+    pub fn wrapping_offset(self, count: isize) -> *const T where T: Sized {
+        unsafe {
+            intrinsics::arith_offset(self, count)
+        }
+    }
+
+    /// Calculates the distance between two pointers. The returned value is in
+    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
+    ///
+    /// This function is the inverse of [`offset`].
+    ///
+    /// [`offset`]: #method.offset
+    /// [`wrapping_offset_from`]: #method.wrapping_offset_from
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and other pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The distance between the pointers, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The distance between the pointers, in bytes, must be an exact multiple
+    ///   of the size of `T`.
+    ///
+    /// * The distance being in bounds cannot rely on "wrapping around" the address space.
+    ///
+    /// The compiler and standard library generally try to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `ptr_into_vec.offset_from(vec.as_ptr())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using [`wrapping_offset_from`] instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Panics
+    ///
+    /// This function panics if `T` is a Zero-Sized Type ("ZST").
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// #![feature(ptr_offset_from)]
+    ///
+    /// let a = [0; 5];
+    /// let ptr1: *const i32 = &a[1];
+    /// let ptr2: *const i32 = &a[3];
+    /// unsafe {
+    ///     assert_eq!(ptr2.offset_from(ptr1), 2);
+    ///     assert_eq!(ptr1.offset_from(ptr2), -2);
+    ///     assert_eq!(ptr1.offset(2), ptr2);
+    ///     assert_eq!(ptr2.offset(-2), ptr1);
+    /// }
+    /// ```
+    #[unstable(feature = "ptr_offset_from", issue = "41079")]
+    #[inline]
+    pub unsafe fn offset_from(self, origin: *const T) -> isize where T: Sized {
+        let pointee_size = mem::size_of::<T>();
+        assert!(0 < pointee_size && pointee_size <= isize::max_value() as usize);
+
+        // This is the same sequence that Clang emits for pointer subtraction.
+        // It can be neither `nsw` nor `nuw` because the input is treated as
+        // unsigned but then the output is treated as signed, so neither works.
+        let d = isize::wrapping_sub(self as _, origin as _);
+        intrinsics::exact_div(d, pointee_size as _)
+    }
+
+    /// Calculates the distance between two pointers. The returned value is in
+    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
+    ///
+    /// If the address different between the two pointers is not a multiple of
+    /// `mem::size_of::<T>()` then the result of the division is rounded towards
+    /// zero.
+    ///
+    /// Though this method is safe for any two pointers, note that its result
+    /// will be mostly useless if the two pointers aren't into the same allocated
+    /// object, for example if they point to two different local variables.
+    ///
+    /// # Panics
+    ///
+    /// This function panics if `T` is a zero-sized type.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// #![feature(ptr_wrapping_offset_from)]
+    ///
+    /// let a = [0; 5];
+    /// let ptr1: *const i32 = &a[1];
+    /// let ptr2: *const i32 = &a[3];
+    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
+    /// assert_eq!(ptr1.wrapping_offset_from(ptr2), -2);
+    /// assert_eq!(ptr1.wrapping_offset(2), ptr2);
+    /// assert_eq!(ptr2.wrapping_offset(-2), ptr1);
+    ///
+    /// let ptr1: *const i32 = 3 as _;
+    /// let ptr2: *const i32 = 13 as _;
+    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
+    /// ```
+    #[unstable(feature = "ptr_wrapping_offset_from", issue = "41079")]
+    #[inline]
+    pub fn wrapping_offset_from(self, origin: *const T) -> isize where T: Sized {
+        let pointee_size = mem::size_of::<T>();
+        assert!(0 < pointee_size && pointee_size <= isize::max_value() as usize);
+
+        let d = isize::wrapping_sub(self as _, origin as _);
+        d.wrapping_div(pointee_size as _)
+    }
+
+    /// Calculates the offset from a pointer (convenience for `.offset(count as isize)`).
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum must fit in a `usize`.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "123";
+    /// let ptr: *const u8 = s.as_ptr();
+    ///
+    /// unsafe {
+    ///     println!("{}", *ptr.add(1) as char);
+    ///     println!("{}", *ptr.add(2) as char);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn add(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.offset(count as isize)
+    }
+
+    /// Calculates the offset from a pointer (convenience for
+    /// `.offset((count as isize).wrapping_neg())`).
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset cannot exceed `isize::MAX` **bytes**.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum must fit in a usize.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len()).sub(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "123";
+    ///
+    /// unsafe {
+    ///     let end: *const u8 = s.as_ptr().add(3);
+    ///     println!("{}", *end.sub(1) as char);
+    ///     println!("{}", *end.sub(2) as char);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn sub(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.offset((count as isize).wrapping_neg())
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    /// (convenience for `.wrapping_offset(count as isize)`)
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    ///
+    /// Always use `.add(count)` instead when possible, because `add`
+    /// allows the compiler to optimize better.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements
+    /// let data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *const u8 = data.as_ptr();
+    /// let step = 2;
+    /// let end_rounded_up = ptr.wrapping_add(6);
+    ///
+    /// // This loop prints "1, 3, 5, "
+    /// while ptr != end_rounded_up {
+    ///     unsafe {
+    ///         print!("{}, ", *ptr);
+    ///     }
+    ///     ptr = ptr.wrapping_add(step);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub fn wrapping_add(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.wrapping_offset(count as isize)
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    /// (convenience for `.wrapping_offset((count as isize).wrapping_sub())`)
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    ///
+    /// Always use `.sub(count)` instead when possible, because `sub`
+    /// allows the compiler to optimize better.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements (backwards)
+    /// let data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *const u8 = data.as_ptr();
+    /// let start_rounded_down = ptr.wrapping_sub(2);
+    /// ptr = ptr.wrapping_add(4);
+    /// let step = 2;
+    /// // This loop prints "5, 3, 1, "
+    /// while ptr != start_rounded_down {
+    ///     unsafe {
+    ///         print!("{}, ", *ptr);
+    ///     }
+    ///     ptr = ptr.wrapping_sub(step);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub fn wrapping_sub(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.wrapping_offset((count as isize).wrapping_neg())
+    }
+
+    /// Reads the value from `self` without moving it. This leaves the
+    /// memory in `self` unchanged.
+    ///
+    /// See [`ptr::read`] for safety concerns and examples.
+    ///
+    /// [`ptr::read`]: ./ptr/fn.read.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read(self) -> T
+        where T: Sized,
+    {
+        read(self)
+    }
+
+    /// Performs a volatile read of the value from `self` without moving it. This
+    /// leaves the memory in `self` unchanged.
+    ///
+    /// Volatile operations are intended to act on I/O memory, and are guaranteed
+    /// to not be elided or reordered by the compiler across other volatile
+    /// operations.
+    ///
+    /// See [`ptr::read_volatile`] for safety concerns and examples.
+    ///
+    /// [`ptr::read_volatile`]: ./ptr/fn.read_volatile.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read_volatile(self) -> T
+        where T: Sized,
+    {
+        read_volatile(self)
+    }
+
+    /// Reads the value from `self` without moving it. This leaves the
+    /// memory in `self` unchanged.
+    ///
+    /// Unlike `read`, the pointer may be unaligned.
+    ///
+    /// See [`ptr::read_unaligned`] for safety concerns and examples.
+    ///
+    /// [`ptr::read_unaligned`]: ./ptr/fn.read_unaligned.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read_unaligned(self) -> T
+        where T: Sized,
+    {
+        read_unaligned(self)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
+    /// and destination may overlap.
+    ///
+    /// NOTE: this has the *same* argument order as [`ptr::copy`].
+    ///
+    /// See [`ptr::copy`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy`]: ./ptr/fn.copy.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_to(self, dest: *mut T, count: usize)
+        where T: Sized,
+    {
+        copy(self, dest, count)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
+    /// and destination may *not* overlap.
+    ///
+    /// NOTE: this has the *same* argument order as [`ptr::copy_nonoverlapping`].
+    ///
+    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_to_nonoverlapping(self, dest: *mut T, count: usize)
+        where T: Sized,
+    {
+        copy_nonoverlapping(self, dest, count)
+    }
+
+    /// Computes the offset that needs to be applied to the pointer in order to make it aligned to
+    /// `align`.
+    ///
+    /// If it is not possible to align the pointer, the implementation returns
+    /// `usize::max_value()`.
+    ///
+    /// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
+    /// used with the `offset` or `offset_to` methods.
+    ///
+    /// There are no guarantees whatsover that offsetting the pointer will not overflow or go
+    /// beyond the allocation that the pointer points into. It is up to the caller to ensure that
+    /// the returned offset is correct in all terms other than alignment.
+    ///
+    /// # Panics
+    ///
+    /// The function panics if `align` is not a power-of-two.
+    ///
+    /// # Examples
+    ///
+    /// Accessing adjacent `u8` as `u16`
+    ///
+    /// ```
+    /// # fn foo(n: usize) {
+    /// # use std::mem::align_of;
+    /// # unsafe {
+    /// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
+    /// let ptr = &x[n] as *const u8;
+    /// let offset = ptr.align_offset(align_of::<u16>());
+    /// if offset < x.len() - n - 1 {
+    ///     let u16_ptr = ptr.add(offset) as *const u16;
+    ///     assert_ne!(*u16_ptr, 500);
+    /// } else {
+    ///     // while the pointer can be aligned via `offset`, it would point
+    ///     // outside the allocation
+    /// }
+    /// # } }
+    /// ```
+    #[stable(feature = "align_offset", since = "1.36.0")]
+    pub fn align_offset(self, align: usize) -> usize where T: Sized {
+        if !align.is_power_of_two() {
+            panic!("align_offset: align is not a power-of-two");
+        }
+        unsafe {
+            align_offset(self, align)
+        }
+    }
+}
+
+
+#[lang = "mut_ptr"]
+impl<T: ?Sized> *mut T {
+    /// Returns `true` if the pointer is null.
+    ///
+    /// Note that unsized types have many possible null pointers, as only the
+    /// raw data pointer is considered, not their length, vtable, etc.
+    /// Therefore, two pointers that are null may still not compare equal to
+    /// each other.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let mut s = [1, 2, 3];
+    /// let ptr: *mut u32 = s.as_mut_ptr();
+    /// assert!(!ptr.is_null());
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    #[inline]
+    pub fn is_null(self) -> bool {
+        // Compare via a cast to a thin pointer, so fat pointers are only
+        // considering their "data" part for null-ness.
+        (self as *mut u8) == null_mut()
+    }
+
+    /// Cast to a pointer to a different type
+    #[unstable(feature = "ptr_cast", issue = "60602")]
+    #[inline]
+    pub const fn cast<U>(self) -> *mut U {
+        self as _
+    }
+
+    /// Returns `None` if the pointer is null, or else returns a reference to
+    /// the value wrapped in `Some`.
+    ///
+    /// # Safety
+    ///
+    /// While this method and its mutable counterpart are useful for
+    /// null-safety, it is important to note that this is still an unsafe
+    /// operation because the returned value could be pointing to invalid
+    /// memory.
+    ///
+    /// Additionally, the lifetime `'a` returned is arbitrarily chosen and does
+    /// not necessarily reflect the actual lifetime of the data.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let ptr: *mut u8 = &mut 10u8 as *mut u8;
+    ///
+    /// unsafe {
+    ///     if let Some(val_back) = ptr.as_ref() {
+    ///         println!("We got back the value: {}!", val_back);
+    ///     }
+    /// }
+    /// ```
+    ///
+    /// # Null-unchecked version
+    ///
+    /// If you are sure the pointer can never be null and are looking for some kind of
+    /// `as_ref_unchecked` that returns the `&T` instead of `Option<&T>`, know that you can
+    /// dereference the pointer directly.
+    ///
+    /// ```
+    /// let ptr: *mut u8 = &mut 10u8 as *mut u8;
+    ///
+    /// unsafe {
+    ///     let val_back = &*ptr;
+    ///     println!("We got back the value: {}!", val_back);
+    /// }
+    /// ```
+    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
+    #[inline]
+    pub unsafe fn as_ref<'a>(self) -> Option<&'a T> {
+        if self.is_null() {
+            None
+        } else {
+            Some(&*self)
+        }
+    }
+
+    /// Calculates the offset from a pointer.
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum, **in bytes** must fit in a usize.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let mut s = [1, 2, 3];
+    /// let ptr: *mut u32 = s.as_mut_ptr();
+    ///
+    /// unsafe {
+    ///     println!("{}", *ptr.offset(1));
+    ///     println!("{}", *ptr.offset(2));
+    /// }
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    #[inline]
+    pub unsafe fn offset(self, count: isize) -> *mut T where T: Sized {
+        intrinsics::offset(self, count) as *mut T
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    /// In particular, the resulting pointer may *not* be used to access a
+    /// different allocated object than the one `self` points to. In other
+    /// words, `x.wrapping_offset(y.wrapping_offset_from(x))` is
+    /// *not* the same as `y`, and dereferencing it is undefined behavior
+    /// unless `x` and `y` point into the same allocated object.
+    ///
+    /// Always use `.offset(count)` instead when possible, because `offset`
+    /// allows the compiler to optimize better. If you need to cross object
+    /// boundaries, cast the pointer to an integer and do the arithmetic there.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements
+    /// let mut data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *mut u8 = data.as_mut_ptr();
+    /// let step = 2;
+    /// let end_rounded_up = ptr.wrapping_offset(6);
+    ///
+    /// while ptr != end_rounded_up {
+    ///     unsafe {
+    ///         *ptr = 0;
+    ///     }
+    ///     ptr = ptr.wrapping_offset(step);
+    /// }
+    /// assert_eq!(&data, &[0, 2, 0, 4, 0]);
+    /// ```
+    #[stable(feature = "ptr_wrapping_offset", since = "1.16.0")]
+    #[inline]
+    pub fn wrapping_offset(self, count: isize) -> *mut T where T: Sized {
+        unsafe {
+            intrinsics::arith_offset(self, count) as *mut T
+        }
+    }
+
+    /// Returns `None` if the pointer is null, or else returns a mutable
+    /// reference to the value wrapped in `Some`.
+    ///
+    /// # Safety
+    ///
+    /// As with `as_ref`, this is unsafe because it cannot verify the validity
+    /// of the returned pointer, nor can it ensure that the lifetime `'a`
+    /// returned is indeed a valid lifetime for the contained data.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let mut s = [1, 2, 3];
+    /// let ptr: *mut u32 = s.as_mut_ptr();
+    /// let first_value = unsafe { ptr.as_mut().unwrap() };
+    /// *first_value = 4;
+    /// println!("{:?}", s); // It'll print: "[4, 2, 3]".
+    /// ```
+    #[stable(feature = "ptr_as_ref", since = "1.9.0")]
+    #[inline]
+    pub unsafe fn as_mut<'a>(self) -> Option<&'a mut T> {
+        if self.is_null() {
+            None
+        } else {
+            Some(&mut *self)
+        }
+    }
+
+    /// Calculates the distance between two pointers. The returned value is in
+    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
+    ///
+    /// This function is the inverse of [`offset`].
+    ///
+    /// [`offset`]: #method.offset-1
+    /// [`wrapping_offset_from`]: #method.wrapping_offset_from-1
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and other pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The distance between the pointers, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The distance between the pointers, in bytes, must be an exact multiple
+    ///   of the size of `T`.
+    ///
+    /// * The distance being in bounds cannot rely on "wrapping around" the address space.
+    ///
+    /// The compiler and standard library generally try to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `ptr_into_vec.offset_from(vec.as_ptr())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using [`wrapping_offset_from`] instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Panics
+    ///
+    /// This function panics if `T` is a Zero-Sized Type ("ZST").
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// #![feature(ptr_offset_from)]
+    ///
+    /// let mut a = [0; 5];
+    /// let ptr1: *mut i32 = &mut a[1];
+    /// let ptr2: *mut i32 = &mut a[3];
+    /// unsafe {
+    ///     assert_eq!(ptr2.offset_from(ptr1), 2);
+    ///     assert_eq!(ptr1.offset_from(ptr2), -2);
+    ///     assert_eq!(ptr1.offset(2), ptr2);
+    ///     assert_eq!(ptr2.offset(-2), ptr1);
+    /// }
+    /// ```
+    #[unstable(feature = "ptr_offset_from", issue = "41079")]
+    #[inline]
+    pub unsafe fn offset_from(self, origin: *const T) -> isize where T: Sized {
+        (self as *const T).offset_from(origin)
+    }
+
+    /// Calculates the distance between two pointers. The returned value is in
+    /// units of T: the distance in bytes is divided by `mem::size_of::<T>()`.
+    ///
+    /// If the address different between the two pointers is not a multiple of
+    /// `mem::size_of::<T>()` then the result of the division is rounded towards
+    /// zero.
+    ///
+    /// Though this method is safe for any two pointers, note that its result
+    /// will be mostly useless if the two pointers aren't into the same allocated
+    /// object, for example if they point to two different local variables.
+    ///
+    /// # Panics
+    ///
+    /// This function panics if `T` is a zero-sized type.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// #![feature(ptr_wrapping_offset_from)]
+    ///
+    /// let mut a = [0; 5];
+    /// let ptr1: *mut i32 = &mut a[1];
+    /// let ptr2: *mut i32 = &mut a[3];
+    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
+    /// assert_eq!(ptr1.wrapping_offset_from(ptr2), -2);
+    /// assert_eq!(ptr1.wrapping_offset(2), ptr2);
+    /// assert_eq!(ptr2.wrapping_offset(-2), ptr1);
+    ///
+    /// let ptr1: *mut i32 = 3 as _;
+    /// let ptr2: *mut i32 = 13 as _;
+    /// assert_eq!(ptr2.wrapping_offset_from(ptr1), 2);
+    /// ```
+    #[unstable(feature = "ptr_wrapping_offset_from", issue = "41079")]
+    #[inline]
+    pub fn wrapping_offset_from(self, origin: *const T) -> isize where T: Sized {
+        (self as *const T).wrapping_offset_from(origin)
+    }
+
+    /// Calculates the offset from a pointer (convenience for `.offset(count as isize)`).
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset, **in bytes**, cannot overflow an `isize`.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum must fit in a `usize`.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "123";
+    /// let ptr: *const u8 = s.as_ptr();
+    ///
+    /// unsafe {
+    ///     println!("{}", *ptr.add(1) as char);
+    ///     println!("{}", *ptr.add(2) as char);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn add(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.offset(count as isize)
+    }
+
+    /// Calculates the offset from a pointer (convenience for
+    /// `.offset((count as isize).wrapping_neg())`).
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// If any of the following conditions are violated, the result is Undefined
+    /// Behavior:
+    ///
+    /// * Both the starting and resulting pointer must be either in bounds or one
+    ///   byte past the end of the same allocated object.
+    ///
+    /// * The computed offset cannot exceed `isize::MAX` **bytes**.
+    ///
+    /// * The offset being in bounds cannot rely on "wrapping around" the address
+    ///   space. That is, the infinite-precision sum must fit in a usize.
+    ///
+    /// The compiler and standard library generally tries to ensure allocations
+    /// never reach a size where an offset is a concern. For instance, `Vec`
+    /// and `Box` ensure they never allocate more than `isize::MAX` bytes, so
+    /// `vec.as_ptr().add(vec.len()).sub(vec.len())` is always safe.
+    ///
+    /// Most platforms fundamentally can't even construct such an allocation.
+    /// For instance, no known 64-bit platform can ever serve a request
+    /// for 2<sup>63</sup> bytes due to page-table limitations or splitting the address space.
+    /// However, some 32-bit and 16-bit platforms may successfully serve a request for
+    /// more than `isize::MAX` bytes with things like Physical Address
+    /// Extension. As such, memory acquired directly from allocators or memory
+    /// mapped files *may* be too large to handle with this function.
+    ///
+    /// Consider using `wrapping_offset` instead if these constraints are
+    /// difficult to satisfy. The only advantage of this method is that it
+    /// enables more aggressive compiler optimizations.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// let s: &str = "123";
+    ///
+    /// unsafe {
+    ///     let end: *const u8 = s.as_ptr().add(3);
+    ///     println!("{}", *end.sub(1) as char);
+    ///     println!("{}", *end.sub(2) as char);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn sub(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.offset((count as isize).wrapping_neg())
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    /// (convenience for `.wrapping_offset(count as isize)`)
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    ///
+    /// Always use `.add(count)` instead when possible, because `add`
+    /// allows the compiler to optimize better.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements
+    /// let data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *const u8 = data.as_ptr();
+    /// let step = 2;
+    /// let end_rounded_up = ptr.wrapping_add(6);
+    ///
+    /// // This loop prints "1, 3, 5, "
+    /// while ptr != end_rounded_up {
+    ///     unsafe {
+    ///         print!("{}, ", *ptr);
+    ///     }
+    ///     ptr = ptr.wrapping_add(step);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub fn wrapping_add(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.wrapping_offset(count as isize)
+    }
+
+    /// Calculates the offset from a pointer using wrapping arithmetic.
+    /// (convenience for `.wrapping_offset((count as isize).wrapping_sub())`)
+    ///
+    /// `count` is in units of T; e.g., a `count` of 3 represents a pointer
+    /// offset of `3 * size_of::<T>()` bytes.
+    ///
+    /// # Safety
+    ///
+    /// The resulting pointer does not need to be in bounds, but it is
+    /// potentially hazardous to dereference (which requires `unsafe`).
+    ///
+    /// Always use `.sub(count)` instead when possible, because `sub`
+    /// allows the compiler to optimize better.
+    ///
+    /// # Examples
+    ///
+    /// Basic usage:
+    ///
+    /// ```
+    /// // Iterate using a raw pointer in increments of two elements (backwards)
+    /// let data = [1u8, 2, 3, 4, 5];
+    /// let mut ptr: *const u8 = data.as_ptr();
+    /// let start_rounded_down = ptr.wrapping_sub(2);
+    /// ptr = ptr.wrapping_add(4);
+    /// let step = 2;
+    /// // This loop prints "5, 3, 1, "
+    /// while ptr != start_rounded_down {
+    ///     unsafe {
+    ///         print!("{}, ", *ptr);
+    ///     }
+    ///     ptr = ptr.wrapping_sub(step);
+    /// }
+    /// ```
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub fn wrapping_sub(self, count: usize) -> Self
+        where T: Sized,
+    {
+        self.wrapping_offset((count as isize).wrapping_neg())
+    }
+
+    /// Reads the value from `self` without moving it. This leaves the
+    /// memory in `self` unchanged.
+    ///
+    /// See [`ptr::read`] for safety concerns and examples.
+    ///
+    /// [`ptr::read`]: ./ptr/fn.read.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read(self) -> T
+        where T: Sized,
+    {
+        read(self)
+    }
+
+    /// Performs a volatile read of the value from `self` without moving it. This
+    /// leaves the memory in `self` unchanged.
+    ///
+    /// Volatile operations are intended to act on I/O memory, and are guaranteed
+    /// to not be elided or reordered by the compiler across other volatile
+    /// operations.
+    ///
+    /// See [`ptr::read_volatile`] for safety concerns and examples.
+    ///
+    /// [`ptr::read_volatile`]: ./ptr/fn.read_volatile.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read_volatile(self) -> T
+        where T: Sized,
+    {
+        read_volatile(self)
+    }
+
+    /// Reads the value from `self` without moving it. This leaves the
+    /// memory in `self` unchanged.
+    ///
+    /// Unlike `read`, the pointer may be unaligned.
+    ///
+    /// See [`ptr::read_unaligned`] for safety concerns and examples.
+    ///
+    /// [`ptr::read_unaligned`]: ./ptr/fn.read_unaligned.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn read_unaligned(self) -> T
+        where T: Sized,
+    {
+        read_unaligned(self)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
+    /// and destination may overlap.
+    ///
+    /// NOTE: this has the *same* argument order as [`ptr::copy`].
+    ///
+    /// See [`ptr::copy`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy`]: ./ptr/fn.copy.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_to(self, dest: *mut T, count: usize)
+        where T: Sized,
+    {
+        copy(self, dest, count)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `self` to `dest`. The source
+    /// and destination may *not* overlap.
+    ///
+    /// NOTE: this has the *same* argument order as [`ptr::copy_nonoverlapping`].
+    ///
+    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_to_nonoverlapping(self, dest: *mut T, count: usize)
+        where T: Sized,
+    {
+        copy_nonoverlapping(self, dest, count)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `src` to `self`. The source
+    /// and destination may overlap.
+    ///
+    /// NOTE: this has the *opposite* argument order of [`ptr::copy`].
+    ///
+    /// See [`ptr::copy`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy`]: ./ptr/fn.copy.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_from(self, src: *const T, count: usize)
+        where T: Sized,
+    {
+        copy(src, self, count)
+    }
+
+    /// Copies `count * size_of<T>` bytes from `src` to `self`. The source
+    /// and destination may *not* overlap.
+    ///
+    /// NOTE: this has the *opposite* argument order of [`ptr::copy_nonoverlapping`].
+    ///
+    /// See [`ptr::copy_nonoverlapping`] for safety concerns and examples.
+    ///
+    /// [`ptr::copy_nonoverlapping`]: ./ptr/fn.copy_nonoverlapping.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn copy_from_nonoverlapping(self, src: *const T, count: usize)
+        where T: Sized,
+    {
+        copy_nonoverlapping(src, self, count)
+    }
+
+    /// Executes the destructor (if any) of the pointed-to value.
+    ///
+    /// See [`ptr::drop_in_place`] for safety concerns and examples.
+    ///
+    /// [`ptr::drop_in_place`]: ./ptr/fn.drop_in_place.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn drop_in_place(self) {
+        drop_in_place(self)
+    }
+
+    /// Overwrites a memory location with the given value without reading or
+    /// dropping the old value.
+    ///
+    /// See [`ptr::write`] for safety concerns and examples.
+    ///
+    /// [`ptr::write`]: ./ptr/fn.write.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn write(self, val: T)
+        where T: Sized,
+    {
+        write(self, val)
+    }
+
+    /// Invokes memset on the specified pointer, setting `count * size_of::<T>()`
+    /// bytes of memory starting at `self` to `val`.
+    ///
+    /// See [`ptr::write_bytes`] for safety concerns and examples.
+    ///
+    /// [`ptr::write_bytes`]: ./ptr/fn.write_bytes.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn write_bytes(self, val: u8, count: usize)
+        where T: Sized,
+    {
+        write_bytes(self, val, count)
+    }
+
+    /// Performs a volatile write of a memory location with the given value without
+    /// reading or dropping the old value.
+    ///
+    /// Volatile operations are intended to act on I/O memory, and are guaranteed
+    /// to not be elided or reordered by the compiler across other volatile
+    /// operations.
+    ///
+    /// See [`ptr::write_volatile`] for safety concerns and examples.
+    ///
+    /// [`ptr::write_volatile`]: ./ptr/fn.write_volatile.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn write_volatile(self, val: T)
+        where T: Sized,
+    {
+        write_volatile(self, val)
+    }
+
+    /// Overwrites a memory location with the given value without reading or
+    /// dropping the old value.
+    ///
+    /// Unlike `write`, the pointer may be unaligned.
+    ///
+    /// See [`ptr::write_unaligned`] for safety concerns and examples.
+    ///
+    /// [`ptr::write_unaligned`]: ./ptr/fn.write_unaligned.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn write_unaligned(self, val: T)
+        where T: Sized,
+    {
+        write_unaligned(self, val)
+    }
+
+    /// Replaces the value at `self` with `src`, returning the old
+    /// value, without dropping either.
+    ///
+    /// See [`ptr::replace`] for safety concerns and examples.
+    ///
+    /// [`ptr::replace`]: ./ptr/fn.replace.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn replace(self, src: T) -> T
+        where T: Sized,
+    {
+        replace(self, src)
+    }
+
+    /// Swaps the values at two mutable locations of the same type, without
+    /// deinitializing either. They may overlap, unlike `mem::swap` which is
+    /// otherwise equivalent.
+    ///
+    /// See [`ptr::swap`] for safety concerns and examples.
+    ///
+    /// [`ptr::swap`]: ./ptr/fn.swap.html
+    #[stable(feature = "pointer_methods", since = "1.26.0")]
+    #[inline]
+    pub unsafe fn swap(self, with: *mut T)
+        where T: Sized,
+    {
+        swap(self, with)
+    }
+
+    /// Computes the offset that needs to be applied to the pointer in order to make it aligned to
+    /// `align`.
+    ///
+    /// If it is not possible to align the pointer, the implementation returns
+    /// `usize::max_value()`.
+    ///
+    /// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
+    /// used with the `offset` or `offset_to` methods.
+    ///
+    /// There are no guarantees whatsover that offsetting the pointer will not overflow or go
+    /// beyond the allocation that the pointer points into. It is up to the caller to ensure that
+    /// the returned offset is correct in all terms other than alignment.
+    ///
+    /// # Panics
+    ///
+    /// The function panics if `align` is not a power-of-two.
+    ///
+    /// # Examples
+    ///
+    /// Accessing adjacent `u8` as `u16`
+    ///
+    /// ```
+    /// # fn foo(n: usize) {
+    /// # use std::mem::align_of;
+    /// # unsafe {
+    /// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
+    /// let ptr = &x[n] as *const u8;
+    /// let offset = ptr.align_offset(align_of::<u16>());
+    /// if offset < x.len() - n - 1 {
+    ///     let u16_ptr = ptr.add(offset) as *const u16;
+    ///     assert_ne!(*u16_ptr, 500);
+    /// } else {
+    ///     // while the pointer can be aligned via `offset`, it would point
+    ///     // outside the allocation
+    /// }
+    /// # } }
+    /// ```
+    #[stable(feature = "align_offset", since = "1.36.0")]
+    pub fn align_offset(self, align: usize) -> usize where T: Sized {
+        if !align.is_power_of_two() {
+            panic!("align_offset: align is not a power-of-two");
+        }
+        unsafe {
+            align_offset(self, align)
+        }
+    }
+}
+
+/// Align pointer `p`.
+///
+/// Calculate offset (in terms of elements of `stride` stride) that has to be applied
+/// to pointer `p` so that pointer `p` would get aligned to `a`.
+///
+/// Note: This implementation has been carefully tailored to not panic. It is UB for this to panic.
+/// The only real change that can be made here is change of `INV_TABLE_MOD_16` and associated
+/// constants.
+///
+/// If we ever decide to make it possible to call the intrinsic with `a` that is not a
+/// power-of-two, it will probably be more prudent to just change to a naive implementation rather
+/// than trying to adapt this to accommodate that change.
+///
+/// Any questions go to @nagisa.
+#[lang="align_offset"]
+pub(crate) unsafe fn align_offset<T: Sized>(p: *const T, a: usize) -> usize {
+    /// Calculate multiplicative modular inverse of `x` modulo `m`.
+    ///
+    /// This implementation is tailored for align_offset and has following preconditions:
+    ///
+    /// * `m` is a power-of-two;
+    /// * `x < m`; (if `x ≥ m`, pass in `x % m` instead)
+    ///
+    /// Implementation of this function shall not panic. Ever.
+    #[inline]
+    fn mod_inv(x: usize, m: usize) -> usize {
+        /// Multiplicative modular inverse table modulo 2⁴ = 16.
+        ///
+        /// Note, that this table does not contain values where inverse does not exist (i.e., for
+        /// `0⁻¹ mod 16`, `2⁻¹ mod 16`, etc.)
+        const INV_TABLE_MOD_16: [u8; 8] = [1, 11, 13, 7, 9, 3, 5, 15];
+        /// Modulo for which the `INV_TABLE_MOD_16` is intended.
+        const INV_TABLE_MOD: usize = 16;
+        /// INV_TABLE_MOD²
+        const INV_TABLE_MOD_SQUARED: usize = INV_TABLE_MOD * INV_TABLE_MOD;
+
+        let table_inverse = INV_TABLE_MOD_16[(x & (INV_TABLE_MOD - 1)) >> 1] as usize;
+        if m <= INV_TABLE_MOD {
+            table_inverse & (m - 1)
+        } else {
+            // We iterate "up" using the following formula:
+            //
+            // $$ xy ≡ 1 (mod 2ⁿ) → xy (2 - xy) ≡ 1 (mod 2²ⁿ) $$
+            //
+            // until 2²ⁿ ≥ m. Then we can reduce to our desired `m` by taking the result `mod m`.
+            let mut inverse = table_inverse;
+            let mut going_mod = INV_TABLE_MOD_SQUARED;
+            loop {
+                // y = y * (2 - xy) mod n
+                //
+                // Note, that we use wrapping operations here intentionally – the original formula
+                // uses e.g., subtraction `mod n`. It is entirely fine to do them `mod
+                // usize::max_value()` instead, because we take the result `mod n` at the end
+                // anyway.
+                inverse = inverse.wrapping_mul(
+                    2usize.wrapping_sub(x.wrapping_mul(inverse))
+                ) & (going_mod - 1);
+                if going_mod > m {
+                    return inverse & (m - 1);
+                }
+                going_mod = going_mod.wrapping_mul(going_mod);
+            }
+        }
+    }
+
+    let stride = mem::size_of::<T>();
+    let a_minus_one = a.wrapping_sub(1);
+    let pmoda = p as usize & a_minus_one;
+
+    if pmoda == 0 {
+        // Already aligned. Yay!
+        return 0;
+    }
+
+    if stride <= 1 {
+        return if stride == 0 {
+            // If the pointer is not aligned, and the element is zero-sized, then no amount of
+            // elements will ever align the pointer.
+            !0
+        } else {
+            a.wrapping_sub(pmoda)
+        };
+    }
+
+    let smoda = stride & a_minus_one;
+    // a is power-of-two so cannot be 0. stride = 0 is handled above.
+    let gcdpow = intrinsics::cttz_nonzero(stride).min(intrinsics::cttz_nonzero(a));
+    let gcd = 1usize << gcdpow;
+
+    if p as usize & (gcd - 1) == 0 {
+        // This branch solves for the following linear congruence equation:
+        //
+        // $$ p + so ≡ 0 mod a $$
+        //
+        // $p$ here is the pointer value, $s$ – stride of `T`, $o$ offset in `T`s, and $a$ – the
+        // requested alignment.
+        //
+        // g = gcd(a, s)
+        // o = (a - (p mod a))/g * ((s/g)⁻¹ mod a)
+        //
+        // The first term is “the relative alignment of p to a”, the second term is “how does
+        // incrementing p by s bytes change the relative alignment of p”. Division by `g` is
+        // necessary to make this equation well formed if $a$ and $s$ are not co-prime.
+        //
+        // Furthermore, the result produced by this solution is not “minimal”, so it is necessary
+        // to take the result $o mod lcm(s, a)$. We can replace $lcm(s, a)$ with just a $a / g$.
+        let j = a.wrapping_sub(pmoda) >> gcdpow;
+        let k = smoda >> gcdpow;
+        return intrinsics::unchecked_rem(j.wrapping_mul(mod_inv(k, a)), a >> gcdpow);
+    }
+
+    // Cannot be aligned at all.
+    usize::max_value()
+}
+
+
+
+// Equality for pointers
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> PartialEq for *const T {
+    #[inline]
+    fn eq(&self, other: &*const T) -> bool { *self == *other }
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> Eq for *const T {}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> PartialEq for *mut T {
+    #[inline]
+    fn eq(&self, other: &*mut T) -> bool { *self == *other }
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> Eq for *mut T {}
+
+/// Compares raw pointers for equality.
+///
+/// This is the same as using the `==` operator, but less generic:
+/// the arguments have to be `*const T` raw pointers,
+/// not anything that implements `PartialEq`.
+///
+/// This can be used to compare `&T` references (which coerce to `*const T` implicitly)
+/// by their address rather than comparing the values they point to
+/// (which is what the `PartialEq for &T` implementation does).
+///
+/// # Examples
+///
+/// ```
+/// use std::ptr;
+///
+/// let five = 5;
+/// let other_five = 5;
+/// let five_ref = &five;
+/// let same_five_ref = &five;
+/// let other_five_ref = &other_five;
+///
+/// assert!(five_ref == same_five_ref);
+/// assert!(ptr::eq(five_ref, same_five_ref));
+///
+/// assert!(five_ref == other_five_ref);
+/// assert!(!ptr::eq(five_ref, other_five_ref));
+/// ```
+///
+/// Slices are also compared by their length (fat pointers):
+///
+/// ```
+/// let a = [1, 2, 3];
+/// assert!(std::ptr::eq(&a[..3], &a[..3]));
+/// assert!(!std::ptr::eq(&a[..2], &a[..3]));
+/// assert!(!std::ptr::eq(&a[0..2], &a[1..3]));
+/// ```
+///
+/// Traits are also compared by their implementation:
+///
+/// ```
+/// #[repr(transparent)]
+/// struct Wrapper { member: i32 }
+///
+/// trait Trait {}
+/// impl Trait for Wrapper {}
+/// impl Trait for i32 {}
+///
+/// fn main() {
+///     let wrapper = Wrapper { member: 10 };
+///
+///     // Pointers have equal addresses.
+///     assert!(std::ptr::eq(
+///         &wrapper as *const Wrapper as *const u8,
+///         &wrapper.member as *const i32 as *const u8
+///     ));
+///
+///     // Objects have equal addresses, but `Trait` has different implementations.
+///     assert!(!std::ptr::eq(
+///         &wrapper as &dyn Trait,
+///         &wrapper.member as &dyn Trait,
+///     ));
+///     assert!(!std::ptr::eq(
+///         &wrapper as &dyn Trait as *const dyn Trait,
+///         &wrapper.member as &dyn Trait as *const dyn Trait,
+///     ));
+///
+///     // Converting the reference to a `*const u8` compares by address.
+///     assert!(std::ptr::eq(
+///         &wrapper as &dyn Trait as *const dyn Trait as *const u8,
+///         &wrapper.member as &dyn Trait as *const dyn Trait as *const u8,
+///     ));
+/// }
+/// ```
+#[stable(feature = "ptr_eq", since = "1.17.0")]
+#[inline]
+pub fn eq<T: ?Sized>(a: *const T, b: *const T) -> bool {
+    a == b
+}
+
+/// Hash a raw pointer.
+///
+/// This can be used to hash a `&T` reference (which coerces to `*const T` implicitly)
+/// by its address rather than the value it points to
+/// (which is what the `Hash for &T` implementation does).
+///
+/// # Examples
+///
+/// ```
+/// use std::collections::hash_map::DefaultHasher;
+/// use std::hash::{Hash, Hasher};
+/// use std::ptr;
+///
+/// let five = 5;
+/// let five_ref = &five;
+///
+/// let mut hasher = DefaultHasher::new();
+/// ptr::hash(five_ref, &mut hasher);
+/// let actual = hasher.finish();
+///
+/// let mut hasher = DefaultHasher::new();
+/// (five_ref as *const i32).hash(&mut hasher);
+/// let expected = hasher.finish();
+///
+/// assert_eq!(actual, expected);
+/// ```
+#[stable(feature = "ptr_hash", since = "1.35.0")]
+pub fn hash<T: ?Sized, S: hash::Hasher>(hashee: *const T, into: &mut S) {
+    use crate::hash::Hash;
+    hashee.hash(into);
+}
+
+// Impls for function pointers
+macro_rules! fnptr_impls_safety_abi {
+    ($FnTy: ty, $($Arg: ident),*) => {
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> PartialEq for $FnTy {
+            #[inline]
+            fn eq(&self, other: &Self) -> bool {
+                *self as usize == *other as usize
+            }
+        }
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> Eq for $FnTy {}
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> PartialOrd for $FnTy {
+            #[inline]
+            fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
+                (*self as usize).partial_cmp(&(*other as usize))
+            }
+        }
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> Ord for $FnTy {
+            #[inline]
+            fn cmp(&self, other: &Self) -> Ordering {
+                (*self as usize).cmp(&(*other as usize))
+            }
+        }
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> hash::Hash for $FnTy {
+            fn hash<HH: hash::Hasher>(&self, state: &mut HH) {
+                state.write_usize(*self as usize)
+            }
+        }
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> fmt::Pointer for $FnTy {
+            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+                fmt::Pointer::fmt(&(*self as *const ()), f)
+            }
+        }
+
+        #[stable(feature = "fnptr_impls", since = "1.4.0")]
+        impl<Ret, $($Arg),*> fmt::Debug for $FnTy {
+            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+                fmt::Pointer::fmt(&(*self as *const ()), f)
+            }
+        }
+    }
+}
+
+macro_rules! fnptr_impls_args {
+    ($($Arg: ident),+) => {
+        fnptr_impls_safety_abi! { extern "Rust" fn($($Arg),*) -> Ret, $($Arg),* }
+        fnptr_impls_safety_abi! { extern "C" fn($($Arg),*) -> Ret, $($Arg),* }
+        fnptr_impls_safety_abi! { extern "C" fn($($Arg),* , ...) -> Ret, $($Arg),* }
+        fnptr_impls_safety_abi! { unsafe extern "Rust" fn($($Arg),*) -> Ret, $($Arg),* }
+        fnptr_impls_safety_abi! { unsafe extern "C" fn($($Arg),*) -> Ret, $($Arg),* }
+        fnptr_impls_safety_abi! { unsafe extern "C" fn($($Arg),* , ...) -> Ret, $($Arg),* }
+    };
+    () => {
+        // No variadic functions with 0 parameters
+        fnptr_impls_safety_abi! { extern "Rust" fn() -> Ret, }
+        fnptr_impls_safety_abi! { extern "C" fn() -> Ret, }
+        fnptr_impls_safety_abi! { unsafe extern "Rust" fn() -> Ret, }
+        fnptr_impls_safety_abi! { unsafe extern "C" fn() -> Ret, }
+    };
+}
+
+fnptr_impls_args! { }
+fnptr_impls_args! { A }
+fnptr_impls_args! { A, B }
+fnptr_impls_args! { A, B, C }
+fnptr_impls_args! { A, B, C, D }
+fnptr_impls_args! { A, B, C, D, E }
+fnptr_impls_args! { A, B, C, D, E, F }
+fnptr_impls_args! { A, B, C, D, E, F, G }
+fnptr_impls_args! { A, B, C, D, E, F, G, H }
+fnptr_impls_args! { A, B, C, D, E, F, G, H, I }
+fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J }
+fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J, K }
+fnptr_impls_args! { A, B, C, D, E, F, G, H, I, J, K, L }
+
+// Comparison for pointers
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> Ord for *const T {
+    #[inline]
+    fn cmp(&self, other: &*const T) -> Ordering {
+        if self < other {
+            Less
+        } else if self == other {
+            Equal
+        } else {
+            Greater
+        }
+    }
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> PartialOrd for *const T {
+    #[inline]
+    fn partial_cmp(&self, other: &*const T) -> Option<Ordering> {
+        Some(self.cmp(other))
+    }
+
+    #[inline]
+    fn lt(&self, other: &*const T) -> bool { *self < *other }
+
+    #[inline]
+    fn le(&self, other: &*const T) -> bool { *self <= *other }
+
+    #[inline]
+    fn gt(&self, other: &*const T) -> bool { *self > *other }
+
+    #[inline]
+    fn ge(&self, other: &*const T) -> bool { *self >= *other }
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> Ord for *mut T {
+    #[inline]
+    fn cmp(&self, other: &*mut T) -> Ordering {
+        if self < other {
+            Less
+        } else if self == other {
+            Equal
+        } else {
+            Greater
+        }
+    }
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T: ?Sized> PartialOrd for *mut T {
+    #[inline]
+    fn partial_cmp(&self, other: &*mut T) -> Option<Ordering> {
+        Some(self.cmp(other))
+    }
+
+    #[inline]
+    fn lt(&self, other: &*mut T) -> bool { *self < *other }
+
+    #[inline]
+    fn le(&self, other: &*mut T) -> bool { *self <= *other }
+
+    #[inline]
+    fn gt(&self, other: &*mut T) -> bool { *self > *other }
+
+    #[inline]
+    fn ge(&self, other: &*mut T) -> bool { *self >= *other }
+}
diff --git a/src/libcore/ptr/non_null.rs b/src/libcore/ptr/non_null.rs
new file mode 100644 (file)
index 0000000..0a6985e
--- /dev/null
@@ -0,0 +1,226 @@
+use crate::convert::From;
+use crate::ops::{CoerceUnsized, DispatchFromDyn};
+use crate::fmt;
+use crate::hash;
+use crate::marker::Unsize;
+use crate::mem;
+use crate::ptr::Unique;
+use crate::cmp::Ordering;
+
+/// `*mut T` but non-zero and covariant.
+///
+/// This is often the correct thing to use when building data structures using
+/// raw pointers, but is ultimately more dangerous to use because of its additional
+/// properties. If you're not sure if you should use `NonNull<T>`, just use `*mut T`!
+///
+/// Unlike `*mut T`, the pointer must always be non-null, even if the pointer
+/// is never dereferenced. This is so that enums may use this forbidden value
+/// as a discriminant -- `Option<NonNull<T>>` has the same size as `*mut T`.
+/// However the pointer may still dangle if it isn't dereferenced.
+///
+/// Unlike `*mut T`, `NonNull<T>` is covariant over `T`. If this is incorrect
+/// for your use case, you should include some [`PhantomData`] in your type to
+/// provide invariance, such as `PhantomData<Cell<T>>` or `PhantomData<&'a mut T>`.
+/// Usually this won't be necessary; covariance is correct for most safe abstractions,
+/// such as `Box`, `Rc`, `Arc`, `Vec`, and `LinkedList`. This is the case because they
+/// provide a public API that follows the normal shared XOR mutable rules of Rust.
+///
+/// Notice that `NonNull<T>` has a `From` instance for `&T`. However, this does
+/// not change the fact that mutating through a (pointer derived from a) shared
+/// reference is undefined behavior unless the mutation happens inside an
+/// [`UnsafeCell<T>`]. The same goes for creating a mutable reference from a shared
+/// reference. When using this `From` instance without an `UnsafeCell<T>`,
+/// it is your responsibility to ensure that `as_mut` is never called, and `as_ptr`
+/// is never used for mutation.
+///
+/// [`PhantomData`]: ../marker/struct.PhantomData.html
+/// [`UnsafeCell<T>`]: ../cell/struct.UnsafeCell.html
+#[stable(feature = "nonnull", since = "1.25.0")]
+#[repr(transparent)]
+#[rustc_layout_scalar_valid_range_start(1)]
+#[cfg_attr(not(stage0), rustc_nonnull_optimization_guaranteed)]
+pub struct NonNull<T: ?Sized> {
+    pointer: *const T,
+}
+
+/// `NonNull` pointers are not `Send` because the data they reference may be aliased.
+// N.B., this impl is unnecessary, but should provide better error messages.
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> !Send for NonNull<T> { }
+
+/// `NonNull` pointers are not `Sync` because the data they reference may be aliased.
+// N.B., this impl is unnecessary, but should provide better error messages.
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> !Sync for NonNull<T> { }
+
+impl<T: Sized> NonNull<T> {
+    /// Creates a new `NonNull` that is dangling, but well-aligned.
+    ///
+    /// This is useful for initializing types which lazily allocate, like
+    /// `Vec::new` does.
+    ///
+    /// Note that the pointer value may potentially represent a valid pointer to
+    /// a `T`, which means this must not be used as a "not yet initialized"
+    /// sentinel value. Types that lazily allocate must track initialization by
+    /// some other means.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub const fn dangling() -> Self {
+        unsafe {
+            let ptr = mem::align_of::<T>() as *mut T;
+            NonNull::new_unchecked(ptr)
+        }
+    }
+}
+
+impl<T: ?Sized> NonNull<T> {
+    /// Creates a new `NonNull`.
+    ///
+    /// # Safety
+    ///
+    /// `ptr` must be non-null.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub const unsafe fn new_unchecked(ptr: *mut T) -> Self {
+        NonNull { pointer: ptr as _ }
+    }
+
+    /// Creates a new `NonNull` if `ptr` is non-null.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub fn new(ptr: *mut T) -> Option<Self> {
+        if !ptr.is_null() {
+            Some(unsafe { Self::new_unchecked(ptr) })
+        } else {
+            None
+        }
+    }
+
+    /// Acquires the underlying `*mut` pointer.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub const fn as_ptr(self) -> *mut T {
+        self.pointer as *mut T
+    }
+
+    /// Dereferences the content.
+    ///
+    /// The resulting lifetime is bound to self so this behaves "as if"
+    /// it were actually an instance of T that is getting borrowed. If a longer
+    /// (unbound) lifetime is needed, use `&*my_ptr.as_ptr()`.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub unsafe fn as_ref(&self) -> &T {
+        &*self.as_ptr()
+    }
+
+    /// Mutably dereferences the content.
+    ///
+    /// The resulting lifetime is bound to self so this behaves "as if"
+    /// it were actually an instance of T that is getting borrowed. If a longer
+    /// (unbound) lifetime is needed, use `&mut *my_ptr.as_ptr()`.
+    #[stable(feature = "nonnull", since = "1.25.0")]
+    #[inline]
+    pub unsafe fn as_mut(&mut self) -> &mut T {
+        &mut *self.as_ptr()
+    }
+
+    /// Cast to a pointer of another type
+    #[stable(feature = "nonnull_cast", since = "1.27.0")]
+    #[inline]
+    pub const fn cast<U>(self) -> NonNull<U> {
+        unsafe {
+            NonNull::new_unchecked(self.as_ptr() as *mut U)
+        }
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> Clone for NonNull<T> {
+    #[inline]
+    fn clone(&self) -> Self {
+        *self
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> Copy for NonNull<T> { }
+
+#[unstable(feature = "coerce_unsized", issue = "27732")]
+impl<T: ?Sized, U: ?Sized> CoerceUnsized<NonNull<U>> for NonNull<T> where T: Unsize<U> { }
+
+#[unstable(feature = "dispatch_from_dyn", issue = "0")]
+impl<T: ?Sized, U: ?Sized> DispatchFromDyn<NonNull<U>> for NonNull<T> where T: Unsize<U> { }
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> fmt::Debug for NonNull<T> {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        fmt::Pointer::fmt(&self.as_ptr(), f)
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> fmt::Pointer for NonNull<T> {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        fmt::Pointer::fmt(&self.as_ptr(), f)
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> Eq for NonNull<T> {}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> PartialEq for NonNull<T> {
+    #[inline]
+    fn eq(&self, other: &Self) -> bool {
+        self.as_ptr() == other.as_ptr()
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> Ord for NonNull<T> {
+    #[inline]
+    fn cmp(&self, other: &Self) -> Ordering {
+        self.as_ptr().cmp(&other.as_ptr())
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> PartialOrd for NonNull<T> {
+    #[inline]
+    fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
+        self.as_ptr().partial_cmp(&other.as_ptr())
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> hash::Hash for NonNull<T> {
+    #[inline]
+    fn hash<H: hash::Hasher>(&self, state: &mut H) {
+        self.as_ptr().hash(state)
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> From<Unique<T>> for NonNull<T> {
+    #[inline]
+    fn from(unique: Unique<T>) -> Self {
+        unsafe { NonNull::new_unchecked(unique.as_ptr()) }
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> From<&mut T> for NonNull<T> {
+    #[inline]
+    fn from(reference: &mut T) -> Self {
+        unsafe { NonNull { pointer: reference as *mut T } }
+    }
+}
+
+#[stable(feature = "nonnull", since = "1.25.0")]
+impl<T: ?Sized> From<&T> for NonNull<T> {
+    #[inline]
+    fn from(reference: &T) -> Self {
+        unsafe { NonNull { pointer: reference as *const T } }
+    }
+}
diff --git a/src/libcore/ptr/unique.rs b/src/libcore/ptr/unique.rs
new file mode 100644 (file)
index 0000000..5911518
--- /dev/null
@@ -0,0 +1,180 @@
+use crate::convert::From;
+use crate::ops::{CoerceUnsized, DispatchFromDyn};
+use crate::fmt;
+use crate::marker::{PhantomData, Unsize};
+use crate::mem;
+use crate::ptr::NonNull;
+
+/// A wrapper around a raw non-null `*mut T` that indicates that the possessor
+/// of this wrapper owns the referent. Useful for building abstractions like
+/// `Box<T>`, `Vec<T>`, `String`, and `HashMap<K, V>`.
+///
+/// Unlike `*mut T`, `Unique<T>` behaves "as if" it were an instance of `T`.
+/// It implements `Send`/`Sync` if `T` is `Send`/`Sync`. It also implies
+/// the kind of strong aliasing guarantees an instance of `T` can expect:
+/// the referent of the pointer should not be modified without a unique path to
+/// its owning Unique.
+///
+/// If you're uncertain of whether it's correct to use `Unique` for your purposes,
+/// consider using `NonNull`, which has weaker semantics.
+///
+/// Unlike `*mut T`, the pointer must always be non-null, even if the pointer
+/// is never dereferenced. This is so that enums may use this forbidden value
+/// as a discriminant -- `Option<Unique<T>>` has the same size as `Unique<T>`.
+/// However the pointer may still dangle if it isn't dereferenced.
+///
+/// Unlike `*mut T`, `Unique<T>` is covariant over `T`. This should always be correct
+/// for any type which upholds Unique's aliasing requirements.
+#[unstable(feature = "ptr_internals", issue = "0",
+           reason = "use NonNull instead and consider PhantomData<T> \
+                     (if you also use #[may_dangle]), Send, and/or Sync")]
+#[doc(hidden)]
+#[repr(transparent)]
+#[rustc_layout_scalar_valid_range_start(1)]
+pub struct Unique<T: ?Sized> {
+    pointer: *const T,
+    // NOTE: this marker has no consequences for variance, but is necessary
+    // for dropck to understand that we logically own a `T`.
+    //
+    // For details, see:
+    // https://github.com/rust-lang/rfcs/blob/master/text/0769-sound-generic-drop.md#phantom-data
+    _marker: PhantomData<T>,
+}
+
+/// `Unique` pointers are `Send` if `T` is `Send` because the data they
+/// reference is unaliased. Note that this aliasing invariant is
+/// unenforced by the type system; the abstraction using the
+/// `Unique` must enforce it.
+#[unstable(feature = "ptr_internals", issue = "0")]
+unsafe impl<T: Send + ?Sized> Send for Unique<T> { }
+
+/// `Unique` pointers are `Sync` if `T` is `Sync` because the data they
+/// reference is unaliased. Note that this aliasing invariant is
+/// unenforced by the type system; the abstraction using the
+/// `Unique` must enforce it.
+#[unstable(feature = "ptr_internals", issue = "0")]
+unsafe impl<T: Sync + ?Sized> Sync for Unique<T> { }
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: Sized> Unique<T> {
+    /// Creates a new `Unique` that is dangling, but well-aligned.
+    ///
+    /// This is useful for initializing types which lazily allocate, like
+    /// `Vec::new` does.
+    ///
+    /// Note that the pointer value may potentially represent a valid pointer to
+    /// a `T`, which means this must not be used as a "not yet initialized"
+    /// sentinel value. Types that lazily allocate must track initialization by
+    /// some other means.
+    // FIXME: rename to dangling() to match NonNull?
+    #[inline]
+    pub const fn empty() -> Self {
+        unsafe {
+            Unique::new_unchecked(mem::align_of::<T>() as *mut T)
+        }
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> Unique<T> {
+    /// Creates a new `Unique`.
+    ///
+    /// # Safety
+    ///
+    /// `ptr` must be non-null.
+    #[inline]
+    pub const unsafe fn new_unchecked(ptr: *mut T) -> Self {
+        Unique { pointer: ptr as _, _marker: PhantomData }
+    }
+
+    /// Creates a new `Unique` if `ptr` is non-null.
+    #[inline]
+    pub fn new(ptr: *mut T) -> Option<Self> {
+        if !ptr.is_null() {
+            Some(unsafe { Unique { pointer: ptr as _, _marker: PhantomData } })
+        } else {
+            None
+        }
+    }
+
+    /// Acquires the underlying `*mut` pointer.
+    #[inline]
+    pub const fn as_ptr(self) -> *mut T {
+        self.pointer as *mut T
+    }
+
+    /// Dereferences the content.
+    ///
+    /// The resulting lifetime is bound to self so this behaves "as if"
+    /// it were actually an instance of T that is getting borrowed. If a longer
+    /// (unbound) lifetime is needed, use `&*my_ptr.as_ptr()`.
+    #[inline]
+    pub unsafe fn as_ref(&self) -> &T {
+        &*self.as_ptr()
+    }
+
+    /// Mutably dereferences the content.
+    ///
+    /// The resulting lifetime is bound to self so this behaves "as if"
+    /// it were actually an instance of T that is getting borrowed. If a longer
+    /// (unbound) lifetime is needed, use `&mut *my_ptr.as_ptr()`.
+    #[inline]
+    pub unsafe fn as_mut(&mut self) -> &mut T {
+        &mut *self.as_ptr()
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> Clone for Unique<T> {
+    #[inline]
+    fn clone(&self) -> Self {
+        *self
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> Copy for Unique<T> { }
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized, U: ?Sized> CoerceUnsized<Unique<U>> for Unique<T> where T: Unsize<U> { }
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized, U: ?Sized> DispatchFromDyn<Unique<U>> for Unique<T> where T: Unsize<U> { }
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> fmt::Debug for Unique<T> {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        fmt::Pointer::fmt(&self.as_ptr(), f)
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> fmt::Pointer for Unique<T> {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        fmt::Pointer::fmt(&self.as_ptr(), f)
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> From<&mut T> for Unique<T> {
+    #[inline]
+    fn from(reference: &mut T) -> Self {
+        unsafe { Unique { pointer: reference as *mut T, _marker: PhantomData } }
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<T: ?Sized> From<&T> for Unique<T> {
+    #[inline]
+    fn from(reference: &T) -> Self {
+        unsafe { Unique { pointer: reference as *const T, _marker: PhantomData } }
+    }
+}
+
+#[unstable(feature = "ptr_internals", issue = "0")]
+impl<'a, T: ?Sized> From<NonNull<T>> for Unique<T> {
+    #[inline]
+    fn from(p: NonNull<T>) -> Self {
+        unsafe { Unique::new_unchecked(p.as_ptr()) }
+    }
+}
index 50d2ba0d3ef7fa06ee9c332bc59b4f5e3c96c3f8..0e782bef39dd8ee6b4dd011f6df94da6369dee3a 100644 (file)
@@ -4158,6 +4158,24 @@ fn next_back(&mut self) -> Option<&'a [T]> {
             Some(snd)
         }
     }
+
+    #[inline]
+    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
+        let len = self.len();
+        if n >= len {
+            self.v = &[];
+            None
+        } else {
+            let start = (len - 1 - n) * self.chunk_size;
+            let end = match start.checked_add(self.chunk_size) {
+                Some(res) => cmp::min(res, self.v.len()),
+                None => self.v.len(),
+            };
+            let nth_back = &self.v[start..end];
+            self.v = &self.v[..start];
+            Some(nth_back)
+        }
+    }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
@@ -4649,6 +4667,23 @@ fn next_back(&mut self) -> Option<&'a [T]> {
             Some(fst)
         }
     }
+
+    #[inline]
+    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
+        let len = self.len();
+        if n >= len {
+            self.v = &[];
+            None
+        } else {
+            // can't underflow because `n < len`
+            let offset_from_end = (len - 1 - n) * self.chunk_size;
+            let end = self.v.len() - offset_from_end;
+            let start = end.saturating_sub(self.chunk_size);
+            let nth_back = &self.v[start..end];
+            self.v = &self.v[end..];
+            Some(nth_back)
+        }
+    }
 }
 
 #[stable(feature = "rchunks", since = "1.31.0")]
@@ -4774,6 +4809,24 @@ fn next_back(&mut self) -> Option<&'a mut [T]> {
             Some(head)
         }
     }
+
+    #[inline]
+    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
+        let len = self.len();
+        if n >= len {
+            self.v = &mut [];
+            None
+        } else {
+            // can't underflow because `n < len`
+            let offset_from_end = (len - 1 - n) * self.chunk_size;
+            let end = self.v.len() - offset_from_end;
+            let start = end.saturating_sub(self.chunk_size);
+            let (tmp, tail) = mem::replace(&mut self.v, &mut []).split_at_mut(end);
+            let (_, nth_back) = tmp.split_at_mut(start);
+            self.v = tail;
+            Some(nth_back)
+        }
+    }
 }
 
 #[stable(feature = "rchunks", since = "1.31.0")]
@@ -4898,6 +4951,24 @@ fn next_back(&mut self) -> Option<&'a [T]> {
             Some(fst)
         }
     }
+
+    #[inline]
+    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
+        let len = self.len();
+        if n >= len {
+            self.v = &[];
+            None
+        } else {
+            // now that we know that `n` corresponds to a chunk,
+            // none of these operations can underflow/overflow
+            let offset = (len - n) * self.chunk_size;
+            let start = self.v.len() - offset;
+            let end = start + self.chunk_size;
+            let nth_back = &self.v[start..end];
+            self.v = &self.v[end..];
+            Some(nth_back)
+        }
+    }
 }
 
 #[stable(feature = "rchunks", since = "1.31.0")]
@@ -5016,6 +5087,25 @@ fn next_back(&mut self) -> Option<&'a mut [T]> {
             Some(head)
         }
     }
+
+    #[inline]
+    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
+        let len = self.len();
+        if n >= len {
+            self.v = &mut [];
+            None
+        } else {
+            // now that we know that `n` corresponds to a chunk,
+            // none of these operations can underflow/overflow
+            let offset = (len - n) * self.chunk_size;
+            let start = self.v.len() - offset;
+            let end = start + self.chunk_size;
+            let (tmp, tail) = mem::replace(&mut self.v, &mut []).split_at_mut(end);
+            let (_, nth_back) = tmp.split_at_mut(start);
+            self.v = tail;
+            Some(nth_back)
+        }
+    }
 }
 
 #[stable(feature = "rchunks", since = "1.31.0")]
index 7dfb1adad9eede80a81eb92635b292327d4a4a56..bedb9e756129c5a0322e3dbe22bbbbeb74992950 100644 (file)
@@ -1084,6 +1084,14 @@ fn test_iterator_sum_result() {
     assert_eq!(v.iter().cloned().sum::<Result<i32, _>>(), Err(()));
 }
 
+#[test]
+fn test_iterator_sum_option() {
+    let v: &[Option<i32>] = &[Some(1), Some(2), Some(3), Some(4)];
+    assert_eq!(v.iter().cloned().sum::<Option<i32>>(), Some(10));
+    let v: &[Option<i32>] = &[Some(1), None, Some(3), Some(4)];
+    assert_eq!(v.iter().cloned().sum::<Option<i32>>(), None);
+}
+
 #[test]
 fn test_iterator_product() {
     let v: &[i32] = &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
@@ -1126,6 +1134,14 @@ fn cmp(&self, other: &Self) -> core::cmp::Ordering {
     }
 }
 
+#[test]
+fn test_iterator_product_option() {
+    let v: &[Option<i32>] = &[Some(1), Some(2), Some(3), Some(4)];
+    assert_eq!(v.iter().cloned().product::<Option<i32>>(), Some(24));
+    let v: &[Option<i32>] = &[Some(1), None, Some(3), Some(4)];
+    assert_eq!(v.iter().cloned().product::<Option<i32>>(), None);
+}
+
 #[test]
 fn test_iterator_max() {
     let v: &[_] = &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
index acf6b03791f01ad27baed0bcc0ddef31e11985cc..9710f019f4e4df0ba630cfd6c4a0c0e6bd246345 100644 (file)
@@ -134,6 +134,30 @@ fn test_chunks_nth() {
     assert_eq!(c2.next(), None);
 }
 
+#[test]
+fn test_chunks_nth_back() {
+    let v: &[i32] = &[0, 1, 2, 3, 4, 5];
+    let mut c = v.chunks(2);
+    assert_eq!(c.nth_back(1).unwrap(), &[2, 3]);
+    assert_eq!(c.next().unwrap(), &[0, 1]);
+    assert_eq!(c.next(), None);
+
+    let v2: &[i32] = &[0, 1, 2, 3, 4];
+    let mut c2 = v2.chunks(3);
+    assert_eq!(c2.nth_back(1).unwrap(), &[0, 1, 2]);
+    assert_eq!(c2.next(), None);
+    assert_eq!(c2.next_back(), None);
+
+    let v3: &[i32] = &[0, 1, 2, 3, 4];
+    let mut c3 = v3.chunks(10);
+    assert_eq!(c3.nth_back(0).unwrap(), &[0, 1, 2, 3, 4]);
+    assert_eq!(c3.next(), None);
+
+    let v4: &[i32] = &[0, 1, 2];
+    let mut c4 = v4.chunks(10);
+    assert_eq!(c4.nth_back(1_000_000_000usize), None);
+}
+
 #[test]
 fn test_chunks_last() {
     let v: &[i32] = &[0, 1, 2, 3, 4, 5];
@@ -356,6 +380,19 @@ fn test_rchunks_nth() {
     assert_eq!(c2.next(), None);
 }
 
+#[test]
+fn test_rchunks_nth_back() {
+    let v: &[i32] = &[0, 1, 2, 3, 4, 5];
+    let mut c = v.rchunks(2);
+    assert_eq!(c.nth_back(1).unwrap(), &[2, 3]);
+    assert_eq!(c.next_back().unwrap(), &[4, 5]);
+
+    let v2: &[i32] = &[0, 1, 2, 3, 4];
+    let mut c2 = v2.rchunks(3);
+    assert_eq!(c2.nth_back(1).unwrap(), &[2, 3, 4]);
+    assert_eq!(c2.next_back(), None);
+}
+
 #[test]
 fn test_rchunks_last() {
     let v: &[i32] = &[0, 1, 2, 3, 4, 5];
@@ -407,6 +444,19 @@ fn test_rchunks_mut_nth() {
     assert_eq!(c2.next(), None);
 }
 
+#[test]
+fn test_rchunks_mut_nth_back() {
+    let v: &mut [i32] = &mut [0, 1, 2, 3, 4, 5];
+    let mut c = v.rchunks_mut(2);
+    assert_eq!(c.nth_back(1).unwrap(), &[2, 3]);
+    assert_eq!(c.next_back().unwrap(), &[4, 5]);
+
+    let v2: &mut [i32] = &mut [0, 1, 2, 3, 4];
+    let mut c2 = v2.rchunks_mut(3);
+    assert_eq!(c2.nth_back(1).unwrap(), &[2, 3, 4]);
+    assert_eq!(c2.next_back(), None);
+}
+
 #[test]
 fn test_rchunks_mut_last() {
     let v: &mut [i32] = &mut [0, 1, 2, 3, 4, 5];
@@ -460,6 +510,19 @@ fn test_rchunks_exact_nth() {
     assert_eq!(c2.next(), None);
 }
 
+#[test]
+fn test_rchunks_exact_nth_back() {
+    let v: &[i32] = &[0, 1, 2, 3, 4, 5];
+    let mut c = v.rchunks_exact(2);
+    assert_eq!(c.nth_back(1).unwrap(), &[2, 3]);
+    assert_eq!(c.next_back().unwrap(), &[4, 5]);
+
+    let v2: &[i32] = &[0, 1, 2, 3, 4, 5, 6];
+    let mut c2 = v2.rchunks_exact(3);
+    assert_eq!(c2.nth_back(1).unwrap(), &[4, 5, 6]);
+    assert_eq!(c2.next(), None);
+}
+
 #[test]
 fn test_rchunks_exact_last() {
     let v: &[i32] = &[0, 1, 2, 3, 4, 5];
@@ -518,6 +581,19 @@ fn test_rchunks_exact_mut_nth() {
     assert_eq!(c2.next(), None);
 }
 
+#[test]
+fn test_rchunks_exact_mut_nth_back() {
+    let v: &mut [i32] = &mut [0, 1, 2, 3, 4, 5];
+    let mut c = v.rchunks_exact_mut(2);
+    assert_eq!(c.nth_back(1).unwrap(), &[2, 3]);
+    assert_eq!(c.next_back().unwrap(), &[4, 5]);
+
+    let v2: &mut [i32] = &mut [0, 1, 2, 3, 4, 5, 6];
+    let mut c2 = v2.rchunks_exact_mut(3);
+    assert_eq!(c2.nth_back(1).unwrap(), &[4, 5, 6]);
+    assert_eq!(c2.next(), None);
+}
+
 #[test]
 fn test_rchunks_exact_mut_last() {
     let v: &mut [i32] = &mut [0, 1, 2, 3, 4, 5];
index 1a6f5d3733e7ac5fbc1664639dc078dad699f6a2..f03a8ddc90825a7a23086878d2150da9d2bb744d 100644 (file)
@@ -425,6 +425,13 @@ pub fn id(&self) -> HirId {
             GenericArg::Const(c) => c.value.hir_id,
         }
     }
+
+    pub fn is_const(&self) -> bool {
+        match self {
+            GenericArg::Const(_) => true,
+            _ => false,
+        }
+    }
 }
 
 #[derive(Clone, RustcEncodable, RustcDecodable, Debug, HashStable)]
index 8ec9d42ec5f827b272ae5a78016fc45a4ee0e93b..f87c6977f33d0261ea99cd3339b5184aa5c4a1ad 100644 (file)
@@ -652,7 +652,7 @@ fn note_error_origin(
                         for sp in prior_arms {
                             err.span_label(*sp, format!(
                                 "this is found to be of type `{}`",
-                                self.resolve_type_vars_if_possible(&last_ty),
+                                self.resolve_vars_if_possible(&last_ty),
                             ));
                         }
                     } else if let Some(sp) = prior_arms.last() {
@@ -1278,7 +1278,7 @@ fn expected_found_str_ty(
         &self,
         exp_found: &ty::error::ExpectedFound<Ty<'tcx>>,
     ) -> Option<(DiagnosticStyledString, DiagnosticStyledString)> {
-        let exp_found = self.resolve_type_vars_if_possible(exp_found);
+        let exp_found = self.resolve_vars_if_possible(exp_found);
         if exp_found.references_error() {
             return None;
         }
@@ -1291,7 +1291,7 @@ fn expected_found_str<T: fmt::Display + TypeFoldable<'tcx>>(
         &self,
         exp_found: &ty::error::ExpectedFound<T>,
     ) -> Option<(DiagnosticStyledString, DiagnosticStyledString)> {
-        let exp_found = self.resolve_type_vars_if_possible(exp_found);
+        let exp_found = self.resolve_vars_if_possible(exp_found);
         if exp_found.references_error() {
             return None;
         }
index ca159872ea7fbde2ccb5e2deff0a21429b8fb48f..972ffbe1820a5569ee59ae336b4f89652e4dcce2 100644 (file)
@@ -24,7 +24,7 @@ fn node_matches_type(&mut self, hir_id: HirId) -> bool {
         });
         match ty_opt {
             Some(ty) => {
-                let ty = self.infcx.resolve_type_vars_if_possible(&ty);
+                let ty = self.infcx.resolve_vars_if_possible(&ty);
                 ty.walk().any(|inner_ty| {
                     inner_ty == self.target_ty || match (&inner_ty.sty, &self.target_ty.sty) {
                         (&Infer(TyVar(a_vid)), &Infer(TyVar(b_vid))) => {
@@ -94,7 +94,7 @@ pub fn need_type_info_err(
         span: Span,
         ty: Ty<'tcx>
     ) -> DiagnosticBuilder<'gcx> {
-        let ty = self.resolve_type_vars_if_possible(&ty);
+        let ty = self.resolve_vars_if_possible(&ty);
         let name = self.extract_type_name(&ty, None);
 
         let mut err_span = span;
@@ -166,7 +166,7 @@ pub fn need_type_info_err_in_generator(
         span: Span,
         ty: Ty<'tcx>
     ) -> DiagnosticBuilder<'gcx> {
-        let ty = self.resolve_type_vars_if_possible(&ty);
+        let ty = self.resolve_vars_if_possible(&ty);
         let name = self.extract_type_name(&ty, None);
 
         let mut err = struct_span_err!(self.tcx.sess,
index 60acbe0afe431935ebf430c6d2dd19d1e83d814a..1dd391950254dd55db1ea4b198d84138489ef6f7 100644 (file)
@@ -210,11 +210,11 @@ fn try_report_placeholders_trait(
             _ => (),
         }
 
-        let expected_trait_ref = self.infcx.resolve_type_vars_if_possible(&ty::TraitRef {
+        let expected_trait_ref = self.infcx.resolve_vars_if_possible(&ty::TraitRef {
             def_id: trait_def_id,
             substs: expected_substs,
         });
-        let actual_trait_ref = self.infcx.resolve_type_vars_if_possible(&ty::TraitRef {
+        let actual_trait_ref = self.infcx.resolve_vars_if_possible(&ty::TraitRef {
             def_id: trait_def_id,
             substs: actual_substs,
         });
index 5f5a2d4a489e361fbfa10bb5c00f31a6614ca2a4..7461d8bc72860ec7ffbe44a23004bf1d0c84095c 100644 (file)
@@ -74,7 +74,7 @@ pub fn fudge_inference_if_ok<T, E, F>(
         let (mut fudger, value) = self.probe(|snapshot| {
             match f() {
                 Ok(value) => {
-                    let value = self.resolve_type_vars_if_possible(&value);
+                    let value = self.resolve_vars_if_possible(&value);
 
                     // At this point, `value` could in principle refer
                     // to inference variables that have been created during
index b5a9184079aa66b42713b6c5101c8e4f41133c2c..a4a7efdbc9e3e204d9687b9afeffba6b46dae0fa 100644 (file)
@@ -1174,7 +1174,7 @@ pub fn set_tainted_by_errors(&self) {
     /// Process the region constraints and report any errors that
     /// result. After this, no more unification operations should be
     /// done -- or the compiler will panic -- but it is legal to use
-    /// `resolve_type_vars_if_possible` as well as `fully_resolve`.
+    /// `resolve_vars_if_possible` as well as `fully_resolve`.
     pub fn resolve_regions_and_report_errors(
         &self,
         region_context: DefId,
@@ -1262,7 +1262,7 @@ pub fn take_region_var_origins(&self) -> VarInfos {
     }
 
     pub fn ty_to_string(&self, t: Ty<'tcx>) -> String {
-        self.resolve_type_vars_if_possible(&t).to_string()
+        self.resolve_vars_if_possible(&t).to_string()
     }
 
     pub fn tys_to_string(&self, ts: &[Ty<'tcx>]) -> String {
@@ -1271,7 +1271,7 @@ pub fn tys_to_string(&self, ts: &[Ty<'tcx>]) -> String {
     }
 
     pub fn trait_ref_to_string(&self, t: &ty::TraitRef<'tcx>) -> String {
-        self.resolve_type_vars_if_possible(t).to_string()
+        self.resolve_vars_if_possible(t).to_string()
     }
 
     /// If `TyVar(vid)` resolves to a type, return that type. Else, return the
@@ -1297,20 +1297,20 @@ pub fn root_var(&self, var: ty::TyVid) -> ty::TyVid {
         self.type_variables.borrow_mut().root_var(var)
     }
 
-    /// Where possible, replaces type/int/float variables in
+    /// Where possible, replaces type/const variables in
     /// `value` with their final value. Note that region variables
-    /// are unaffected. If a type variable has not been unified, it
+    /// are unaffected. If a type/const variable has not been unified, it
     /// is left as is. This is an idempotent operation that does
     /// not affect inference state in any way and so you can do it
     /// at will.
-    pub fn resolve_type_vars_if_possible<T>(&self, value: &T) -> T
+    pub fn resolve_vars_if_possible<T>(&self, value: &T) -> T
     where
         T: TypeFoldable<'tcx>,
     {
         if !value.needs_infer() {
             return value.clone(); // avoid duplicated subst-folding
         }
-        let mut r = resolve::OpportunisticTypeResolver::new(self);
+        let mut r = resolve::OpportunisticVarResolver::new(self);
         value.fold_with(&mut r)
     }
 
@@ -1318,7 +1318,7 @@ pub fn resolve_type_vars_if_possible<T>(&self, value: &T) -> T
     /// process of visiting `T`, this will resolve (where possible)
     /// type variables in `T`, but it never constructs the final,
     /// resolved type, so it's more efficient than
-    /// `resolve_type_vars_if_possible()`.
+    /// `resolve_vars_if_possible()`.
     pub fn unresolved_type_vars<T>(&self, value: &T) -> Option<(Ty<'tcx>, Option<Span>)>
     where
         T: TypeFoldable<'tcx>,
@@ -1389,7 +1389,7 @@ pub fn type_error_struct_with_diag<M>(
     where
         M: FnOnce(String) -> DiagnosticBuilder<'tcx>,
     {
-        let actual_ty = self.resolve_type_vars_if_possible(&actual_ty);
+        let actual_ty = self.resolve_vars_if_possible(&actual_ty);
         debug!("type_error_struct_with_diag({:?}, {:?})", sp, actual_ty);
 
         // Don't report an error if actual type is `Error`.
@@ -1446,7 +1446,7 @@ pub fn type_is_copy_modulo_regions(
         ty: Ty<'tcx>,
         span: Span,
     ) -> bool {
-        let ty = self.resolve_type_vars_if_possible(&ty);
+        let ty = self.resolve_vars_if_possible(&ty);
 
         // Even if the type may have no inference variables, during
         // type-checking closure types are in local tables only.
index 4351f94df2f135db586d5b7f310eaac9bd3416b2..220b7b5fa67feeb45eb52358ab561c00929e6a59 100644 (file)
@@ -286,7 +286,7 @@ pub fn constrain_opaque_type<FRR: FreeRegionRelations<'tcx>>(
 
         let tcx = self.tcx;
 
-        let concrete_ty = self.resolve_type_vars_if_possible(&opaque_defn.concrete_ty);
+        let concrete_ty = self.resolve_vars_if_possible(&opaque_defn.concrete_ty);
 
         debug!("constrain_opaque_type: concrete_ty={:?}", concrete_ty);
 
index 39aa51a95f793cb9bebe71b05f16bafc9f493df5..3e626999200fea98900e671761c1feea6d703efc 100644 (file)
@@ -168,7 +168,7 @@ pub fn add_implied_bounds(
         debug!("add_implied_bounds()");
 
         for &ty in fn_sig_tys {
-            let ty = infcx.resolve_type_vars_if_possible(&ty);
+            let ty = infcx.resolve_vars_if_possible(&ty);
             debug!("add_implied_bounds: ty = {}", ty);
             let implied_bounds = infcx.implied_outlives_bounds(self.param_env, body_id, ty, span);
             self.add_outlives_bounds(Some(infcx), implied_bounds)
index ee66032848519887c0454b0290946d6fd872c398..90b3be213854c93e0b0059f24e323c2c40569409 100644 (file)
@@ -177,7 +177,7 @@ pub fn process_registered_region_obligations(
                 sup_type, sub_region, origin
             );
 
-            let sup_type = self.resolve_type_vars_if_possible(&sup_type);
+            let sup_type = self.resolve_vars_if_possible(&sup_type);
 
             if let Some(region_bound_pairs) = region_bound_pairs_map.get(&body_id) {
                 let outlives = &mut TypeOutlives::new(
@@ -215,7 +215,7 @@ pub fn type_must_outlive(
             implicit_region_bound,
             param_env,
         );
-        let ty = self.resolve_type_vars_if_possible(&ty);
+        let ty = self.resolve_vars_if_possible(&ty);
         outlives.type_must_outlive(origin, ty, region);
     }
 }
index 079385368f883885981e8f5478d074007a9ca133..95bae8f2bd1afb7b4326f18be4ecf1dd3f4f296e 100644 (file)
@@ -1,28 +1,28 @@
 use super::{InferCtxt, FixupError, FixupResult, Span, type_variable::TypeVariableOrigin};
 use crate::mir::interpret::ConstValue;
-use crate::ty::{self, Ty, TyCtxt, TypeFoldable, InferConst};
+use crate::ty::{self, Ty, Const, TyCtxt, TypeFoldable, InferConst, TypeFlags};
 use crate::ty::fold::{TypeFolder, TypeVisitor};
 
 ///////////////////////////////////////////////////////////////////////////
-// OPPORTUNISTIC TYPE RESOLVER
+// OPPORTUNISTIC VAR RESOLVER
 
-/// The opportunistic type resolver can be used at any time. It simply replaces
-/// type variables that have been unified with the things they have
+/// The opportunistic resolver can be used at any time. It simply replaces
+/// type/const variables that have been unified with the things they have
 /// been unified with (similar to `shallow_resolve`, but deep). This is
 /// useful for printing messages etc but also required at various
 /// points for correctness.
-pub struct OpportunisticTypeResolver<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
+pub struct OpportunisticVarResolver<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
     infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
 }
 
-impl<'a, 'gcx, 'tcx> OpportunisticTypeResolver<'a, 'gcx, 'tcx> {
+impl<'a, 'gcx, 'tcx> OpportunisticVarResolver<'a, 'gcx, 'tcx> {
     #[inline]
     pub fn new(infcx: &'a InferCtxt<'a, 'gcx, 'tcx>) -> Self {
-        OpportunisticTypeResolver { infcx }
+        OpportunisticVarResolver { infcx }
     }
 }
 
-impl<'a, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for OpportunisticTypeResolver<'a, 'gcx, 'tcx> {
+impl<'a, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for OpportunisticVarResolver<'a, 'gcx, 'tcx> {
     fn tcx<'b>(&'b self) -> TyCtxt<'b, 'gcx, 'tcx> {
         self.infcx.tcx
     }
@@ -31,8 +31,17 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> {
         if !t.has_infer_types() {
             t // micro-optimize -- if there is nothing in this type that this fold affects...
         } else {
-            let t0 = self.infcx.shallow_resolve(t);
-            t0.super_fold_with(self)
+            let t = self.infcx.shallow_resolve(t);
+            t.super_fold_with(self)
+        }
+    }
+
+    fn fold_const(&mut self, ct: &'tcx Const<'tcx>) -> &'tcx Const<'tcx> {
+        if !ct.has_type_flags(TypeFlags::HAS_CT_INFER) {
+            ct // micro-optimize -- if there is nothing in this const that this fold affects...
+        } else {
+            let ct = self.infcx.shallow_resolve(ct);
+            ct.super_fold_with(self)
         }
     }
 }
index 69d865f53d469f3083a0bcd6abb6410947f3dc77..f7af51e47526cd38392ec0340db3660425a7f05b 100644 (file)
 
 declare_lint! {
     pub BARE_TRAIT_OBJECTS,
-    Allow,
+    Warn,
     "suggest using `dyn Trait` for trait objects"
 }
 
index c6b544469b5fa6840e68f60cd7204c701ff5838c..8d7c6f18a854f23913db941643cdeabcdd977a70 100644 (file)
@@ -458,10 +458,10 @@ pub fn type_is_copy_modulo_regions(
             .unwrap_or(true)
     }
 
-    fn resolve_type_vars_if_possible<T>(&self, value: &T) -> T
+    fn resolve_vars_if_possible<T>(&self, value: &T) -> T
         where T: TypeFoldable<'tcx>
     {
-        self.infcx.map(|infcx| infcx.resolve_type_vars_if_possible(value))
+        self.infcx.map(|infcx| infcx.resolve_vars_if_possible(value))
             .unwrap_or_else(|| value.clone())
     }
 
@@ -475,7 +475,7 @@ fn resolve_type_vars_or_error(&self,
                                   -> McResult<Ty<'tcx>> {
         match ty {
             Some(ty) => {
-                let ty = self.resolve_type_vars_if_possible(&ty);
+                let ty = self.resolve_vars_if_possible(&ty);
                 if ty.references_error() || ty.is_ty_var() {
                     debug!("resolve_type_vars_or_error: error from {:?}", ty);
                     Err(())
@@ -602,7 +602,7 @@ fn cat_expr_adjusted_with<F>(&self, expr: &hir::Expr,
         where F: FnOnce() -> McResult<cmt_<'tcx>>
     {
         debug!("cat_expr_adjusted_with({:?}): {:?}", adjustment, expr);
-        let target = self.resolve_type_vars_if_possible(&adjustment.target);
+        let target = self.resolve_vars_if_possible(&adjustment.target);
         match adjustment.kind {
             adjustment::Adjust::Deref(overloaded) => {
                 // Equivalent to *expr or something similar.
index 736b4633b38f9865eeeaaf573b0857e9b8c23896..593a09b6866dbb8335b58c42b5be149941b1bf64 100644 (file)
@@ -170,16 +170,11 @@ pub enum Set1<T> {
 
 impl<T: PartialEq> Set1<T> {
     pub fn insert(&mut self, value: T) {
-        if let Set1::Empty = *self {
-            *self = Set1::One(value);
-            return;
-        }
-        if let Set1::One(ref old) = *self {
-            if *old == value {
-                return;
-            }
-        }
-        *self = Set1::Many;
+        *self = match self {
+            Set1::Empty => Set1::One(value),
+            Set1::One(old) if *old == value => return,
+            _ => Set1::Many,
+        };
     }
 }
 
index 1cc927b1f720f3a549493b8d7b906f55fb97c349..007013f8f8287f108d93e6a55fbf42c6ccf7a117 100644 (file)
@@ -3,7 +3,7 @@
 use rustc_data_structures::stable_hasher::{HashStable, StableHasher,
                                            StableHasherResult};
 use crate::ich::StableHashingContext;
-use crate::mir::{Mir, BasicBlock};
+use crate::mir::{Body, BasicBlock};
 
 use crate::rustc_serialize as serialize;
 
@@ -47,7 +47,7 @@ pub fn invalidate(&self) {
 
     pub fn predecessors(
         &self,
-        mir: &Mir<'_>
+        mir: &Body<'_>
     ) -> MappedReadGuard<'_, IndexVec<BasicBlock, Vec<BasicBlock>>> {
         if self.predecessors.borrow().is_none() {
             *self.predecessors.borrow_mut() = Some(calculate_predecessors(mir));
@@ -57,7 +57,7 @@ pub fn predecessors(
     }
 }
 
-fn calculate_predecessors(mir: &Mir<'_>) -> IndexVec<BasicBlock, Vec<BasicBlock>> {
+fn calculate_predecessors(mir: &Body<'_>) -> IndexVec<BasicBlock, Vec<BasicBlock>> {
     let mut result = IndexVec::from_elem(vec![], mir.basic_blocks());
     for (bb, data) in mir.basic_blocks().iter_enumerated() {
         if let Some(ref term) = data.terminator {
index 0e2da4c577205010a32689fb2f584ce904d489b2..9549a5af5af5c7c64c62e0ab45852abf24e28e29 100644 (file)
@@ -2,7 +2,6 @@
 
 use super::{
     Pointer, EvalResult, AllocId, ScalarMaybeUndef, write_target_uint, read_target_uint, Scalar,
-    truncate,
 };
 
 use crate::ty::layout::{Size, Align};
@@ -407,18 +406,9 @@ pub fn write_scalar(
             ScalarMaybeUndef::Undef => return self.mark_definedness(ptr, type_size, false),
         };
 
-        let bytes = match val {
-            Scalar::Ptr(val) => {
-                assert_eq!(type_size, cx.data_layout().pointer_size);
-                val.offset.bytes() as u128
-            }
-
-            Scalar::Bits { bits, size } => {
-                assert_eq!(size as u64, type_size.bytes());
-                debug_assert_eq!(truncate(bits, Size::from_bytes(size.into())), bits,
-                    "Unexpected value of size {} when writing to memory", size);
-                bits
-            },
+        let bytes = match val.to_bits_or_ptr(type_size, cx) {
+            Err(val) => val.offset.bytes() as u128,
+            Ok(data) => data,
         };
 
         let endian = cx.data_layout().endian;
index 595ea8bd34687c6451960d1e7e407b98ba064563..7985af914ff93e314b9b7ccc8b251772a4a8fcdf 100644 (file)
@@ -47,7 +47,7 @@ pub struct GlobalId<'tcx> {
     /// For a promoted global, the `Instance` of the function they belong to.
     pub instance: ty::Instance<'tcx>,
 
-    /// The index for promoted globals within their function's `Mir`.
+    /// The index for promoted globals within their function's `mir::Body`.
     pub promoted: Option<mir::Promoted>,
 }
 
@@ -349,6 +349,7 @@ pub fn create_fn_alloc(&mut self, instance: Instance<'tcx>) -> AllocId {
     /// illegal and will likely ICE.
     /// This function exists to allow const eval to detect the difference between evaluation-
     /// local dangling pointers and allocations in constants/statics.
+    #[inline]
     pub fn get(&self, id: AllocId) -> Option<AllocKind<'tcx>> {
         self.id_to_kind.get(&id).cloned()
     }
@@ -397,6 +398,7 @@ fn set_alloc_id_same_memory(&mut self, id: AllocId, mem: &'tcx Allocation) {
 // Methods to access integers in the target endianness
 ////////////////////////////////////////////////////////////////////////////////
 
+#[inline]
 pub fn write_target_uint(
     endianness: layout::Endian,
     mut target: &mut [u8],
@@ -409,6 +411,7 @@ pub fn write_target_uint(
     }
 }
 
+#[inline]
 pub fn read_target_uint(endianness: layout::Endian, mut source: &[u8]) -> Result<u128, io::Error> {
     match endianness {
         layout::Endian::Little => source.read_uint128::<LittleEndian>(source.len()),
@@ -420,8 +423,15 @@ pub fn read_target_uint(endianness: layout::Endian, mut source: &[u8]) -> Result
 // Methods to facilitate working with signed integers stored in a u128
 ////////////////////////////////////////////////////////////////////////////////
 
+/// Truncate `value` to `size` bits and then sign-extend it to 128 bits
+/// (i.e., if it is negative, fill with 1's on the left).
+#[inline]
 pub fn sign_extend(value: u128, size: Size) -> u128 {
     let size = size.bits();
+    if size == 0 {
+        // Truncated until nothing is left.
+        return 0;
+    }
     // sign extend
     let shift = 128 - size;
     // shift the unsigned value to the left
@@ -429,8 +439,14 @@ pub fn sign_extend(value: u128, size: Size) -> u128 {
     (((value << shift) as i128) >> shift) as u128
 }
 
+/// Truncate `value` to `size` bits.
+#[inline]
 pub fn truncate(value: u128, size: Size) -> u128 {
     let size = size.bits();
+    if size == 0 {
+        // Truncated until nothing is left.
+        return 0;
+    }
     let shift = 128 - size;
     // truncate (shift left to drop out leftover values, shift right to fill with zeroes)
     (value << shift) >> shift
index 9422abc4e6f715e8f9e52b950bdbd22282714301..9e71399d4fdf7eacd9d02e4e12d1932e35b7ae74 100644 (file)
@@ -20,30 +20,20 @@ fn pointer_size(&self) -> Size {
         self.data_layout().pointer_size
     }
 
-    //// Trunace the given value to the pointer size; also return whether there was an overflow
+    /// Helper function: truncate given value-"overflowed flag" pair to pointer size and
+    /// update "overflowed flag" if there was an overflow.
+    /// This should be called by all the other methods before returning!
     #[inline]
-    fn truncate_to_ptr(&self, val: u128) -> (u64, bool) {
+    fn truncate_to_ptr(&self, (val, over): (u64, bool)) -> (u64, bool) {
+        let val = val as u128;
         let max_ptr_plus_1 = 1u128 << self.pointer_size().bits();
-        ((val % max_ptr_plus_1) as u64, val >= max_ptr_plus_1)
-    }
-
-    #[inline]
-    fn offset<'tcx>(&self, val: u64, i: u64) -> EvalResult<'tcx, u64> {
-        let (res, over) = self.overflowing_offset(val, i);
-        if over { err!(Overflow(mir::BinOp::Add)) } else { Ok(res) }
+        ((val % max_ptr_plus_1) as u64, over || val >= max_ptr_plus_1)
     }
 
     #[inline]
     fn overflowing_offset(&self, val: u64, i: u64) -> (u64, bool) {
-        let (res, over1) = val.overflowing_add(i);
-        let (res, over2) = self.truncate_to_ptr(u128::from(res));
-        (res, over1 || over2)
-    }
-
-    #[inline]
-    fn signed_offset<'tcx>(&self, val: u64, i: i64) -> EvalResult<'tcx, u64> {
-        let (res, over) = self.overflowing_signed_offset(val, i128::from(i));
-        if over { err!(Overflow(mir::BinOp::Add)) } else { Ok(res) }
+        let res = val.overflowing_add(i);
+        self.truncate_to_ptr(res)
     }
 
     // Overflow checking only works properly on the range from -u64 to +u64.
@@ -51,14 +41,27 @@ fn signed_offset<'tcx>(&self, val: u64, i: i64) -> EvalResult<'tcx, u64> {
     fn overflowing_signed_offset(&self, val: u64, i: i128) -> (u64, bool) {
         // FIXME: is it possible to over/underflow here?
         if i < 0 {
-            // trickery to ensure that i64::min_value() works fine
-            // this formula only works for true negative values, it panics for zero!
+            // Trickery to ensure that i64::min_value() works fine: compute n = -i.
+            // This formula only works for true negative values, it overflows for zero!
             let n = u64::max_value() - (i as u64) + 1;
-            val.overflowing_sub(n)
+            let res = val.overflowing_sub(n);
+            self.truncate_to_ptr(res)
         } else {
             self.overflowing_offset(val, i as u64)
         }
     }
+
+    #[inline]
+    fn offset<'tcx>(&self, val: u64, i: u64) -> EvalResult<'tcx, u64> {
+        let (res, over) = self.overflowing_offset(val, i);
+        if over { err!(Overflow(mir::BinOp::Add)) } else { Ok(res) }
+    }
+
+    #[inline]
+    fn signed_offset<'tcx>(&self, val: u64, i: i64) -> EvalResult<'tcx, u64> {
+        let (res, over) = self.overflowing_signed_offset(val, i128::from(i));
+        if over { err!(Overflow(mir::BinOp::Add)) } else { Ok(res) }
+    }
 }
 
 impl<T: layout::HasDataLayout> PointerArithmetic for T {}
index 72545f23f8e2bf3ac67a39ebef68f6afd60c0e76..21792b847db77e2e6fb0319436a0f61868a09d5f 100644 (file)
@@ -87,11 +87,11 @@ pub fn try_to_ptr(&self) -> Option<Pointer> {
          RustcEncodable, RustcDecodable, Hash, HashStable)]
 pub enum Scalar<Tag=(), Id=AllocId> {
     /// The raw bytes of a simple value.
-    Bits {
-        /// The first `size` bytes are the value.
+    Raw {
+        /// The first `size` bytes of `data` are the value.
         /// Do not try to read less or more bytes than that. The remaining bytes must be 0.
+        data: u128,
         size: u8,
-        bits: u128,
     },
 
     /// A pointer into an `Allocation`. An `Allocation` in the `memory` module has a list of
@@ -108,16 +108,14 @@ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
         match self {
             Scalar::Ptr(ptr) =>
                 write!(f, "{:?}", ptr),
-            &Scalar::Bits { bits, size } => {
+            &Scalar::Raw { data, size } => {
+                Scalar::check_data(data, size);
                 if size == 0 {
-                    assert_eq!(bits, 0, "ZST value must be 0");
                     write!(f, "<ZST>")
                 } else {
-                    assert_eq!(truncate(bits, Size::from_bytes(size as u64)), bits,
-                            "Scalar value {:#x} exceeds size of {} bytes", bits, size);
                     // Format as hex number wide enough to fit any value of the given `size`.
-                    // So bits=20, size=1 will be "0x14", but with size=4 it'll be "0x00000014".
-                    write!(f, "0x{:>0width$x}", bits, width=(size*2) as usize)
+                    // So data=20, size=1 will be "0x14", but with size=4 it'll be "0x00000014".
+                    write!(f, "0x{:>0width$x}", data, width=(size*2) as usize)
                 }
             }
         }
@@ -128,17 +126,23 @@ impl<Tag> fmt::Display for Scalar<Tag> {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
         match self {
             Scalar::Ptr(_) => write!(f, "a pointer"),
-            Scalar::Bits { bits, .. } => write!(f, "{}", bits),
+            Scalar::Raw { data, .. } => write!(f, "{}", data),
         }
     }
 }
 
 impl<'tcx> Scalar<()> {
+    #[inline(always)]
+    fn check_data(data: u128, size: u8) {
+        debug_assert_eq!(truncate(data, Size::from_bytes(size as u64)), data,
+                         "Scalar value {:#x} exceeds size of {} bytes", data, size);
+    }
+
     #[inline]
     pub fn with_tag<Tag>(self, new_tag: Tag) -> Scalar<Tag> {
         match self {
             Scalar::Ptr(ptr) => Scalar::Ptr(ptr.with_tag(new_tag)),
-            Scalar::Bits { bits, size } => Scalar::Bits { bits, size },
+            Scalar::Raw { data, size } => Scalar::Raw { data, size },
         }
     }
 
@@ -155,31 +159,31 @@ impl<'tcx, Tag> Scalar<Tag> {
     pub fn erase_tag(self) -> Scalar {
         match self {
             Scalar::Ptr(ptr) => Scalar::Ptr(ptr.erase_tag()),
-            Scalar::Bits { bits, size } => Scalar::Bits { bits, size },
+            Scalar::Raw { data, size } => Scalar::Raw { data, size },
         }
     }
 
     #[inline]
     pub fn ptr_null(cx: &impl HasDataLayout) -> Self {
-        Scalar::Bits {
-            bits: 0,
+        Scalar::Raw {
+            data: 0,
             size: cx.data_layout().pointer_size.bytes() as u8,
         }
     }
 
     #[inline]
     pub fn zst() -> Self {
-        Scalar::Bits { bits: 0, size: 0 }
+        Scalar::Raw { data: 0, size: 0 }
     }
 
     #[inline]
     pub fn ptr_offset(self, i: Size, cx: &impl HasDataLayout) -> EvalResult<'tcx, Self> {
         let dl = cx.data_layout();
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, dl.pointer_size.bytes());
-                Ok(Scalar::Bits {
-                    bits: dl.offset(bits as u64, i.bytes())? as u128,
+                Ok(Scalar::Raw {
+                    data: dl.offset(data as u64, i.bytes())? as u128,
                     size,
                 })
             }
@@ -191,10 +195,10 @@ pub fn ptr_offset(self, i: Size, cx: &impl HasDataLayout) -> EvalResult<'tcx, Se
     pub fn ptr_wrapping_offset(self, i: Size, cx: &impl HasDataLayout) -> Self {
         let dl = cx.data_layout();
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, dl.pointer_size.bytes());
-                Scalar::Bits {
-                    bits: dl.overflowing_offset(bits as u64, i.bytes()).0 as u128,
+                Scalar::Raw {
+                    data: dl.overflowing_offset(data as u64, i.bytes()).0 as u128,
                     size,
                 }
             }
@@ -206,10 +210,10 @@ pub fn ptr_wrapping_offset(self, i: Size, cx: &impl HasDataLayout) -> Self {
     pub fn ptr_signed_offset(self, i: i64, cx: &impl HasDataLayout) -> EvalResult<'tcx, Self> {
         let dl = cx.data_layout();
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, dl.pointer_size().bytes());
-                Ok(Scalar::Bits {
-                    bits: dl.signed_offset(bits as u64, i)? as u128,
+                Ok(Scalar::Raw {
+                    data: dl.signed_offset(data as u64, i)? as u128,
                     size,
                 })
             }
@@ -221,10 +225,10 @@ pub fn ptr_signed_offset(self, i: i64, cx: &impl HasDataLayout) -> EvalResult<'t
     pub fn ptr_wrapping_signed_offset(self, i: i64, cx: &impl HasDataLayout) -> Self {
         let dl = cx.data_layout();
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, dl.pointer_size.bytes());
-                Scalar::Bits {
-                    bits: dl.overflowing_signed_offset(bits as u64, i128::from(i)).0 as u128,
+                Scalar::Raw {
+                    data: dl.overflowing_signed_offset(data as u64, i128::from(i)).0 as u128,
                     size,
                 }
             }
@@ -232,14 +236,14 @@ pub fn ptr_wrapping_signed_offset(self, i: i64, cx: &impl HasDataLayout) -> Self
         }
     }
 
-    /// Returns this pointers offset from the allocation base, or from NULL (for
+    /// Returns this pointer's offset from the allocation base, or from NULL (for
     /// integer pointers).
     #[inline]
     pub fn get_ptr_offset(self, cx: &impl HasDataLayout) -> Size {
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, cx.pointer_size().bytes());
-                Size::from_bytes(bits as u64)
+                Size::from_bytes(data as u64)
             }
             Scalar::Ptr(ptr) => ptr.offset,
         }
@@ -248,9 +252,9 @@ pub fn get_ptr_offset(self, cx: &impl HasDataLayout) -> Size {
     #[inline]
     pub fn is_null_ptr(self, cx: &impl HasDataLayout) -> bool {
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, cx.data_layout().pointer_size.bytes());
-                bits == 0
+                data == 0
             },
             Scalar::Ptr(_) => false,
         }
@@ -258,20 +262,22 @@ pub fn is_null_ptr(self, cx: &impl HasDataLayout) -> bool {
 
     #[inline]
     pub fn from_bool(b: bool) -> Self {
-        Scalar::Bits { bits: b as u128, size: 1 }
+        Scalar::Raw { data: b as u128, size: 1 }
     }
 
     #[inline]
     pub fn from_char(c: char) -> Self {
-        Scalar::Bits { bits: c as u128, size: 4 }
+        Scalar::Raw { data: c as u128, size: 4 }
     }
 
     #[inline]
     pub fn from_uint(i: impl Into<u128>, size: Size) -> Self {
         let i = i.into();
-        debug_assert_eq!(truncate(i, size), i,
-                         "Unsigned value {} does not fit in {} bits", i, size.bits());
-        Scalar::Bits { bits: i, size: size.bytes() as u8 }
+        assert_eq!(
+            truncate(i, size), i,
+            "Unsigned value {:#x} does not fit in {} bits", i, size.bits()
+        );
+        Scalar::Raw { data: i, size: size.bytes() as u8 }
     }
 
     #[inline]
@@ -279,28 +285,51 @@ pub fn from_int(i: impl Into<i128>, size: Size) -> Self {
         let i = i.into();
         // `into` performed sign extension, we have to truncate
         let truncated = truncate(i as u128, size);
-        debug_assert_eq!(sign_extend(truncated, size) as i128, i,
-                         "Signed value {} does not fit in {} bits", i, size.bits());
-        Scalar::Bits { bits: truncated, size: size.bytes() as u8 }
+        assert_eq!(
+            sign_extend(truncated, size) as i128, i,
+            "Signed value {:#x} does not fit in {} bits", i, size.bits()
+        );
+        Scalar::Raw { data: truncated, size: size.bytes() as u8 }
     }
 
     #[inline]
     pub fn from_f32(f: f32) -> Self {
-        Scalar::Bits { bits: f.to_bits() as u128, size: 4 }
+        Scalar::Raw { data: f.to_bits() as u128, size: 4 }
     }
 
     #[inline]
     pub fn from_f64(f: f64) -> Self {
-        Scalar::Bits { bits: f.to_bits() as u128, size: 8 }
+        Scalar::Raw { data: f.to_bits() as u128, size: 8 }
+    }
+
+    #[inline]
+    pub fn to_bits_or_ptr(
+        self,
+        target_size: Size,
+        cx: &impl HasDataLayout,
+    ) -> Result<u128, Pointer<Tag>> {
+        match self {
+            Scalar::Raw { data, size } => {
+                assert_eq!(target_size.bytes(), size as u64);
+                assert_ne!(size, 0, "you should never look at the bits of a ZST");
+                Scalar::check_data(data, size);
+                Ok(data)
+            }
+            Scalar::Ptr(ptr) => {
+                assert_eq!(target_size, cx.data_layout().pointer_size);
+                Err(ptr)
+            }
+        }
     }
 
     #[inline]
     pub fn to_bits(self, target_size: Size) -> EvalResult<'tcx, u128> {
         match self {
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(target_size.bytes(), size as u64);
-                assert_ne!(size, 0, "to_bits cannot be used with zsts");
-                Ok(bits)
+                assert_ne!(size, 0, "you should never look at the bits of a ZST");
+                Scalar::check_data(data, size);
+                Ok(data)
             }
             Scalar::Ptr(_) => err!(ReadPointerAsBytes),
         }
@@ -309,8 +338,8 @@ pub fn to_bits(self, target_size: Size) -> EvalResult<'tcx, u128> {
     #[inline]
     pub fn to_ptr(self) -> EvalResult<'tcx, Pointer<Tag>> {
         match self {
-            Scalar::Bits { bits: 0, .. } => err!(InvalidNullPointerUsage),
-            Scalar::Bits { .. } => err!(ReadBytesAsPointer),
+            Scalar::Raw { data: 0, .. } => err!(InvalidNullPointerUsage),
+            Scalar::Raw { .. } => err!(ReadBytesAsPointer),
             Scalar::Ptr(p) => Ok(p),
         }
     }
@@ -318,7 +347,7 @@ pub fn to_ptr(self) -> EvalResult<'tcx, Pointer<Tag>> {
     #[inline]
     pub fn is_bits(self) -> bool {
         match self {
-            Scalar::Bits { .. } => true,
+            Scalar::Raw { .. } => true,
             _ => false,
         }
     }
@@ -333,8 +362,8 @@ pub fn is_ptr(self) -> bool {
 
     pub fn to_bool(self) -> EvalResult<'tcx, bool> {
         match self {
-            Scalar::Bits { bits: 0, size: 1 } => Ok(false),
-            Scalar::Bits { bits: 1, size: 1 } => Ok(true),
+            Scalar::Raw { data: 0, size: 1 } => Ok(false),
+            Scalar::Raw { data: 1, size: 1 } => Ok(true),
             _ => err!(InvalidBool),
         }
     }
@@ -350,27 +379,23 @@ pub fn to_char(self) -> EvalResult<'tcx, char> {
     pub fn to_u8(self) -> EvalResult<'static, u8> {
         let sz = Size::from_bits(8);
         let b = self.to_bits(sz)?;
-        assert_eq!(b as u8 as u128, b);
         Ok(b as u8)
     }
 
     pub fn to_u32(self) -> EvalResult<'static, u32> {
         let sz = Size::from_bits(32);
         let b = self.to_bits(sz)?;
-        assert_eq!(b as u32 as u128, b);
         Ok(b as u32)
     }
 
     pub fn to_u64(self) -> EvalResult<'static, u64> {
         let sz = Size::from_bits(64);
         let b = self.to_bits(sz)?;
-        assert_eq!(b as u64 as u128, b);
         Ok(b as u64)
     }
 
     pub fn to_usize(self, cx: &impl HasDataLayout) -> EvalResult<'static, u64> {
         let b = self.to_bits(cx.data_layout().pointer_size)?;
-        assert_eq!(b as u64 as u128, b);
         Ok(b as u64)
     }
 
@@ -378,7 +403,6 @@ pub fn to_i8(self) -> EvalResult<'static, i8> {
         let sz = Size::from_bits(8);
         let b = self.to_bits(sz)?;
         let b = sign_extend(b, sz) as i128;
-        assert_eq!(b as i8 as i128, b);
         Ok(b as i8)
     }
 
@@ -386,7 +410,6 @@ pub fn to_i32(self) -> EvalResult<'static, i32> {
         let sz = Size::from_bits(32);
         let b = self.to_bits(sz)?;
         let b = sign_extend(b, sz) as i128;
-        assert_eq!(b as i32 as i128, b);
         Ok(b as i32)
     }
 
@@ -394,14 +417,13 @@ pub fn to_i64(self) -> EvalResult<'static, i64> {
         let sz = Size::from_bits(64);
         let b = self.to_bits(sz)?;
         let b = sign_extend(b, sz) as i128;
-        assert_eq!(b as i64 as i128, b);
         Ok(b as i64)
     }
 
     pub fn to_isize(self, cx: &impl HasDataLayout) -> EvalResult<'static, i64> {
-        let b = self.to_bits(cx.data_layout().pointer_size)?;
-        let b = sign_extend(b, cx.data_layout().pointer_size) as i128;
-        assert_eq!(b as i64 as i128, b);
+        let sz = cx.data_layout().pointer_size;
+        let b = self.to_bits(sz)?;
+        let b = sign_extend(b, sz) as i128;
         Ok(b as i64)
     }
 
index 84aff8101a09d99c3ed55111ba46572bc30ad713..d4ef134728eafe5b6514557a6c570b75aa5603f9 100644 (file)
@@ -60,7 +60,7 @@ fn local_decls(&self) -> &LocalDecls<'tcx> {
     }
 }
 
-impl<'tcx> HasLocalDecls<'tcx> for Mir<'tcx> {
+impl<'tcx> HasLocalDecls<'tcx> for Body<'tcx> {
     fn local_decls(&self) -> &LocalDecls<'tcx> {
         &self.local_decls
     }
@@ -86,7 +86,7 @@ pub fn phase_index(&self) -> usize {
 
 /// Lowered representation of a single function.
 #[derive(Clone, RustcEncodable, RustcDecodable, Debug)]
-pub struct Mir<'tcx> {
+pub struct Body<'tcx> {
     /// List of basic blocks. References to basic block use a newtyped index type `BasicBlock`
     /// that indexes into this vector.
     basic_blocks: IndexVec<BasicBlock, BasicBlockData<'tcx>>,
@@ -107,15 +107,15 @@ pub struct Mir<'tcx> {
     pub source_scope_local_data: ClearCrossCrate<IndexVec<SourceScope, SourceScopeLocalData>>,
 
     /// Rvalues promoted from this function, such as borrows of constants.
-    /// Each of them is the Mir of a constant with the fn's type parameters
+    /// Each of them is the Body of a constant with the fn's type parameters
     /// in scope, but a separate set of locals.
-    pub promoted: IndexVec<Promoted, Mir<'tcx>>,
+    pub promoted: IndexVec<Promoted, Body<'tcx>>,
 
     /// Yields type of the function, if it is a generator.
     pub yield_ty: Option<Ty<'tcx>>,
 
     /// Generator drop glue
-    pub generator_drop: Option<Box<Mir<'tcx>>>,
+    pub generator_drop: Option<Box<Body<'tcx>>>,
 
     /// The layout of a generator. Produced by the state transformation.
     pub generator_layout: Option<GeneratorLayout<'tcx>>,
@@ -167,12 +167,12 @@ pub struct Mir<'tcx> {
     cache: cache::Cache,
 }
 
-impl<'tcx> Mir<'tcx> {
+impl<'tcx> Body<'tcx> {
     pub fn new(
         basic_blocks: IndexVec<BasicBlock, BasicBlockData<'tcx>>,
         source_scopes: IndexVec<SourceScope, SourceScopeData>,
         source_scope_local_data: ClearCrossCrate<IndexVec<SourceScope, SourceScopeLocalData>>,
-        promoted: IndexVec<Promoted, Mir<'tcx>>,
+        promoted: IndexVec<Promoted, Body<'tcx>>,
         yield_ty: Option<Ty<'tcx>>,
         local_decls: LocalDecls<'tcx>,
         user_type_annotations: CanonicalUserTypeAnnotations<'tcx>,
@@ -189,7 +189,7 @@ pub fn new(
             local_decls.len()
         );
 
-        Mir {
+        Body {
             phase: MirPhase::Build,
             basic_blocks,
             source_scopes,
@@ -423,7 +423,7 @@ pub enum Safety {
     ExplicitUnsafe(hir::HirId),
 }
 
-impl_stable_hash_for!(struct Mir<'tcx> {
+impl_stable_hash_for!(struct Body<'tcx> {
     phase,
     basic_blocks,
     source_scopes,
@@ -442,7 +442,7 @@ pub enum Safety {
     cache
 });
 
-impl<'tcx> Index<BasicBlock> for Mir<'tcx> {
+impl<'tcx> Index<BasicBlock> for Body<'tcx> {
     type Output = BasicBlockData<'tcx>;
 
     #[inline]
@@ -451,7 +451,7 @@ fn index(&self, index: BasicBlock) -> &BasicBlockData<'tcx> {
     }
 }
 
-impl<'tcx> IndexMut<BasicBlock> for Mir<'tcx> {
+impl<'tcx> IndexMut<BasicBlock> for Body<'tcx> {
     #[inline]
     fn index_mut(&mut self, index: BasicBlock) -> &mut BasicBlockData<'tcx> {
         &mut self.basic_blocks_mut()[index]
@@ -599,7 +599,7 @@ pub struct Local {
     }
 }
 
-/// Classifies locals into categories. See `Mir::local_kind`.
+/// Classifies locals into categories. See `Body::local_kind`.
 #[derive(PartialEq, Eq, Debug, HashStable)]
 pub enum LocalKind {
     /// User-declared variable binding
@@ -1669,10 +1669,7 @@ pub fn fmt_successor_labels(&self) -> Vec<Cow<'static, str>> {
                         .map(|&u| {
                             tcx.mk_const(ty::Const {
                                 val: ConstValue::Scalar(
-                                    Scalar::Bits {
-                                        bits: u,
-                                        size: size.bytes() as u8,
-                                    }.into(),
+                                    Scalar::from_uint(u, size).into(),
                                 ),
                                 ty: switch_ty,
                             }).to_string().into()
@@ -2040,7 +2037,7 @@ pub fn elem(self, elem: PlaceElem<'tcx>) -> Place<'tcx> {
     /// a single deref of a local.
     //
     // FIXME: can we safely swap the semantics of `fn base_local` below in here instead?
-    pub fn local(&self) -> Option<Local> {
+    pub fn local_or_deref_local(&self) -> Option<Local> {
         match self {
             Place::Base(PlaceBase::Local(local)) |
             Place::Projection(box Projection {
@@ -2831,23 +2828,23 @@ fn fmt(&self, fmt: &mut Formatter<'_>) -> fmt::Result {
     }
 }
 
-impl<'tcx> graph::DirectedGraph for Mir<'tcx> {
+impl<'tcx> graph::DirectedGraph for Body<'tcx> {
     type Node = BasicBlock;
 }
 
-impl<'tcx> graph::WithNumNodes for Mir<'tcx> {
+impl<'tcx> graph::WithNumNodes for Body<'tcx> {
     fn num_nodes(&self) -> usize {
         self.basic_blocks.len()
     }
 }
 
-impl<'tcx> graph::WithStartNode for Mir<'tcx> {
+impl<'tcx> graph::WithStartNode for Body<'tcx> {
     fn start_node(&self) -> Self::Node {
         START_BLOCK
     }
 }
 
-impl<'tcx> graph::WithPredecessors for Mir<'tcx> {
+impl<'tcx> graph::WithPredecessors for Body<'tcx> {
     fn predecessors<'graph>(
         &'graph self,
         node: Self::Node,
@@ -2856,7 +2853,7 @@ fn predecessors<'graph>(
     }
 }
 
-impl<'tcx> graph::WithSuccessors for Mir<'tcx> {
+impl<'tcx> graph::WithSuccessors for Body<'tcx> {
     fn successors<'graph>(
         &'graph self,
         node: Self::Node,
@@ -2865,12 +2862,12 @@ fn successors<'graph>(
     }
 }
 
-impl<'a, 'b> graph::GraphPredecessors<'b> for Mir<'a> {
+impl<'a, 'b> graph::GraphPredecessors<'b> for Body<'a> {
     type Item = BasicBlock;
     type Iter = IntoIter<BasicBlock>;
 }
 
-impl<'a, 'b> graph::GraphSuccessors<'b> for Mir<'a> {
+impl<'a, 'b> graph::GraphSuccessors<'b> for Body<'a> {
     type Item = BasicBlock;
     type Iter = iter::Cloned<Successors<'b>>;
 }
@@ -2909,7 +2906,7 @@ pub fn successor_within_block(&self) -> Location {
     }
 
     /// Returns `true` if `other` is earlier in the control flow graph than `self`.
-    pub fn is_predecessor_of<'tcx>(&self, other: Location, mir: &Mir<'tcx>) -> bool {
+    pub fn is_predecessor_of<'tcx>(&self, other: Location, mir: &Body<'tcx>) -> bool {
         // If we are in the same block as the other location and are an earlier statement
         // then we are a predecessor of `other`.
         if self.block == other.block && self.statement_index < other.statement_index {
@@ -3162,7 +3159,7 @@ pub enum ClosureOutlivesSubject<'tcx> {
 }
 
 BraceStructTypeFoldableImpl! {
-    impl<'tcx> TypeFoldable<'tcx> for Mir<'tcx> {
+    impl<'tcx> TypeFoldable<'tcx> for Body<'tcx> {
         phase,
         basic_blocks,
         source_scopes,
index a26468b0fb6ce0560bc1a1cb46c404dddd0a1872..ca79bc15358c500fb6f3216af3933ddf43af2e87 100644 (file)
@@ -188,49 +188,6 @@ fn hash_stable<W: StableHasherResult>(&self,
     }
 }
 
-#[derive(Clone, Default)]
-pub struct Stats {
-    pub n_glues_created: usize,
-    pub n_null_glues: usize,
-    pub n_real_glues: usize,
-    pub n_fns: usize,
-    pub n_inlines: usize,
-    pub n_closures: usize,
-    pub n_llvm_insns: usize,
-    pub llvm_insns: FxHashMap<String, usize>,
-    // (ident, llvm-instructions)
-    pub fn_stats: Vec<(String, usize)>,
-}
-
-impl_stable_hash_for!(struct self::Stats {
-    n_glues_created,
-    n_null_glues,
-    n_real_glues,
-    n_fns,
-    n_inlines,
-    n_closures,
-    n_llvm_insns,
-    llvm_insns,
-    fn_stats
-});
-
-impl Stats {
-    pub fn extend(&mut self, stats: Stats) {
-        self.n_glues_created += stats.n_glues_created;
-        self.n_null_glues += stats.n_null_glues;
-        self.n_real_glues += stats.n_real_glues;
-        self.n_fns += stats.n_fns;
-        self.n_inlines += stats.n_inlines;
-        self.n_closures += stats.n_closures;
-        self.n_llvm_insns += stats.n_llvm_insns;
-
-        for (k, v) in stats.llvm_insns {
-            *self.llvm_insns.entry(k).or_insert(0) += v;
-        }
-        self.fn_stats.extend(stats.fn_stats);
-    }
-}
-
 pub struct CodegenUnitNameBuilder<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
     cache: FxHashMap<CrateNum, String>,
index f8398c27cc2daefc3965b3dd190859d5f3ed6c8c..75d995d801d7853d6234fb2c551332fb18325fea 100644 (file)
 /// A preorder traversal of this graph is either `A B D C` or `A C D B`
 #[derive(Clone)]
 pub struct Preorder<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     visited: BitSet<BasicBlock>,
     worklist: Vec<BasicBlock>,
     root_is_start_block: bool,
 }
 
 impl<'a, 'tcx> Preorder<'a, 'tcx> {
-    pub fn new(mir: &'a Mir<'tcx>, root: BasicBlock) -> Preorder<'a, 'tcx> {
+    pub fn new(mir: &'a Body<'tcx>, root: BasicBlock) -> Preorder<'a, 'tcx> {
         let worklist = vec![root];
 
         Preorder {
@@ -40,7 +40,7 @@ pub fn new(mir: &'a Mir<'tcx>, root: BasicBlock) -> Preorder<'a, 'tcx> {
     }
 }
 
-pub fn preorder<'a, 'tcx>(mir: &'a Mir<'tcx>) -> Preorder<'a, 'tcx> {
+pub fn preorder<'a, 'tcx>(mir: &'a Body<'tcx>) -> Preorder<'a, 'tcx> {
     Preorder::new(mir, START_BLOCK)
 }
 
@@ -99,14 +99,14 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 ///
 /// A Postorder traversal of this graph is `D B C A` or `D C B A`
 pub struct Postorder<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     visited: BitSet<BasicBlock>,
     visit_stack: Vec<(BasicBlock, Successors<'a>)>,
     root_is_start_block: bool,
 }
 
 impl<'a, 'tcx> Postorder<'a, 'tcx> {
-    pub fn new(mir: &'a Mir<'tcx>, root: BasicBlock) -> Postorder<'a, 'tcx> {
+    pub fn new(mir: &'a Body<'tcx>, root: BasicBlock) -> Postorder<'a, 'tcx> {
         let mut po = Postorder {
             mir,
             visited: BitSet::new_empty(mir.basic_blocks().len()),
@@ -194,7 +194,7 @@ fn traverse_successor(&mut self) {
     }
 }
 
-pub fn postorder<'a, 'tcx>(mir: &'a Mir<'tcx>) -> Postorder<'a, 'tcx> {
+pub fn postorder<'a, 'tcx>(mir: &'a Body<'tcx>) -> Postorder<'a, 'tcx> {
     Postorder::new(mir, START_BLOCK)
 }
 
@@ -252,13 +252,13 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 /// to re-use the traversal
 #[derive(Clone)]
 pub struct ReversePostorder<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     blocks: Vec<BasicBlock>,
     idx: usize
 }
 
 impl<'a, 'tcx> ReversePostorder<'a, 'tcx> {
-    pub fn new(mir: &'a Mir<'tcx>, root: BasicBlock) -> ReversePostorder<'a, 'tcx> {
+    pub fn new(mir: &'a Body<'tcx>, root: BasicBlock) -> ReversePostorder<'a, 'tcx> {
         let blocks : Vec<_> = Postorder::new(mir, root).map(|(bb, _)| bb).collect();
 
         let len = blocks.len();
@@ -276,7 +276,7 @@ pub fn reset(&mut self) {
 }
 
 
-pub fn reverse_postorder<'a, 'tcx>(mir: &'a Mir<'tcx>) -> ReversePostorder<'a, 'tcx> {
+pub fn reverse_postorder<'a, 'tcx>(mir: &'a Body<'tcx>) -> ReversePostorder<'a, 'tcx> {
     ReversePostorder::new(mir, START_BLOCK)
 }
 
index 64ffd80e21ec0d5e269acc6f0c110afd6ff17959..dd33fae0d6197ed509cd86a7d0d863bff3ad65a2 100644 (file)
@@ -71,8 +71,8 @@ pub trait $visitor_trait_name<'tcx> {
             // Override these, and call `self.super_xxx` to revert back to the
             // default behavior.
 
-            fn visit_mir(&mut self, mir: & $($mutability)? Mir<'tcx>) {
-                self.super_mir(mir);
+            fn visit_body(&mut self, mir: & $($mutability)? Body<'tcx>) {
+                self.super_body(mir);
             }
 
             fn visit_basic_block_data(&mut self,
@@ -251,8 +251,8 @@ fn visit_source_scope(&mut self,
             // The `super_xxx` methods comprise the default behavior and are
             // not meant to be overridden.
 
-            fn super_mir(&mut self,
-                         mir: & $($mutability)? Mir<'tcx>) {
+            fn super_body(&mut self,
+                         mir: & $($mutability)? Body<'tcx>) {
                 if let Some(yield_ty) = &$($mutability)? mir.yield_ty {
                     self.visit_ty(yield_ty, TyContext::YieldTy(SourceInfo {
                         span: mir.span,
@@ -261,7 +261,7 @@ fn super_mir(&mut self,
                 }
 
                 // for best performance, we want to use an iterator rather
-                // than a for-loop, to avoid calling Mir::invalidate for
+                // than a for-loop, to avoid calling `mir::Body::invalidate` for
                 // each basic block.
                 macro_rules! basic_blocks {
                     (mut) => (mir.basic_blocks_mut().iter_enumerated_mut());
@@ -825,7 +825,7 @@ fn super_closure_substs(&mut self,
 
             // Convenience methods
 
-            fn visit_location(&mut self, mir: & $($mutability)? Mir<'tcx>, location: Location) {
+            fn visit_location(&mut self, mir: & $($mutability)? Body<'tcx>, location: Location) {
                 let basic_block = & $($mutability)? mir[location.block];
                 if basic_block.statements.len() == location.statement_index {
                     if let Some(ref $($mutability)? terminator) = basic_block.terminator {
index ed363800d79def6c82d5fb5efecd28663981ec0f..81aa8d434d37fa04e918f53c9a1b2aa69e5933b7 100644 (file)
@@ -88,7 +88,7 @@
             desc { "getting a list of all mir_keys" }
         }
 
-        /// Maps DefId's that have an associated Mir to the result
+        /// Maps DefId's that have an associated `mir::Body` to the result
         /// of the MIR qualify_consts pass. The actual meaning of
         /// the value isn't known except to the pass itself.
         query mir_const_qualif(key: DefId) -> (u8, &'tcx BitSet<mir::Local>) {
 
         /// Fetch the MIR for a given `DefId` right after it's built - this includes
         /// unreachable code.
-        query mir_built(_: DefId) -> &'tcx Steal<mir::Mir<'tcx>> {}
+        query mir_built(_: DefId) -> &'tcx Steal<mir::Body<'tcx>> {}
 
         /// Fetch the MIR for a given `DefId` up till the point where it is
         /// ready for const evaluation.
         ///
         /// See the README for the `mir` module for details.
-        query mir_const(_: DefId) -> &'tcx Steal<mir::Mir<'tcx>> {
+        query mir_const(_: DefId) -> &'tcx Steal<mir::Body<'tcx>> {
             no_hash
         }
 
-        query mir_validated(_: DefId) -> &'tcx Steal<mir::Mir<'tcx>> {
+        query mir_validated(_: DefId) -> &'tcx Steal<mir::Body<'tcx>> {
             no_hash
         }
 
         /// MIR after our optimization passes have run. This is MIR that is ready
         /// for codegen. This is also the only query that can fetch non-local MIR, at present.
-        query optimized_mir(key: DefId) -> &'tcx mir::Mir<'tcx> {
+        query optimized_mir(key: DefId) -> &'tcx mir::Body<'tcx> {
             cache { key.is_local() }
             load_cached(tcx, id) {
-                let mir: Option<crate::mir::Mir<'tcx>> = tcx.queries.on_disk_cache
+                let mir: Option<crate::mir::Body<'tcx>> = tcx.queries.on_disk_cache
                                                             .try_load_query_result(tcx, id);
                 mir.map(|x| tcx.alloc_mir(x))
             }
         /// in the case of closures, this will be redirected to the enclosing function.
         query region_scope_tree(_: DefId) -> &'tcx region::ScopeTree {}
 
-        query mir_shims(key: ty::InstanceDef<'tcx>) -> &'tcx mir::Mir<'tcx> {
+        query mir_shims(key: ty::InstanceDef<'tcx>) -> &'tcx mir::Body<'tcx> {
             no_force
             desc { |tcx| "generating MIR shim for `{}`", tcx.def_path_str(key.def_id()) }
         }
index 44b6e03655773628d1e4b55f5e57734534fd6f7a..300d0cbfba55bd3e3f10a1f02bdfa06c2b5b2030 100644 (file)
@@ -117,16 +117,16 @@ pub fn enabled(&self) -> bool {
 }
 
 #[derive(Clone, PartialEq, Hash)]
-pub enum PgoGenerate {
+pub enum SwitchWithOptPath {
     Enabled(Option<PathBuf>),
     Disabled,
 }
 
-impl PgoGenerate {
+impl SwitchWithOptPath {
     pub fn enabled(&self) -> bool {
         match *self {
-            PgoGenerate::Enabled(_) => true,
-            PgoGenerate::Disabled => false,
+            SwitchWithOptPath::Enabled(_) => true,
+            SwitchWithOptPath::Disabled => false,
         }
     }
 }
@@ -834,7 +834,7 @@ mod $mod_desc {
         pub const parse_linker_plugin_lto: Option<&str> =
             Some("either a boolean (`yes`, `no`, `on`, `off`, etc), \
                   or the path to the linker plugin");
-        pub const parse_pgo_generate: Option<&str> =
+        pub const parse_switch_with_opt_path: Option<&str> =
             Some("an optional path to the profiling data output directory");
         pub const parse_merge_functions: Option<&str> =
             Some("one of: `disabled`, `trampolines`, or `aliases`");
@@ -842,7 +842,7 @@ mod $mod_desc {
 
     #[allow(dead_code)]
     mod $mod_set {
-        use super::{$struct_name, Passes, Sanitizer, LtoCli, LinkerPluginLto, PgoGenerate};
+        use super::{$struct_name, Passes, Sanitizer, LtoCli, LinkerPluginLto, SwitchWithOptPath};
         use rustc_target::spec::{LinkerFlavor, MergeFunctions, PanicStrategy, RelroLevel};
         use std::path::PathBuf;
         use std::str::FromStr;
@@ -1097,10 +1097,10 @@ fn parse_linker_plugin_lto(slot: &mut LinkerPluginLto, v: Option<&str>) -> bool
             true
         }
 
-        fn parse_pgo_generate(slot: &mut PgoGenerate, v: Option<&str>) -> bool {
+        fn parse_switch_with_opt_path(slot: &mut SwitchWithOptPath, v: Option<&str>) -> bool {
             *slot = match v {
-                None => PgoGenerate::Enabled(None),
-                Some(path) => PgoGenerate::Enabled(Some(PathBuf::from(path))),
+                None => SwitchWithOptPath::Enabled(None),
+                Some(path) => SwitchWithOptPath::Enabled(Some(PathBuf::from(path))),
             };
             true
         }
@@ -1216,21 +1216,12 @@ fn parse_merge_functions(slot: &mut Option<MergeFunctions>, v: Option<&str>) ->
         "measure time of each rustc pass"),
     time: bool = (false, parse_bool, [UNTRACKED],
         "measure time of rustc processes"),
-    count_llvm_insns: bool = (false, parse_bool,
-        [UNTRACKED_WITH_WARNING(true,
-        "The output generated by `-Z count_llvm_insns` might not be reliable \
-         when used with incremental compilation")],
-        "count where LLVM instrs originate"),
     time_llvm_passes: bool = (false, parse_bool, [UNTRACKED_WITH_WARNING(true,
         "The output of `-Z time-llvm-passes` will only reflect timings of \
          re-codegened modules when used with incremental compilation" )],
         "measure time of each LLVM pass"),
     input_stats: bool = (false, parse_bool, [UNTRACKED],
         "gather statistics about the input"),
-    codegen_stats: bool = (false, parse_bool, [UNTRACKED_WITH_WARNING(true,
-        "The output of `-Z codegen-stats` might not be accurate when incremental \
-         compilation is enabled")],
-        "gather codegen statistics"),
     asm_comments: bool = (false, parse_bool, [TRACKED],
         "generate comments into the assembly (may change behavior)"),
     verify_llvm_ir: bool = (false, parse_bool, [TRACKED],
@@ -1379,7 +1370,8 @@ fn parse_merge_functions(slot: &mut Option<MergeFunctions>, v: Option<&str>) ->
         "extra arguments to prepend to the linker invocation (space separated)"),
     profile: bool = (false, parse_bool, [TRACKED],
                      "insert profiling code"),
-    pgo_gen: PgoGenerate = (PgoGenerate::Disabled, parse_pgo_generate, [TRACKED],
+    pgo_gen: SwitchWithOptPath = (SwitchWithOptPath::Disabled,
+        parse_switch_with_opt_path, [TRACKED],
         "Generate PGO profile data, to a given file, or to the default location if it's empty."),
     pgo_use: Option<PathBuf> = (None, parse_opt_pathbuf, [TRACKED],
         "Use PGO profile data from the given profile file."),
@@ -1447,7 +1439,8 @@ fn parse_merge_functions(slot: &mut Option<MergeFunctions>, v: Option<&str>) ->
         "don't interleave execution of lints; allows benchmarking individual lints"),
     crate_attr: Vec<String> = (Vec::new(), parse_string_push, [TRACKED],
         "inject the given attribute in the crate"),
-    self_profile: bool = (false, parse_bool, [UNTRACKED],
+    self_profile: SwitchWithOptPath = (SwitchWithOptPath::Disabled,
+        parse_switch_with_opt_path, [UNTRACKED],
         "run the self profiler and output the raw event data"),
     self_profile_events: Option<Vec<String>> = (None, parse_opt_comma_list, [UNTRACKED],
         "specifies which kinds of events get recorded by the self profiler"),
@@ -2558,7 +2551,7 @@ mod dep_tracking {
     use std::path::PathBuf;
     use std::collections::hash_map::DefaultHasher;
     use super::{CrateType, DebugInfo, ErrorOutputType, OptLevel, OutputTypes,
-                Passes, Sanitizer, LtoCli, LinkerPluginLto, PgoGenerate};
+                Passes, Sanitizer, LtoCli, LinkerPluginLto, SwitchWithOptPath};
     use syntax::feature_gate::UnstableFeatures;
     use rustc_target::spec::{MergeFunctions, PanicStrategy, RelroLevel, TargetTriple};
     use syntax::edition::Edition;
@@ -2626,7 +2619,7 @@ fn hash(&self, hasher: &mut DefaultHasher, error_format: ErrorOutputType) {
     impl_dep_tracking_hash_via_hash!(TargetTriple);
     impl_dep_tracking_hash_via_hash!(Edition);
     impl_dep_tracking_hash_via_hash!(LinkerPluginLto);
-    impl_dep_tracking_hash_via_hash!(PgoGenerate);
+    impl_dep_tracking_hash_via_hash!(SwitchWithOptPath);
 
     impl_dep_tracking_hash_for_sortable_vec_of!(String);
     impl_dep_tracking_hash_for_sortable_vec_of!(PathBuf);
@@ -2694,7 +2687,7 @@ mod tests {
         build_session_options_and_crate_config,
         to_crate_config
     };
-    use crate::session::config::{LtoCli, LinkerPluginLto, PgoGenerate, ExternEntry};
+    use crate::session::config::{LtoCli, LinkerPluginLto, SwitchWithOptPath, ExternEntry};
     use crate::session::build_session;
     use crate::session::search_paths::SearchPath;
     use std::collections::{BTreeMap, BTreeSet};
@@ -3207,7 +3200,7 @@ fn test_codegen_options_tracking_hash() {
         assert!(reference.dep_tracking_hash() != opts.dep_tracking_hash());
 
         opts = reference.clone();
-        opts.debugging_opts.pgo_gen = PgoGenerate::Enabled(None);
+        opts.debugging_opts.pgo_gen = SwitchWithOptPath::Enabled(None);
         assert_ne!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
 
         opts = reference.clone();
@@ -3257,14 +3250,10 @@ fn test_debugging_options_tracking_hash() {
         assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
         opts.debugging_opts.time_passes = true;
         assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
-        opts.debugging_opts.count_llvm_insns = true;
-        assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
         opts.debugging_opts.time_llvm_passes = true;
         assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
         opts.debugging_opts.input_stats = true;
         assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
-        opts.debugging_opts.codegen_stats = true;
-        assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
         opts.debugging_opts.borrowck_stats = true;
         assert_eq!(reference.dep_tracking_hash(), opts.dep_tracking_hash());
         opts.debugging_opts.meta_stats = true;
index 3d8092f6e007073c9edb0b91063ae22eb13c145f..40af5b45f9c35ebc1a00727022a5d7240d6757bd 100644 (file)
@@ -9,7 +9,7 @@
 use crate::lint::builtin::BuiltinLintDiagnostics;
 use crate::middle::allocator::AllocatorKind;
 use crate::middle::dependency_format;
-use crate::session::config::OutputType;
+use crate::session::config::{OutputType, SwitchWithOptPath};
 use crate::session::search_paths::{PathKind, SearchPath};
 use crate::util::nodemap::{FxHashMap, FxHashSet};
 use crate::util::common::{duration_to_secs_str, ErrorReported};
@@ -519,15 +519,9 @@ pub fn profile_queries_and_keys(&self) -> bool {
     pub fn instrument_mcount(&self) -> bool {
         self.opts.debugging_opts.instrument_mcount
     }
-    pub fn count_llvm_insns(&self) -> bool {
-        self.opts.debugging_opts.count_llvm_insns
-    }
     pub fn time_llvm_passes(&self) -> bool {
         self.opts.debugging_opts.time_llvm_passes
     }
-    pub fn codegen_stats(&self) -> bool {
-        self.opts.debugging_opts.codegen_stats
-    }
     pub fn meta_stats(&self) -> bool {
         self.opts.debugging_opts.meta_stats
     }
@@ -1137,8 +1131,18 @@ fn build_session_(
     driver_lint_caps: FxHashMap<lint::LintId, lint::Level>,
 ) -> Session {
     let self_profiler =
-        if sopts.debugging_opts.self_profile {
-            let profiler = SelfProfiler::new(&sopts.debugging_opts.self_profile_events);
+        if let SwitchWithOptPath::Enabled(ref d) = sopts.debugging_opts.self_profile {
+            let directory = if let Some(ref directory) = d {
+                directory
+            } else {
+                std::path::Path::new(".")
+            };
+
+            let profiler = SelfProfiler::new(
+                directory,
+                sopts.crate_name.as_ref().map(|s| &s[..]),
+                &sopts.debugging_opts.self_profile_events
+            );
             match profiler {
                 Ok(profiler) => {
                     crate::ty::query::QueryName::register_with_profiler(&profiler);
@@ -1281,6 +1285,18 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
                               path.display()));
         }
     }
+
+    // PGO does not work reliably with panic=unwind on Windows. Let's make it
+    // an error to combine the two for now. It always runs into an assertions
+    // if LLVM is built with assertions, but without assertions it sometimes
+    // does not crash and will probably generate a corrupted binary.
+    if sess.opts.debugging_opts.pgo_gen.enabled() &&
+       sess.target.target.options.is_like_msvc &&
+       sess.panic_strategy() == PanicStrategy::Unwind {
+        sess.err("Profile-guided optimization does not yet work in conjunction \
+                  with `-Cpanic=unwind` on Windows when targeting MSVC. \
+                  See https://github.com/rust-lang/rust/issues/61002 for details.");
+    }
 }
 
 /// Hash value constructed out of all the `-C metadata` arguments passed to the
index 2fa896962daf9f6c5442241ee41188b62bdd0409..7505b3c1be8444b1995938f93b80c259bb4e2716 100644 (file)
@@ -307,9 +307,9 @@ fn evaluate_predicates<'b, 'gcx, 'c>(
                 continue;
             }
 
-            // Call infcx.resolve_type_vars_if_possible to see if we can
+            // Call infcx.resolve_vars_if_possible to see if we can
             // get rid of any inference variables.
-            let obligation = infcx.resolve_type_vars_if_possible(
+            let obligation = infcx.resolve_vars_if_possible(
                 &Obligation::new(dummy_cause.clone(), new_env, pred)
             );
             let result = select.select(&obligation);
@@ -642,7 +642,7 @@ fn evaluate_nested_obligations<
                 fresh_preds.insert(self.clean_pred(select.infcx(), predicate));
 
             // Resolve any inference variables that we can, to help selection succeed
-            predicate = select.infcx().resolve_type_vars_if_possible(&predicate);
+            predicate = select.infcx().resolve_vars_if_possible(&predicate);
 
             // We only add a predicate as a user-displayable bound if
             // it involves a generic parameter, and doesn't contain
index d9eb6d8157dfbdd3590af1e35eecd1fe10eb9510..a7b5e6cf41b779981a49d74ff4f09b1fa0c0775d 100644 (file)
@@ -33,7 +33,7 @@ fn in_environment(
     obligation: PredicateObligation<'tcx>
 ) -> InEnvironment<'tcx, PredicateObligation<'tcx>> {
     assert!(!infcx.is_in_snapshot());
-    let obligation = infcx.resolve_type_vars_if_possible(&obligation);
+    let obligation = infcx.resolve_vars_if_possible(&obligation);
 
     let environment = match obligation.param_env.def_id {
         Some(def_id) => infcx.tcx.environment(def_id),
index 7e3d6d752ccdcf83c96c0eb750f27e4ebba26eee..591557eb2bea5785efbea87f5f0883a0f498d7d7 100644 (file)
@@ -153,11 +153,11 @@ fn drain_fulfillment_cx_or_panic<T>(&self,
             bug!("Encountered errors `{:?}` resolving bounds after type-checking", errors);
         }
 
-        let result = self.resolve_type_vars_if_possible(result);
+        let result = self.resolve_vars_if_possible(result);
         let result = self.tcx.erase_regions(&result);
 
         self.tcx.lift_to_global(&result).unwrap_or_else(||
-            bug!("Uninferred types/regions in `{:?}`", result)
+            bug!("Uninferred types/regions/consts in `{:?}`", result)
         )
     }
 }
index afbce5a4f0a49170e83fd41347281b9eeca6e368..c6521a931bb29b0876e5f003ad40ece17beecabd 100644 (file)
@@ -155,7 +155,7 @@ fn overlap_within_probe(
         a_impl_header.predicates
                      .iter()
                      .chain(&b_impl_header.predicates)
-                     .map(|p| infcx.resolve_type_vars_if_possible(p))
+                     .map(|p| infcx.resolve_vars_if_possible(p))
                      .map(|p| Obligation { cause: ObligationCause::dummy(),
                                            param_env,
                                            recursion_depth: 0,
@@ -171,7 +171,7 @@ fn overlap_within_probe(
         return None
     }
 
-    let impl_header = selcx.infcx().resolve_type_vars_if_possible(&a_impl_header);
+    let impl_header = selcx.infcx().resolve_vars_if_possible(&a_impl_header);
     let intercrate_ambiguity_causes = selcx.take_intercrate_ambiguity_causes();
     debug!("overlap: intercrate_ambiguity_causes={:#?}", intercrate_ambiguity_causes);
 
index 9019c4a0575d40b9c5c12df1aa7fb6335cd946cf..5a2bf07b065f8747ea20c2898718afa7da71a5a2 100644 (file)
@@ -186,7 +186,7 @@ fn report_projection_error(&self,
                                error: &MismatchedProjectionTypes<'tcx>)
     {
         let predicate =
-            self.resolve_type_vars_if_possible(&obligation.predicate);
+            self.resolve_vars_if_possible(&obligation.predicate);
 
         if predicate.references_error() {
             return
@@ -531,7 +531,7 @@ pub fn report_overflow_error<T>(&self,
         where T: fmt::Display + TypeFoldable<'tcx>
     {
         let predicate =
-            self.resolve_type_vars_if_possible(&obligation.predicate);
+            self.resolve_vars_if_possible(&obligation.predicate);
         let mut err = struct_span_err!(self.tcx.sess, obligation.cause.span, E0275,
                                        "overflow evaluating the requirement `{}`",
                                        predicate);
@@ -553,7 +553,7 @@ pub fn report_overflow_error<T>(&self,
     /// we do not suggest increasing the overflow limit, which is not
     /// going to help).
     pub fn report_overflow_error_cycle(&self, cycle: &[PredicateObligation<'tcx>]) -> ! {
-        let cycle = self.resolve_type_vars_if_possible(&cycle.to_owned());
+        let cycle = self.resolve_vars_if_possible(&cycle.to_owned());
         assert!(cycle.len() > 0);
 
         debug!("report_overflow_error_cycle: cycle={:?}", cycle);
@@ -589,7 +589,7 @@ pub fn report_extra_impl_obligation(&self,
     fn get_parent_trait_ref(&self, code: &ObligationCauseCode<'tcx>) -> Option<String> {
         match code {
             &ObligationCauseCode::BuiltinDerivedObligation(ref data) => {
-                let parent_trait_ref = self.resolve_type_vars_if_possible(
+                let parent_trait_ref = self.resolve_vars_if_possible(
                     &data.parent_trait_ref);
                 match self.get_parent_trait_ref(&data.parent_code) {
                     Some(t) => Some(t),
@@ -625,7 +625,7 @@ pub fn report_selection_error(
                 match obligation.predicate {
                     ty::Predicate::Trait(ref trait_predicate) => {
                         let trait_predicate =
-                            self.resolve_type_vars_if_possible(trait_predicate);
+                            self.resolve_vars_if_possible(trait_predicate);
 
                         if self.tcx.sess.has_errors() && trait_predicate.references_error() {
                             return;
@@ -749,7 +749,7 @@ pub fn report_selection_error(
                     }
 
                     ty::Predicate::RegionOutlives(ref predicate) => {
-                        let predicate = self.resolve_type_vars_if_possible(predicate);
+                        let predicate = self.resolve_vars_if_possible(predicate);
                         let err = self.region_outlives_predicate(&obligation.cause,
                                                                  &predicate).err().unwrap();
                         struct_span_err!(
@@ -761,7 +761,7 @@ pub fn report_selection_error(
 
                     ty::Predicate::Projection(..) | ty::Predicate::TypeOutlives(..) => {
                         let predicate =
-                            self.resolve_type_vars_if_possible(&obligation.predicate);
+                            self.resolve_vars_if_possible(&obligation.predicate);
                         struct_span_err!(self.tcx.sess, span, E0280,
                             "the requirement `{}` is not satisfied",
                             predicate)
@@ -852,8 +852,8 @@ pub fn report_selection_error(
             }
 
             OutputTypeParameterMismatch(ref found_trait_ref, ref expected_trait_ref, _) => {
-                let found_trait_ref = self.resolve_type_vars_if_possible(&*found_trait_ref);
-                let expected_trait_ref = self.resolve_type_vars_if_possible(&*expected_trait_ref);
+                let found_trait_ref = self.resolve_vars_if_possible(&*found_trait_ref);
+                let expected_trait_ref = self.resolve_vars_if_possible(&*expected_trait_ref);
 
                 if expected_trait_ref.self_ty().references_error() {
                     return;
@@ -1345,7 +1345,7 @@ fn maybe_report_ambiguity(&self, obligation: &PredicateObligation<'tcx>,
         // ambiguous impls. The latter *ought* to be a
         // coherence violation, so we don't report it here.
 
-        let predicate = self.resolve_type_vars_if_possible(&obligation.predicate);
+        let predicate = self.resolve_vars_if_possible(&obligation.predicate);
         let span = obligation.cause.span;
 
         debug!("maybe_report_ambiguity(predicate={:?}, obligation={:?})",
@@ -1617,7 +1617,7 @@ fn note_obligation_cause_code<T>(&self,
                 err.note("shared static variables must have a type that implements `Sync`");
             }
             ObligationCauseCode::BuiltinDerivedObligation(ref data) => {
-                let parent_trait_ref = self.resolve_type_vars_if_possible(&data.parent_trait_ref);
+                let parent_trait_ref = self.resolve_vars_if_possible(&data.parent_trait_ref);
                 let ty = parent_trait_ref.skip_binder().self_ty();
                 err.note(&format!("required because it appears within the type `{}`", ty));
                 obligated_types.push(ty);
@@ -1631,7 +1631,7 @@ fn note_obligation_cause_code<T>(&self,
                 }
             }
             ObligationCauseCode::ImplDerivedObligation(ref data) => {
-                let parent_trait_ref = self.resolve_type_vars_if_possible(&data.parent_trait_ref);
+                let parent_trait_ref = self.resolve_vars_if_possible(&data.parent_trait_ref);
                 err.note(
                     &format!("required because of the requirements on the impl of `{}` for `{}`",
                              parent_trait_ref,
@@ -1672,7 +1672,7 @@ fn is_recursive_obligation(&self,
                                obligated_types: &mut Vec<&ty::TyS<'tcx>>,
                                cause_code: &ObligationCauseCode<'tcx>) -> bool {
         if let ObligationCauseCode::BuiltinDerivedObligation(ref data) = cause_code {
-            let parent_trait_ref = self.resolve_type_vars_if_possible(&data.parent_trait_ref);
+            let parent_trait_ref = self.resolve_vars_if_possible(&data.parent_trait_ref);
 
             if obligated_types.iter().any(|ot| ot == &parent_trait_ref.skip_binder().self_ty()) {
                 return true;
index 96212d829d44884cec1c4aef2d47e4b3093ecf43..c7943d16885bd018e134b4d4e48051dc5305e22d 100644 (file)
@@ -178,7 +178,7 @@ fn register_predicate_obligation<'a, 'gcx>(&mut self,
     {
         // this helps to reduce duplicate errors, as well as making
         // debug output much nicer to read and so on.
-        let obligation = infcx.resolve_type_vars_if_possible(&obligation);
+        let obligation = infcx.resolve_vars_if_possible(&obligation);
 
         debug!("register_predicate_obligation(obligation={:?})", obligation);
 
@@ -261,7 +261,7 @@ fn process_obligation(&mut self,
             }) {
                 debug!("process_predicate: pending obligation {:?} still stalled on {:?}",
                        self.selcx.infcx()
-                           .resolve_type_vars_if_possible(&pending_obligation.obligation),
+                           .resolve_vars_if_possible(&pending_obligation.obligation),
                        pending_obligation.stalled_on);
                 return ProcessResult::Unchanged;
             }
@@ -272,7 +272,7 @@ fn process_obligation(&mut self,
 
         if obligation.predicate.has_infer_types() {
             obligation.predicate =
-                self.selcx.infcx().resolve_type_vars_if_possible(&obligation.predicate);
+                self.selcx.infcx().resolve_vars_if_possible(&obligation.predicate);
         }
 
         debug!("process_obligation: obligation = {:?}", obligation);
@@ -318,7 +318,7 @@ fn process_obligation(&mut self,
                             trait_ref_type_vars(self.selcx, data.to_poly_trait_ref());
 
                         debug!("process_predicate: pending obligation {:?} now stalled on {:?}",
-                               self.selcx.infcx().resolve_type_vars_if_possible(obligation),
+                               self.selcx.infcx().resolve_vars_if_possible(obligation),
                                pending_obligation.stalled_on);
 
                         ProcessResult::Unchanged
@@ -519,7 +519,7 @@ fn trait_ref_type_vars<'a, 'gcx, 'tcx>(selcx: &mut SelectionContext<'a, 'gcx, 't
 {
     t.skip_binder() // ok b/c this check doesn't care about regions
      .input_types()
-     .map(|t| selcx.infcx().resolve_type_vars_if_possible(&t))
+     .map(|t| selcx.infcx().resolve_vars_if_possible(&t))
      .filter(|t| t.has_infer_types())
      .flat_map(|t| t.walk())
      .filter(|t| match t.sty { ty::Infer(_) => true, _ => false })
index 4b555e54f397da8e3581262b9527208e2168a097..c135b0b759c6f2d3574917667d4e8db90c41a72a 100644 (file)
@@ -927,7 +927,7 @@ pub fn fully_normalize<'a, 'gcx, 'tcx, T>(
     debug!("fully_normalize: select_all_or_error start");
     fulfill_cx.select_all_or_error(infcx)?;
     debug!("fully_normalize: select_all_or_error complete");
-    let resolved_value = infcx.resolve_type_vars_if_possible(&normalized_value);
+    let resolved_value = infcx.resolve_vars_if_possible(&normalized_value);
     debug!("fully_normalize: resolved_value={:?}", resolved_value);
     Ok(resolved_value)
 }
index 92d5d4f03190313ef5952c51fee1cf7e45ef8e87..88bb3172c5e79f84edea0de30cca5d111c2b0653 100644 (file)
@@ -312,7 +312,7 @@ fn new(selcx: &'a mut SelectionContext<'b, 'gcx, 'tcx>,
     }
 
     fn fold<T:TypeFoldable<'tcx>>(&mut self, value: &T) -> T {
-        let value = self.selcx.infcx().resolve_type_vars_if_possible(value);
+        let value = self.selcx.infcx().resolve_vars_if_possible(value);
 
         if !value.has_projections() {
             value
@@ -508,7 +508,7 @@ fn opt_normalize_projection_type<'a, 'b, 'gcx, 'tcx>(
 {
     let infcx = selcx.infcx();
 
-    let projection_ty = infcx.resolve_type_vars_if_possible(&projection_ty);
+    let projection_ty = infcx.resolve_vars_if_possible(&projection_ty);
     let cache_key = ProjectionCacheKey { ty: projection_ty };
 
     debug!("opt_normalize_projection_type(\
@@ -1614,7 +1614,7 @@ pub fn from_poly_projection_predicate(selcx: &mut SelectionContext<'cx, 'gcx, 't
                 // from a specific call to `opt_normalize_projection_type` - if
                 // there's no precise match, the original cache entry is "stranded"
                 // anyway.
-                ty: infcx.resolve_type_vars_if_possible(&predicate.projection_ty)
+                ty: infcx.resolve_vars_if_possible(&predicate.projection_ty)
             })
     }
 }
index 5800b024ad2459bfefd064b261e1df428cef5eda..c4aa14d2b7ebcb69472d82ab5d0db1e3db695668 100644 (file)
@@ -54,7 +54,7 @@ pub fn dropck_outlives(&self, ty: Ty<'tcx>) -> InferOk<'tcx, Vec<Kind<'tcx>>> {
                     &orig_values,
                     result)
                 {
-                    let ty = self.infcx.resolve_type_vars_if_possible(&ty);
+                    let ty = self.infcx.resolve_vars_if_possible(&ty);
                     let kinds = value.into_kinds_reporting_overflows(tcx, span, ty);
                     return InferOk {
                         value: kinds,
index 7e38282cc1adcd2d1d19dd4196f76cb7fb99f3c3..5933d2366e81c337a16652a2a5faa0e935d11a59 100644 (file)
@@ -97,7 +97,7 @@ fn scrape_region_constraints<'gcx, 'tcx, R>(
         region_obligations
             .iter()
             .map(|(_, r_o)| (r_o.sup_type, r_o.sub_region))
-            .map(|(ty, r)| (infcx.resolve_type_vars_if_possible(&ty), r)),
+            .map(|(ty, r)| (infcx.resolve_vars_if_possible(&ty), r)),
         &region_constraint_data,
     );
 
index ec5e127a5ec4b0b4e326a628ef970cea839d2e7b..ba96233b85328191b0491c8e5c0793f410313b62 100644 (file)
@@ -1463,7 +1463,7 @@ fn is_knowable<'o>(&mut self, stack: &TraitObligationStack<'o, 'tcx>) -> Option<
 
         let obligation = &stack.obligation;
         let predicate = self.infcx()
-            .resolve_type_vars_if_possible(&obligation.predicate);
+            .resolve_vars_if_possible(&obligation.predicate);
 
         // OK to skip binder because of the nature of the
         // trait-ref-is-knowable check, which does not care about
@@ -1621,7 +1621,7 @@ fn assemble_candidates<'o>(
             cause: obligation.cause.clone(),
             recursion_depth: obligation.recursion_depth,
             predicate: self.infcx()
-                .resolve_type_vars_if_possible(&obligation.predicate),
+                .resolve_vars_if_possible(&obligation.predicate),
         };
 
         if obligation.predicate.skip_binder().self_ty().is_ty_var() {
@@ -1737,7 +1737,7 @@ fn match_projection_obligation_against_definition_bounds(
         snapshot: &CombinedSnapshot<'_, 'tcx>,
     ) -> bool {
         let poly_trait_predicate = self.infcx()
-            .resolve_type_vars_if_possible(&obligation.predicate);
+            .resolve_vars_if_possible(&obligation.predicate);
         let (placeholder_trait_predicate, placeholder_map) = self.infcx()
             .replace_bound_vars_with_placeholders(&poly_trait_predicate);
         debug!(
index 5da4a1b9c5f36f81e4206d52706117e67b00d316..b5d45d040fb99e25382a9876e1f2d34bb85b4f5b 100644 (file)
@@ -278,7 +278,7 @@ fn fulfill_implication<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>,
 
                 // Now resolve the *substitution* we built for the target earlier, replacing
                 // the inference variables inside with whatever we got from fulfillment.
-                Ok(infcx.resolve_type_vars_if_possible(&target_substs))
+                Ok(infcx.resolve_vars_if_possible(&target_substs))
             }
         }
     })
index a56fe7d7003a1b0e31d1abce55b2fb1f0f78859e..ff218911ffb8197afca886679b666f392fca5cf2 100644 (file)
@@ -23,7 +23,7 @@
 use crate::middle::lang_items;
 use crate::middle::resolve_lifetime::{self, ObjectLifetimeDefault};
 use crate::middle::stability;
-use crate::mir::{self, Mir, interpret, ProjectionKind};
+use crate::mir::{self, Body, interpret, ProjectionKind};
 use crate::mir::interpret::{ConstValue, Allocation, Scalar};
 use crate::ty::subst::{Kind, InternalSubsts, SubstsRef, Subst};
 use crate::ty::ReprOptions;
@@ -103,8 +103,8 @@ pub struct GlobalArenas<'tcx> {
     generics: TypedArena<ty::Generics>,
     trait_def: TypedArena<ty::TraitDef>,
     adt_def: TypedArena<ty::AdtDef>,
-    steal_mir: TypedArena<Steal<Mir<'tcx>>>,
-    mir: TypedArena<Mir<'tcx>>,
+    steal_mir: TypedArena<Steal<Body<'tcx>>>,
+    mir: TypedArena<Body<'tcx>>,
     tables: TypedArena<ty::TypeckTables<'tcx>>,
     /// miri allocations
     const_allocs: TypedArena<interpret::Allocation>,
@@ -1001,7 +1001,7 @@ fn new(interners: &CtxtInterners<'tcx>, types: &CommonTypes<'tcx>) -> CommonCons
 
         CommonConsts {
             err: mk_const(ty::Const {
-                val: ConstValue::Scalar(Scalar::Bits { bits: 0, size: 0 }),
+                val: ConstValue::Scalar(Scalar::zst()),
                 ty: types.err,
             }),
         }
@@ -1154,11 +1154,11 @@ pub fn alloc_generics(self, generics: ty::Generics) -> &'gcx ty::Generics {
         self.global_arenas.generics.alloc(generics)
     }
 
-    pub fn alloc_steal_mir(self, mir: Mir<'gcx>) -> &'gcx Steal<Mir<'gcx>> {
+    pub fn alloc_steal_mir(self, mir: Body<'gcx>) -> &'gcx Steal<Body<'gcx>> {
         self.global_arenas.steal_mir.alloc(Steal::new(mir))
     }
 
-    pub fn alloc_mir(self, mir: Mir<'gcx>) -> &'gcx Mir<'gcx> {
+    pub fn alloc_mir(self, mir: Body<'gcx>) -> &'gcx Body<'gcx> {
         self.global_arenas.mir.alloc(mir)
     }
 
index 4e4024d5bab43e67ba507a02be7d3b68d825daad..09426fe19e11eac2c21991aae10fc21dd6c9dc01 100644 (file)
@@ -80,6 +80,12 @@ fn report_maybe_different(f: &mut fmt::Formatter<'_>,
             }
         };
 
+        macro_rules! pluralise {
+            ($x:expr) => {
+                if $x != 1 { "s" } else { "" }
+            };
+        }
+
         match *self {
             CyclicTy(_) => write!(f, "cyclic type of infinite size"),
             Mismatch => write!(f, "types differ"),
@@ -94,17 +100,21 @@ fn report_maybe_different(f: &mut fmt::Formatter<'_>,
                        values.found)
             }
             Mutability => write!(f, "types differ in mutability"),
-            FixedArraySize(values) => {
-                write!(f, "expected an array with a fixed size of {} elements, \
-                           found one with {} elements",
+            TupleSize(values) => {
+                write!(f, "expected a tuple with {} element{}, \
+                           found one with {} element{}",
                        values.expected,
-                       values.found)
+                       pluralise!(values.expected),
+                       values.found,
+                       pluralise!(values.found))
             }
-            TupleSize(values) => {
-                write!(f, "expected a tuple with {} elements, \
-                           found one with {} elements",
+            FixedArraySize(values) => {
+                write!(f, "expected an array with a fixed size of {} element{}, \
+                           found one with {} element{}",
                        values.expected,
-                       values.found)
+                       pluralise!(values.expected),
+                       values.found,
+                       pluralise!(values.found))
             }
             ArgCount => {
                 write!(f, "incorrect number of function parameters")
@@ -157,8 +167,9 @@ fn report_maybe_different(f: &mut fmt::Formatter<'_>,
                        tcx.def_path_str(values.found))
             }),
             ProjectionBoundsLength(ref values) => {
-                write!(f, "expected {} associated type bindings, found {}",
+                write!(f, "expected {} associated type binding{}, found {}",
                        values.expected,
+                       pluralise!(values.expected),
                        values.found)
             },
             ExistentialMismatch(ref values) => {
@@ -166,7 +177,7 @@ fn report_maybe_different(f: &mut fmt::Formatter<'_>,
                                        &format!("trait `{}`", values.found))
             }
             ConstMismatch(ref values) => {
-                write!(f, "expected `{:?}`, found `{:?}`", values.expected, values.found)
+                write!(f, "expected `{}`, found `{}`", values.expected, values.found)
             }
         }
     }
index f1d1abfa0fb4b55978bcdbd196887beab35aa4dd..fa993325e271233e362d6c850626eb58f6e631f5 100644 (file)
@@ -19,7 +19,7 @@
 use crate::infer::canonical::Canonical;
 use crate::middle::lang_items::{FnTraitLangItem, FnMutTraitLangItem, FnOnceTraitLangItem};
 use crate::middle::resolve_lifetime::ObjectLifetimeDefault;
-use crate::mir::Mir;
+use crate::mir::Body;
 use crate::mir::interpret::{GlobalId, ErrorHandled};
 use crate::mir::GeneratorLayout;
 use crate::session::CrateDisambiguator;
@@ -3002,7 +3002,7 @@ pub fn item_name(self, id: DefId) -> Symbol {
 
     /// Returns the possibly-auto-generated MIR of a `(DefId, Subst)` pair.
     pub fn instance_mir(self, instance: ty::InstanceDef<'gcx>)
-                        -> &'gcx Mir<'gcx>
+                        -> &'gcx Body<'gcx>
     {
         match instance {
             ty::InstanceDef::Item(did) => {
index 4b4dd5d88d93add28055afb84bd9b0a7272af36a..a246d9652f2f045ef3b1c9667b736c191e0d2d62 100644 (file)
@@ -845,22 +845,22 @@ fn pretty_print_const(
             p!(write("{}", name));
             return Ok(self);
         }
-        if let ConstValue::Scalar(Scalar::Bits { bits, .. }) = ct.val {
+        if let ConstValue::Scalar(Scalar::Raw { data, .. }) = ct.val {
             match ct.ty.sty {
                 ty::Bool => {
-                    p!(write("{}", if bits == 0 { "false" } else { "true" }));
+                    p!(write("{}", if data == 0 { "false" } else { "true" }));
                     return Ok(self);
                 },
                 ty::Float(ast::FloatTy::F32) => {
-                    p!(write("{}f32", Single::from_bits(bits)));
+                    p!(write("{}f32", Single::from_bits(data)));
                     return Ok(self);
                 },
                 ty::Float(ast::FloatTy::F64) => {
-                    p!(write("{}f64", Double::from_bits(bits)));
+                    p!(write("{}f64", Double::from_bits(data)));
                     return Ok(self);
                 },
                 ty::Uint(ui) => {
-                    p!(write("{}{}", bits, ui));
+                    p!(write("{}{}", data, ui));
                     return Ok(self);
                 },
                 ty::Int(i) =>{
@@ -868,11 +868,11 @@ fn pretty_print_const(
                     let size = self.tcx().layout_of(ty::ParamEnv::empty().and(ty))
                         .unwrap()
                         .size;
-                    p!(write("{}{}", sign_extend(bits, size) as i128, i));
+                    p!(write("{}{}", sign_extend(data, size) as i128, i));
                     return Ok(self);
                 },
                 ty::Char => {
-                    p!(write("{:?}", ::std::char::from_u32(bits as u32).unwrap()));
+                    p!(write("{:?}", ::std::char::from_u32(data as u32).unwrap()));
                     return Ok(self);
                 }
                 _ => {},
index 2049341327495bc822005f99a131df03f1ef1542..0440be13a7271faa361d58ee08ba859f74937170 100644 (file)
@@ -8,9 +8,7 @@
 use crate::ty::subst::{Kind, UnpackedKind, SubstsRef};
 use crate::ty::{self, Ty, TyCtxt, TypeFoldable};
 use crate::ty::error::{ExpectedFound, TypeError};
-use crate::mir::interpret::{GlobalId, ConstValue, Scalar};
-use crate::util::common::ErrorReported;
-use syntax_pos::DUMMY_SP;
+use crate::mir::interpret::{ConstValue, Scalar, GlobalId};
 use std::rc::Rc;
 use std::iter;
 use rustc_target::spec::abi;
@@ -474,55 +472,19 @@ pub fn super_relate_tys<'a, 'gcx, 'tcx, R>(relation: &mut R,
         (&ty::Array(a_t, sz_a), &ty::Array(b_t, sz_b)) =>
         {
             let t = relation.relate(&a_t, &b_t)?;
-            let to_u64 = |x: ty::Const<'tcx>| -> Result<u64, ErrorReported> {
-                match x.val {
-                    // FIXME(const_generics): this doesn't work right now,
-                    // because it tries to relate an `Infer` to a `Param`.
-                    ConstValue::Unevaluated(def_id, substs) => {
-                        // FIXME(eddyb) get the right param_env.
-                        let param_env = ty::ParamEnv::empty();
-                        if let Some(substs) = tcx.lift_to_global(&substs) {
-                            let instance = ty::Instance::resolve(
-                                tcx.global_tcx(),
-                                param_env,
-                                def_id,
-                                substs,
-                            );
-                            if let Some(instance) = instance {
-                                let cid = GlobalId {
-                                    instance,
-                                    promoted: None,
-                                };
-                                if let Some(s) = tcx.const_eval(param_env.and(cid))
-                                                    .ok()
-                                                    .map(|c| c.unwrap_usize(tcx)) {
-                                    return Ok(s)
-                                }
-                            }
+            match relation.relate(&sz_a, &sz_b) {
+                Ok(sz) => Ok(tcx.mk_ty(ty::Array(t, sz))),
+                Err(err) => {
+                    // Check whether the lengths are both concrete/known values,
+                    // but are unequal, for better diagnostics.
+                    match (sz_a.assert_usize(tcx), sz_b.assert_usize(tcx)) {
+                        (Some(sz_a_val), Some(sz_b_val)) => {
+                            Err(TypeError::FixedArraySize(
+                                expected_found(relation, &sz_a_val, &sz_b_val)
+                            ))
                         }
-                        tcx.sess.delay_span_bug(tcx.def_span(def_id),
-                            "array length could not be evaluated");
-                        Err(ErrorReported)
+                        _ => return Err(err),
                     }
-                    _ => x.assert_usize(tcx).ok_or_else(|| {
-                        tcx.sess.delay_span_bug(DUMMY_SP,
-                            "array length could not be evaluated");
-                        ErrorReported
-                    })
-                }
-            };
-            match (to_u64(*sz_a), to_u64(*sz_b)) {
-                (Ok(sz_a_u64), Ok(sz_b_u64)) => {
-                    if sz_a_u64 == sz_b_u64 {
-                        Ok(tcx.mk_ty(ty::Array(t, sz_a)))
-                    } else {
-                        Err(TypeError::FixedArraySize(
-                            expected_found(relation, &sz_a_u64, &sz_b_u64)))
-                    }
-                }
-                // We reported an error or will ICE, so we can return Error.
-                (Err(ErrorReported), _) | (_, Err(ErrorReported)) => {
-                    Ok(tcx.types.err)
                 }
             }
         }
@@ -598,11 +560,36 @@ pub fn super_relate_consts<'a, 'gcx, 'tcx, R>(
 {
     let tcx = relation.tcx();
 
+    let eagerly_eval = |x: &'tcx ty::Const<'tcx>| {
+        if let ConstValue::Unevaluated(def_id, substs) = x.val {
+            // FIXME(eddyb) get the right param_env.
+            let param_env = ty::ParamEnv::empty();
+            if let Some(substs) = tcx.lift_to_global(&substs) {
+                let instance = ty::Instance::resolve(
+                    tcx.global_tcx(),
+                    param_env,
+                    def_id,
+                    substs,
+                );
+                if let Some(instance) = instance {
+                    let cid = GlobalId {
+                        instance,
+                        promoted: None,
+                    };
+                    if let Ok(ct) = tcx.const_eval(param_env.and(cid)) {
+                        return ct.val;
+                    }
+                }
+            }
+        }
+        x.val
+    };
+
     // Currently, the values that can be unified are those that
     // implement both `PartialEq` and `Eq`, corresponding to
     // `structural_match` types.
     // FIXME(const_generics): check for `structural_match` synthetic attribute.
-    match (a.val, b.val) {
+    match (eagerly_eval(a), eagerly_eval(b)) {
         (ConstValue::Infer(_), _) | (_, ConstValue::Infer(_)) => {
             // The caller should handle these cases!
             bug!("var types encountered in super_relate_consts: {:?} {:?}", a, b)
@@ -613,8 +600,13 @@ pub fn super_relate_consts<'a, 'gcx, 'tcx, R>(
         (ConstValue::Placeholder(p1), ConstValue::Placeholder(p2)) if p1 == p2 => {
             Ok(a)
         }
-        (ConstValue::Scalar(Scalar::Bits { .. }), _) if a == b => {
-            Ok(a)
+        (a_val @ ConstValue::Scalar(Scalar::Raw { .. }), b_val @ _)
+            if a.ty == b.ty && a_val == b_val =>
+        {
+            Ok(tcx.mk_const(ty::Const {
+                val: a_val,
+                ty: a.ty,
+            }))
         }
         (ConstValue::ByRef(..), _) => {
             bug!(
@@ -635,9 +627,7 @@ pub fn super_relate_consts<'a, 'gcx, 'tcx, R>(
                 }))
             }
 
-            _ => {
-            Err(TypeError::ConstMismatch(expected_found(relation, &a, &b)))
-        }
+        _ => Err(TypeError::ConstMismatch(expected_found(relation, &a, &b))),
     }
 }
 
index a8f9301ba51c96c74fea8e5e3ef0035a87247384..711e59dbcc9d2752b3c35b9a1b7bbcdb36fdc787 100644 (file)
@@ -7,9 +7,9 @@
 /// optimization, but that'd be expensive. And yet we don't just want
 /// to mutate it in place, because that would spoil the idea that
 /// queries are these pure functions that produce an immutable value
-/// (since if you did the query twice, you could observe the
-/// mutations). So instead we have the query produce a `&'tcx
-/// Steal<Mir<'tcx>>` (to be very specific). Now we can read from this
+/// (since if you did the query twice, you could observe the mutations).
+/// So instead we have the query produce a `&'tcx Steal<mir::Body<'tcx>>`
+/// (to be very specific). Now we can read from this
 /// as much as we want (using `borrow()`), but you can also
 /// `steal()`. Once you steal, any further attempt to read will panic.
 /// Therefore, we know that -- assuming no ICE -- nobody is observing
index 4711429502f3fd5c1eb17273523844f193718ff8..0a673dd380b5254416da4ea452c86d6f1e7dbc60 100644 (file)
@@ -3,7 +3,7 @@
 use crate::hir;
 use crate::hir::def_id::DefId;
 use crate::infer::canonical::Canonical;
-use crate::mir::interpret::{ConstValue, truncate};
+use crate::mir::interpret::ConstValue;
 use crate::middle::region;
 use polonius_engine::Atom;
 use rustc_data_structures::indexed_vec::Idx;
@@ -2232,14 +2232,12 @@ pub fn from_bits(
         let size = tcx.layout_of(ty).unwrap_or_else(|e| {
             panic!("could not compute layout for {:?}: {:?}", ty, e)
         }).size;
-        let truncated = truncate(bits, size);
-        assert_eq!(truncated, bits, "from_bits called with untruncated value");
-        Self::from_scalar(tcx, Scalar::Bits { bits, size: size.bytes() as u8 }, ty.value)
+        Self::from_scalar(tcx, Scalar::from_uint(bits, size), ty.value)
     }
 
     #[inline]
     pub fn zero_sized(tcx: TyCtxt<'_, '_, 'tcx>, ty: Ty<'tcx>) -> &'tcx Self {
-        Self::from_scalar(tcx, Scalar::Bits { bits: 0, size: 0 }, ty)
+        Self::from_scalar(tcx, Scalar::zst(), ty)
     }
 
     #[inline]
index 585970e64df8d65b1a73636af3a4dd688fe71a17..8624856a4f55ca96fd0da56bc62403445bd47f07 100644 (file)
@@ -1,6 +1,8 @@
 use std::borrow::Cow;
 use std::error::Error;
+use std::fs;
 use std::mem::{self, Discriminant};
+use std::path::Path;
 use std::process;
 use std::thread::ThreadId;
 use std::u32;
@@ -71,10 +73,17 @@ pub struct SelfProfiler {
 }
 
 impl SelfProfiler {
-    pub fn new(event_filters: &Option<Vec<String>>) -> Result<SelfProfiler, Box<dyn Error>> {
-        let filename = format!("pid-{}.rustc_profile", process::id());
-        let path = std::path::Path::new(&filename);
-        let profiler = Profiler::new(path)?;
+    pub fn new(
+        output_directory: &Path,
+        crate_name: Option<&str>,
+        event_filters: &Option<Vec<String>>
+    ) -> Result<SelfProfiler, Box<dyn Error>> {
+        fs::create_dir_all(output_directory)?;
+
+        let crate_name = crate_name.unwrap_or("unknown-crate");
+        let filename = format!("{}-{}.rustc_profile", crate_name, process::id());
+        let path = output_directory.join(&filename);
+        let profiler = Profiler::new(&path)?;
 
         let query_event_kind = profiler.alloc_string("Query");
         let generic_activity_event_kind = profiler.alloc_string("GenericActivity");
index 1eee9ab8c0b67cdd6f9807498a5896ce77e6acd5..d8a9f681639a049d28063c7d9cb348c1c81c57a7 100644 (file)
@@ -13,7 +13,7 @@
 use rustc::hir::def_id::LOCAL_CRATE;
 use rustc_codegen_ssa::back::write::{CodegenContext, ModuleConfig, run_assembler};
 use rustc_codegen_ssa::traits::*;
-use rustc::session::config::{self, OutputType, Passes, Lto, PgoGenerate};
+use rustc::session::config::{self, OutputType, Passes, Lto, SwitchWithOptPath};
 use rustc::session::Session;
 use rustc::ty::TyCtxt;
 use rustc_codegen_ssa::{RLIB_BYTECODE_EXTENSION, ModuleCodegen, CompiledModule};
@@ -707,7 +707,7 @@ pub unsafe fn with_llvm_pmb(llmod: &llvm::Module,
     let inline_threshold = config.inline_threshold;
 
     let pgo_gen_path = match config.pgo_gen {
-        PgoGenerate::Enabled(ref opt_dir_path) => {
+        SwitchWithOptPath::Enabled(ref opt_dir_path) => {
             let path = if let Some(dir_path) = opt_dir_path {
                 dir_path.join("default_%m.profraw")
             } else {
@@ -716,7 +716,7 @@ pub unsafe fn with_llvm_pmb(llmod: &llvm::Module,
 
             Some(CString::new(format!("{}", path.display())).unwrap())
         }
-        PgoGenerate::Disabled => {
+        SwitchWithOptPath::Disabled => {
             None
         }
     };
index 9077e89a4020eae8cc5b479ec13d83d6b1d89008..f8c6087373f1eb9218bd24c475e22bb6a8d417b6 100644 (file)
@@ -24,7 +24,7 @@
 use crate::context::CodegenCx;
 use crate::monomorphize::partitioning::CodegenUnitExt;
 use rustc::dep_graph;
-use rustc::mir::mono::{Linkage, Visibility, Stats};
+use rustc::mir::mono::{Linkage, Visibility};
 use rustc::middle::cstore::{EncodedMetadata};
 use rustc::ty::TyCtxt;
 use rustc::middle::exported_symbols;
@@ -104,17 +104,17 @@ pub fn iter_globals(llmod: &'ll llvm::Module) -> ValueIter<'ll> {
     }
 }
 
-pub fn compile_codegen_unit<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                                  cgu_name: InternedString)
-                                  -> Stats {
+pub fn compile_codegen_unit(tcx: TyCtxt<'a, 'tcx, 'tcx>, cgu_name: InternedString) {
     let start_time = Instant::now();
 
     let dep_node = tcx.codegen_unit(cgu_name).codegen_dep_node(tcx);
-    let ((stats, module), _) = tcx.dep_graph.with_task(dep_node,
-                                                       tcx,
-                                                       cgu_name,
-                                                       module_codegen,
-                                                       dep_graph::hash_result);
+    let (module, _) = tcx.dep_graph.with_task(
+        dep_node,
+        tcx,
+        cgu_name,
+        module_codegen,
+        dep_graph::hash_result,
+    );
     let time_to_codegen = start_time.elapsed();
 
     // We assume that the cost to run LLVM on a CGU is proportional to
@@ -123,17 +123,15 @@ pub fn compile_codegen_unit<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                time_to_codegen.subsec_nanos() as u64;
 
     submit_codegened_module_to_llvm(&LlvmCodegenBackend(()), tcx, module, cost);
-    return stats;
 
     fn module_codegen<'ll, 'tcx>(
         tcx: TyCtxt<'ll, 'tcx, 'tcx>,
-        cgu_name: InternedString)
-        -> (Stats, ModuleCodegen<ModuleLlvm>)
-    {
+        cgu_name: InternedString,
+    ) -> ModuleCodegen<ModuleLlvm> {
         let cgu = tcx.codegen_unit(cgu_name);
         // Instantiate monomorphizations without filling out definitions yet...
         let llvm_module = ModuleLlvm::new(tcx, &cgu_name.as_str());
-        let stats = {
+        {
             let cx = CodegenCx::new(tcx, cgu, &llvm_module);
             let mono_items = cx.codegen_unit
                                .items_in_deterministic_order(cx.tcx);
@@ -169,15 +167,13 @@ fn module_codegen<'ll, 'tcx>(
             if cx.sess().opts.debuginfo != DebugInfo::None {
                 cx.debuginfo_finalize();
             }
+        }
 
-            cx.consume_stats().into_inner()
-        };
-
-        (stats, ModuleCodegen {
+        ModuleCodegen {
             name: cgu_name.to_string(),
             module_llvm: llvm_module,
             kind: ModuleKind::Regular,
-        })
+        }
     }
 }
 
index 48808eea3045ea892382cf08046db9297eb4c466..42e7a72c43b217cffdcd9615347bd7a3f0772722 100644 (file)
@@ -147,21 +147,18 @@ fn position_at_end(&mut self, llbb: &'ll BasicBlock) {
     }
 
     fn ret_void(&mut self) {
-        self.count_insn("retvoid");
         unsafe {
             llvm::LLVMBuildRetVoid(self.llbuilder);
         }
     }
 
     fn ret(&mut self, v: &'ll Value) {
-        self.count_insn("ret");
         unsafe {
             llvm::LLVMBuildRet(self.llbuilder, v);
         }
     }
 
     fn br(&mut self, dest: &'ll BasicBlock) {
-        self.count_insn("br");
         unsafe {
             llvm::LLVMBuildBr(self.llbuilder, dest);
         }
@@ -173,7 +170,6 @@ fn cond_br(
         then_llbb: &'ll BasicBlock,
         else_llbb: &'ll BasicBlock,
     ) {
-        self.count_insn("condbr");
         unsafe {
             llvm::LLVMBuildCondBr(self.llbuilder, cond, then_llbb, else_llbb);
         }
@@ -204,7 +200,6 @@ fn invoke(
         catch: &'ll BasicBlock,
         funclet: Option<&Funclet<'ll>>,
     ) -> &'ll Value {
-        self.count_insn("invoke");
 
         debug!("Invoke {:?} with args ({:?})",
                llfn,
@@ -227,7 +222,6 @@ fn invoke(
     }
 
     fn unreachable(&mut self) {
-        self.count_insn("unreachable");
         unsafe {
             llvm::LLVMBuildUnreachable(self.llbuilder);
         }
@@ -235,21 +229,18 @@ fn unreachable(&mut self) {
 
     /* Arithmetic */
     fn add(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("add");
         unsafe {
             llvm::LLVMBuildAdd(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fadd(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fadd");
         unsafe {
             llvm::LLVMBuildFAdd(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fadd_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fadd");
         unsafe {
             let instr = llvm::LLVMBuildFAdd(self.llbuilder, lhs, rhs, noname());
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -258,21 +249,18 @@ fn fadd_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
     }
 
     fn sub(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("sub");
         unsafe {
             llvm::LLVMBuildSub(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fsub(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fsub");
         unsafe {
             llvm::LLVMBuildFSub(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fsub_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fsub");
         unsafe {
             let instr = llvm::LLVMBuildFSub(self.llbuilder, lhs, rhs, noname());
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -281,21 +269,18 @@ fn fsub_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
     }
 
     fn mul(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("mul");
         unsafe {
             llvm::LLVMBuildMul(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fmul(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fmul");
         unsafe {
             llvm::LLVMBuildFMul(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fmul_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fmul");
         unsafe {
             let instr = llvm::LLVMBuildFMul(self.llbuilder, lhs, rhs, noname());
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -305,42 +290,36 @@ fn fmul_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
 
 
     fn udiv(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("udiv");
         unsafe {
             llvm::LLVMBuildUDiv(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn exactudiv(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("exactudiv");
         unsafe {
             llvm::LLVMBuildExactUDiv(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn sdiv(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("sdiv");
         unsafe {
             llvm::LLVMBuildSDiv(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn exactsdiv(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("exactsdiv");
         unsafe {
             llvm::LLVMBuildExactSDiv(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fdiv(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fdiv");
         unsafe {
             llvm::LLVMBuildFDiv(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn fdiv_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fdiv");
         unsafe {
             let instr = llvm::LLVMBuildFDiv(self.llbuilder, lhs, rhs, noname());
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -349,28 +328,24 @@ fn fdiv_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
     }
 
     fn urem(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("urem");
         unsafe {
             llvm::LLVMBuildURem(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn srem(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("srem");
         unsafe {
             llvm::LLVMBuildSRem(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn frem(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("frem");
         unsafe {
             llvm::LLVMBuildFRem(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn frem_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("frem");
         unsafe {
             let instr = llvm::LLVMBuildFRem(self.llbuilder, lhs, rhs, noname());
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -379,63 +354,54 @@ fn frem_fast(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
     }
 
     fn shl(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("shl");
         unsafe {
             llvm::LLVMBuildShl(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn lshr(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("lshr");
         unsafe {
             llvm::LLVMBuildLShr(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn ashr(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("ashr");
         unsafe {
             llvm::LLVMBuildAShr(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn and(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("and");
         unsafe {
             llvm::LLVMBuildAnd(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn or(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("or");
         unsafe {
             llvm::LLVMBuildOr(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn xor(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("xor");
         unsafe {
             llvm::LLVMBuildXor(self.llbuilder, lhs, rhs, noname())
         }
     }
 
     fn neg(&mut self, v: &'ll Value) -> &'ll Value {
-        self.count_insn("neg");
         unsafe {
             llvm::LLVMBuildNeg(self.llbuilder, v, noname())
         }
     }
 
     fn fneg(&mut self, v: &'ll Value) -> &'ll Value {
-        self.count_insn("fneg");
         unsafe {
             llvm::LLVMBuildFNeg(self.llbuilder, v, noname())
         }
     }
 
     fn not(&mut self, v: &'ll Value) -> &'ll Value {
-        self.count_insn("not");
         unsafe {
             llvm::LLVMBuildNot(self.llbuilder, v, noname())
         }
@@ -524,7 +490,6 @@ fn alloca(&mut self, ty: &'ll Type, name: &str, align: Align) -> &'ll Value {
     }
 
     fn dynamic_alloca(&mut self, ty: &'ll Type, name: &str, align: Align) -> &'ll Value {
-        self.count_insn("alloca");
         unsafe {
             let alloca = if name.is_empty() {
                 llvm::LLVMBuildAlloca(self.llbuilder, ty, noname())
@@ -543,7 +508,6 @@ fn array_alloca(&mut self,
                         len: &'ll Value,
                         name: &str,
                         align: Align) -> &'ll Value {
-        self.count_insn("alloca");
         unsafe {
             let alloca = if name.is_empty() {
                 llvm::LLVMBuildArrayAlloca(self.llbuilder, ty, len, noname())
@@ -558,7 +522,6 @@ fn array_alloca(&mut self,
     }
 
     fn load(&mut self, ptr: &'ll Value, align: Align) -> &'ll Value {
-        self.count_insn("load");
         unsafe {
             let load = llvm::LLVMBuildLoad(self.llbuilder, ptr, noname());
             llvm::LLVMSetAlignment(load, align.bytes() as c_uint);
@@ -567,11 +530,10 @@ fn load(&mut self, ptr: &'ll Value, align: Align) -> &'ll Value {
     }
 
     fn volatile_load(&mut self, ptr: &'ll Value) -> &'ll Value {
-        self.count_insn("load.volatile");
         unsafe {
-            let insn = llvm::LLVMBuildLoad(self.llbuilder, ptr, noname());
-            llvm::LLVMSetVolatile(insn, llvm::True);
-            insn
+            let load = llvm::LLVMBuildLoad(self.llbuilder, ptr, noname());
+            llvm::LLVMSetVolatile(load, llvm::True);
+            load
         }
     }
 
@@ -581,7 +543,6 @@ fn atomic_load(
         order: rustc_codegen_ssa::common::AtomicOrdering,
         size: Size,
     ) -> &'ll Value {
-        self.count_insn("load.atomic");
         unsafe {
             let load = llvm::LLVMRustBuildAtomicLoad(
                 self.llbuilder,
@@ -745,7 +706,6 @@ fn store_with_flags(
         flags: MemFlags,
     ) -> &'ll Value {
         debug!("Store {:?} -> {:?} ({:?})", val, ptr, flags);
-        self.count_insn("store");
         let ptr = self.check_store(val, ptr);
         unsafe {
             let store = llvm::LLVMBuildStore(self.llbuilder, val, ptr);
@@ -774,7 +734,6 @@ fn store_with_flags(
    fn atomic_store(&mut self, val: &'ll Value, ptr: &'ll Value,
                    order: rustc_codegen_ssa::common::AtomicOrdering, size: Size) {
         debug!("Store {:?} -> {:?}", val, ptr);
-        self.count_insn("store.atomic");
         let ptr = self.check_store(val, ptr);
         unsafe {
             let store = llvm::LLVMRustBuildAtomicStore(
@@ -789,7 +748,6 @@ fn atomic_store(&mut self, val: &'ll Value, ptr: &'ll Value,
     }
 
     fn gep(&mut self, ptr: &'ll Value, indices: &[&'ll Value]) -> &'ll Value {
-        self.count_insn("gep");
         unsafe {
             llvm::LLVMBuildGEP(self.llbuilder, ptr, indices.as_ptr(),
                                indices.len() as c_uint, noname())
@@ -797,7 +755,6 @@ fn gep(&mut self, ptr: &'ll Value, indices: &[&'ll Value]) -> &'ll Value {
     }
 
     fn inbounds_gep(&mut self, ptr: &'ll Value, indices: &[&'ll Value]) -> &'ll Value {
-        self.count_insn("inboundsgep");
         unsafe {
             llvm::LLVMBuildInBoundsGEP(
                 self.llbuilder, ptr, indices.as_ptr(), indices.len() as c_uint, noname())
@@ -805,7 +762,6 @@ fn inbounds_gep(&mut self, ptr: &'ll Value, indices: &[&'ll Value]) -> &'ll Valu
     }
 
     fn struct_gep(&mut self, ptr: &'ll Value, idx: u64) -> &'ll Value {
-        self.count_insn("structgep");
         assert_eq!(idx as c_uint as u64, idx);
         unsafe {
             llvm::LLVMBuildStructGEP(self.llbuilder, ptr, idx as c_uint, noname())
@@ -814,77 +770,66 @@ fn struct_gep(&mut self, ptr: &'ll Value, idx: u64) -> &'ll Value {
 
     /* Casts */
     fn trunc(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("trunc");
         unsafe {
             llvm::LLVMBuildTrunc(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn sext(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("sext");
         unsafe {
             llvm::LLVMBuildSExt(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn fptoui(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("fptoui");
         unsafe {
             llvm::LLVMBuildFPToUI(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn fptosi(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("fptosi");
         unsafe {
             llvm::LLVMBuildFPToSI(self.llbuilder, val, dest_ty,noname())
         }
     }
 
     fn uitofp(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("uitofp");
         unsafe {
             llvm::LLVMBuildUIToFP(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn sitofp(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("sitofp");
         unsafe {
             llvm::LLVMBuildSIToFP(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn fptrunc(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("fptrunc");
         unsafe {
             llvm::LLVMBuildFPTrunc(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn fpext(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("fpext");
         unsafe {
             llvm::LLVMBuildFPExt(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn ptrtoint(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("ptrtoint");
         unsafe {
             llvm::LLVMBuildPtrToInt(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn inttoptr(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("inttoptr");
         unsafe {
             llvm::LLVMBuildIntToPtr(self.llbuilder, val, dest_ty, noname())
         }
     }
 
     fn bitcast(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("bitcast");
         unsafe {
             llvm::LLVMBuildBitCast(self.llbuilder, val, dest_ty, noname())
         }
@@ -892,14 +837,12 @@ fn bitcast(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
 
 
     fn intcast(&mut self, val: &'ll Value, dest_ty: &'ll Type, is_signed: bool) -> &'ll Value {
-        self.count_insn("intcast");
         unsafe {
             llvm::LLVMRustBuildIntCast(self.llbuilder, val, dest_ty, is_signed)
         }
     }
 
     fn pointercast(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("pointercast");
         unsafe {
             llvm::LLVMBuildPointerCast(self.llbuilder, val, dest_ty, noname())
         }
@@ -907,7 +850,6 @@ fn pointercast(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
 
     /* Comparisons */
     fn icmp(&mut self, op: IntPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("icmp");
         let op = llvm::IntPredicate::from_generic(op);
         unsafe {
             llvm::LLVMBuildICmp(self.llbuilder, op as c_uint, lhs, rhs, noname())
@@ -915,7 +857,6 @@ fn icmp(&mut self, op: IntPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &'ll V
     }
 
     fn fcmp(&mut self, op: RealPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("fcmp");
         unsafe {
             llvm::LLVMBuildFCmp(self.llbuilder, op as c_uint, lhs, rhs, noname())
         }
@@ -984,7 +925,6 @@ fn select(
         then_val: &'ll Value,
         else_val: &'ll Value,
     ) -> &'ll Value {
-        self.count_insn("select");
         unsafe {
             llvm::LLVMBuildSelect(self.llbuilder, cond, then_val, else_val, noname())
         }
@@ -992,14 +932,12 @@ fn select(
 
     #[allow(dead_code)]
     fn va_arg(&mut self, list: &'ll Value, ty: &'ll Type) -> &'ll Value {
-        self.count_insn("vaarg");
         unsafe {
             llvm::LLVMBuildVAArg(self.llbuilder, list, ty, noname())
         }
     }
 
     fn extract_element(&mut self, vec: &'ll Value, idx: &'ll Value) -> &'ll Value {
-        self.count_insn("extractelement");
         unsafe {
             llvm::LLVMBuildExtractElement(self.llbuilder, vec, idx, noname())
         }
@@ -1016,7 +954,6 @@ fn vector_splat(&mut self, num_elts: usize, elt: &'ll Value) -> &'ll Value {
     }
 
     fn extract_value(&mut self, agg_val: &'ll Value, idx: u64) -> &'ll Value {
-        self.count_insn("extractvalue");
         assert_eq!(idx as c_uint as u64, idx);
         unsafe {
             llvm::LLVMBuildExtractValue(self.llbuilder, agg_val, idx as c_uint, noname())
@@ -1025,7 +962,6 @@ fn extract_value(&mut self, agg_val: &'ll Value, idx: u64) -> &'ll Value {
 
     fn insert_value(&mut self, agg_val: &'ll Value, elt: &'ll Value,
                        idx: u64) -> &'ll Value {
-        self.count_insn("insertvalue");
         assert_eq!(idx as c_uint as u64, idx);
         unsafe {
             llvm::LLVMBuildInsertValue(self.llbuilder, agg_val, elt, idx as c_uint,
@@ -1035,7 +971,6 @@ fn insert_value(&mut self, agg_val: &'ll Value, elt: &'ll Value,
 
     fn landing_pad(&mut self, ty: &'ll Type, pers_fn: &'ll Value,
                        num_clauses: usize) -> &'ll Value {
-        self.count_insn("landingpad");
         unsafe {
             llvm::LLVMBuildLandingPad(self.llbuilder, ty, pers_fn,
                                       num_clauses as c_uint, noname())
@@ -1043,14 +978,12 @@ fn landing_pad(&mut self, ty: &'ll Type, pers_fn: &'ll Value,
     }
 
     fn set_cleanup(&mut self, landing_pad: &'ll Value) {
-        self.count_insn("setcleanup");
         unsafe {
             llvm::LLVMSetCleanup(landing_pad, llvm::True);
         }
     }
 
     fn resume(&mut self, exn: &'ll Value) -> &'ll Value {
-        self.count_insn("resume");
         unsafe {
             llvm::LLVMBuildResume(self.llbuilder, exn)
         }
@@ -1059,7 +992,6 @@ fn resume(&mut self, exn: &'ll Value) -> &'ll Value {
     fn cleanup_pad(&mut self,
                        parent: Option<&'ll Value>,
                        args: &[&'ll Value]) -> Funclet<'ll> {
-        self.count_insn("cleanuppad");
         let name = const_cstr!("cleanuppad");
         let ret = unsafe {
             llvm::LLVMRustBuildCleanupPad(self.llbuilder,
@@ -1075,7 +1007,6 @@ fn cleanup_ret(
         &mut self, funclet: &Funclet<'ll>,
         unwind: Option<&'ll BasicBlock>,
     ) -> &'ll Value {
-        self.count_insn("cleanupret");
         let ret = unsafe {
             llvm::LLVMRustBuildCleanupRet(self.llbuilder, funclet.cleanuppad(), unwind)
         };
@@ -1085,7 +1016,6 @@ fn cleanup_ret(
     fn catch_pad(&mut self,
                      parent: &'ll Value,
                      args: &[&'ll Value]) -> Funclet<'ll> {
-        self.count_insn("catchpad");
         let name = const_cstr!("catchpad");
         let ret = unsafe {
             llvm::LLVMRustBuildCatchPad(self.llbuilder, parent,
@@ -1101,7 +1031,6 @@ fn catch_switch(
         unwind: Option<&'ll BasicBlock>,
         num_handlers: usize,
     ) -> &'ll Value {
-        self.count_insn("catchswitch");
         let name = const_cstr!("catchswitch");
         let ret = unsafe {
             llvm::LLVMRustBuildCatchSwitch(self.llbuilder, parent, unwind,
@@ -1199,7 +1128,6 @@ fn call(
         args: &[&'ll Value],
         funclet: Option<&Funclet<'ll>>,
     ) -> &'ll Value {
-        self.count_insn("call");
 
         debug!("Call {:?} with args ({:?})",
                llfn,
@@ -1221,7 +1149,6 @@ fn call(
     }
 
     fn zext(&mut self, val: &'ll Value, dest_ty: &'ll Type) -> &'ll Value {
-        self.count_insn("zext");
         unsafe {
             llvm::LLVMBuildZExt(self.llbuilder, val, dest_ty, noname())
         }
@@ -1285,19 +1212,6 @@ pub fn llfn(&self) -> &'ll Value {
         }
     }
 
-    fn count_insn(&self, category: &str) {
-        if self.sess().codegen_stats() {
-            self.stats.borrow_mut().n_llvm_insns += 1;
-        }
-        if self.sess().count_llvm_insns() {
-            *self.stats
-                      .borrow_mut()
-                      .llvm_insns
-                      .entry(category.to_string())
-                      .or_insert(0) += 1;
-        }
-    }
-
     fn position_at_start(&mut self, llbb: &'ll BasicBlock) {
         unsafe {
             llvm::LLVMRustPositionBuilderAtStart(self.llbuilder, llbb);
@@ -1305,12 +1219,10 @@ fn position_at_start(&mut self, llbb: &'ll BasicBlock) {
     }
 
     pub fn minnum(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("minnum");
         unsafe { llvm::LLVMRustBuildMinNum(self.llbuilder, lhs, rhs) }
     }
 
     pub fn maxnum(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
-        self.count_insn("maxnum");
         unsafe { llvm::LLVMRustBuildMaxNum(self.llbuilder, lhs, rhs) }
     }
 
@@ -1319,7 +1231,6 @@ pub fn insert_element(
         elt: &'ll Value,
         idx: &'ll Value,
     ) -> &'ll Value {
-        self.count_insn("insertelement");
         unsafe {
             llvm::LLVMBuildInsertElement(self.llbuilder, vec, elt, idx, noname())
         }
@@ -1331,14 +1242,12 @@ pub fn shuffle_vector(
         v2: &'ll Value,
         mask: &'ll Value,
     ) -> &'ll Value {
-        self.count_insn("shufflevector");
         unsafe {
             llvm::LLVMBuildShuffleVector(self.llbuilder, v1, v2, mask, noname())
         }
     }
 
     pub fn vector_reduce_fadd_fast(&mut self, acc: &'ll Value, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fadd_fast");
         unsafe {
             // FIXME: add a non-fast math version once
             // https://bugs.llvm.org/show_bug.cgi?id=36732
@@ -1349,7 +1258,6 @@ pub fn vector_reduce_fadd_fast(&mut self, acc: &'ll Value, src: &'ll Value) -> &
         }
     }
     pub fn vector_reduce_fmul_fast(&mut self, acc: &'ll Value, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fmul_fast");
         unsafe {
             // FIXME: add a non-fast math version once
             // https://bugs.llvm.org/show_bug.cgi?id=36732
@@ -1360,35 +1268,27 @@ pub fn vector_reduce_fmul_fast(&mut self, acc: &'ll Value, src: &'ll Value) -> &
         }
     }
     pub fn vector_reduce_add(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.add");
         unsafe { llvm::LLVMRustBuildVectorReduceAdd(self.llbuilder, src) }
     }
     pub fn vector_reduce_mul(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.mul");
         unsafe { llvm::LLVMRustBuildVectorReduceMul(self.llbuilder, src) }
     }
     pub fn vector_reduce_and(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.and");
         unsafe { llvm::LLVMRustBuildVectorReduceAnd(self.llbuilder, src) }
     }
     pub fn vector_reduce_or(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.or");
         unsafe { llvm::LLVMRustBuildVectorReduceOr(self.llbuilder, src) }
     }
     pub fn vector_reduce_xor(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.xor");
         unsafe { llvm::LLVMRustBuildVectorReduceXor(self.llbuilder, src) }
     }
     pub fn vector_reduce_fmin(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fmin");
         unsafe { llvm::LLVMRustBuildVectorReduceFMin(self.llbuilder, src, /*NoNaNs:*/ false) }
     }
     pub fn vector_reduce_fmax(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fmax");
         unsafe { llvm::LLVMRustBuildVectorReduceFMax(self.llbuilder, src, /*NoNaNs:*/ false) }
     }
     pub fn vector_reduce_fmin_fast(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fmin_fast");
         unsafe {
             let instr = llvm::LLVMRustBuildVectorReduceFMin(self.llbuilder, src, /*NoNaNs:*/ true);
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -1396,7 +1296,6 @@ pub fn vector_reduce_fmin_fast(&mut self, src: &'ll Value) -> &'ll Value {
         }
     }
     pub fn vector_reduce_fmax_fast(&mut self, src: &'ll Value) -> &'ll Value {
-        self.count_insn("vector.reduce.fmax_fast");
         unsafe {
             let instr = llvm::LLVMRustBuildVectorReduceFMax(self.llbuilder, src, /*NoNaNs:*/ true);
             llvm::LLVMRustSetHasUnsafeAlgebra(instr);
@@ -1404,11 +1303,9 @@ pub fn vector_reduce_fmax_fast(&mut self, src: &'ll Value) -> &'ll Value {
         }
     }
     pub fn vector_reduce_min(&mut self, src: &'ll Value, is_signed: bool) -> &'ll Value {
-        self.count_insn("vector.reduce.min");
         unsafe { llvm::LLVMRustBuildVectorReduceMin(self.llbuilder, src, is_signed) }
     }
     pub fn vector_reduce_max(&mut self, src: &'ll Value, is_signed: bool) -> &'ll Value {
-        self.count_insn("vector.reduce.max");
         unsafe { llvm::LLVMRustBuildVectorReduceMax(self.llbuilder, src, is_signed) }
     }
 
@@ -1419,7 +1316,6 @@ pub fn add_clause(&mut self, landing_pad: &'ll Value, clause: &'ll Value) {
     }
 
     pub fn catch_ret(&mut self, funclet: &Funclet<'ll>, unwind: &'ll BasicBlock) -> &'ll Value {
-        self.count_insn("catchret");
         let ret = unsafe {
             llvm::LLVMRustBuildCatchRet(self.llbuilder, funclet.cleanuppad(), unwind)
         };
@@ -1488,7 +1384,6 @@ fn check_call<'b>(&mut self,
     }
 
     pub fn va_arg(&mut self, list: &'ll Value, ty: &'ll Type) -> &'ll Value {
-        self.count_insn("vaarg");
         unsafe {
             llvm::LLVMBuildVAArg(self.llbuilder, list, ty, noname())
         }
@@ -1511,7 +1406,6 @@ fn call_lifetime_intrinsic(&mut self, intrinsic: &str, ptr: &'ll Value, size: Si
     }
 
     fn phi(&mut self, ty: &'ll Type, vals: &[&'ll Value], bbs: &[&'ll BasicBlock]) -> &'ll Value {
-        self.count_insn("addincoming");
         assert_eq!(vals.len(), bbs.len());
         let phi = unsafe {
             llvm::LLVMBuildPhi(self.llbuilder, ty, noname())
@@ -1525,7 +1419,6 @@ fn phi(&mut self, ty: &'ll Type, vals: &[&'ll Value], bbs: &[&'ll BasicBlock]) -
     }
 
     fn add_incoming_to_phi(&mut self, phi: &'ll Value, val: &'ll Value, bb: &'ll BasicBlock) {
-        self.count_insn("addincoming");
         unsafe {
             llvm::LLVMAddIncoming(phi, &val, &bb, 1 as c_uint);
         }
index b9fd9629e6ff193ba17f007c7a12c290b92ce17e..c713362440d97140b8d185fe00c76049d2942ed4 100644 (file)
@@ -294,13 +294,13 @@ fn scalar_to_backend(
     ) -> &'ll Value {
         let bitsize = if layout.is_bool() { 1 } else { layout.value.size(self).bits() };
         match cv {
-            Scalar::Bits { size: 0, .. } => {
+            Scalar::Raw { size: 0, .. } => {
                 assert_eq!(0, layout.value.size(self).bytes());
                 self.const_undef(self.type_ix(0))
             },
-            Scalar::Bits { bits, size } => {
+            Scalar::Raw { data, size } => {
                 assert_eq!(size as u64, layout.value.size(self).bytes());
-                let llval = self.const_uint_big(self.type_ix(bitsize), bits);
+                let llval = self.const_uint_big(self.type_ix(bitsize), data);
                 if layout.value == layout::Pointer {
                     unsafe { llvm::LLVMConstIntToPtr(llval, llty) }
                 } else {
index 5f47108309fbfdac3749da165bba96e0682c90c5..99b5cf42551faff6d56c991e7174c3180c905d7d 100644 (file)
@@ -102,7 +102,7 @@ fn check_and_apply_linkage(
     attrs: &CodegenFnAttrs,
     ty: Ty<'tcx>,
     sym: LocalInternedString,
-    span: Option<Span>
+    span: Span
 ) -> &'ll Value {
     let llty = cx.layout_of(ty).llvm_type(cx);
     if let Some(linkage) = attrs.linkage {
@@ -116,11 +116,8 @@ fn check_and_apply_linkage(
         let llty2 = if let ty::RawPtr(ref mt) = ty.sty {
             cx.layout_of(mt.ty).llvm_type(cx)
         } else {
-            if let Some(span) = span {
-                cx.sess().span_fatal(span, "must have type `*const T` or `*mut T`")
-            } else {
-                bug!("must have type `*const T` or `*mut T`")
-            }
+            cx.sess().span_fatal(
+                span, "must have type `*const T` or `*mut T` due to `#[linkage]` attribute")
         };
         unsafe {
             // Declare a symbol `foo` with the desired linkage.
@@ -136,14 +133,7 @@ fn check_and_apply_linkage(
             let mut real_name = "_rust_extern_with_linkage_".to_string();
             real_name.push_str(&sym);
             let g2 = cx.define_global(&real_name, llty).unwrap_or_else(||{
-                if let Some(span) = span {
-                    cx.sess().span_fatal(
-                        span,
-                        &format!("symbol `{}` is already defined", &sym)
-                    )
-                } else {
-                    bug!("symbol `{}` is already defined", &sym)
-                }
+                cx.sess().span_fatal(span, &format!("symbol `{}` is already defined", &sym))
             });
             llvm::LLVMRustSetLinkage(g2, llvm::Linkage::InternalLinkage);
             llvm::LLVMSetInitializer(g2, g1);
@@ -240,7 +230,7 @@ impl CodegenCx<'ll, 'tcx> {
                     ref attrs, span, node: hir::ForeignItemKind::Static(..), ..
                 }) => {
                     let fn_attrs = self.tcx.codegen_fn_attrs(def_id);
-                    (check_and_apply_linkage(&self, &fn_attrs, ty, sym, Some(span)), attrs)
+                    (check_and_apply_linkage(&self, &fn_attrs, ty, sym, span), attrs)
                 }
 
                 item => bug!("get_static: expected static, found {:?}", item)
@@ -260,7 +250,8 @@ impl CodegenCx<'ll, 'tcx> {
             debug!("get_static: sym={} item_attr={:?}", sym, self.tcx.item_attrs(def_id));
 
             let attrs = self.tcx.codegen_fn_attrs(def_id);
-            let g = check_and_apply_linkage(&self, &attrs, ty, sym, None);
+            let span = self.tcx.def_span(def_id);
+            let g = check_and_apply_linkage(&self, &attrs, ty, sym, span);
 
             // Thread-local statics in some other crate need to *always* be linked
             // against in a thread-local fashion, so we need to be sure to apply the
index 7bf8f705ea8ad84d2427bb70c3a6b557463ae385..b6b47d047c8b1023e8c7ef843167ff0b3d502257 100644 (file)
@@ -12,7 +12,6 @@
 
 use rustc_data_structures::base_n;
 use rustc_data_structures::small_c_str::SmallCStr;
-use rustc::mir::mono::Stats;
 use rustc::session::config::{self, DebugInfo};
 use rustc::session::Session;
 use rustc::ty::layout::{
@@ -44,7 +43,6 @@ pub struct CodegenCx<'ll, 'tcx: 'll> {
 
     pub llmod: &'ll llvm::Module,
     pub llcx: &'ll llvm::Context,
-    pub stats: RefCell<Stats>,
     pub codegen_unit: Arc<CodegenUnit<'tcx>>,
 
     /// Cache instances of monomorphic and polymorphic items
@@ -284,7 +282,6 @@ impl<'ll, 'tcx> CodegenCx<'ll, 'tcx> {
             tls_model,
             llmod,
             llcx,
-            stats: RefCell::new(Stats::default()),
             codegen_unit,
             instances: Default::default(),
             vtables: Default::default(),
@@ -408,14 +405,6 @@ fn check_overflow(&self) -> bool {
         self.check_overflow
     }
 
-    fn stats(&self) -> &RefCell<Stats> {
-        &self.stats
-    }
-
-    fn consume_stats(self) -> RefCell<Stats> {
-        self.stats
-    }
-
     fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>> {
         &self.codegen_unit
     }
index c8ddf733ecf1f5c8d1583afda83616f94e601068..8b3ed5b0c623a5533bf9ec0047c8cda51b2617e8 100644 (file)
@@ -5,7 +5,7 @@
 use crate::llvm;
 use crate::llvm::debuginfo::{DIScope, DISubprogram};
 use crate::common::CodegenCx;
-use rustc::mir::{Mir, SourceScope};
+use rustc::mir::{Body, SourceScope};
 
 use libc::c_uint;
 
@@ -20,7 +20,7 @@
 /// If debuginfo is disabled, the returned vector is empty.
 pub fn create_mir_scopes(
     cx: &CodegenCx<'ll, '_>,
-    mir: &Mir<'_>,
+    mir: &Body<'_>,
     debug_context: &FunctionDebugContext<&'ll DISubprogram>,
 ) -> IndexVec<SourceScope, MirDebugScope<&'ll DIScope>> {
     let null_scope = MirDebugScope {
@@ -55,7 +55,7 @@ pub fn create_mir_scopes(
 }
 
 fn make_mir_scope(cx: &CodegenCx<'ll, '_>,
-                  mir: &Mir<'_>,
+                  mir: &Body<'_>,
                   has_variables: &BitSet<SourceScope>,
                   debug_context: &FunctionDebugContextData<&'ll DISubprogram>,
                   scope: SourceScope,
index 527290392fff45a27f73ef22404f7d37f6d22f5a..6fa594d44530004bbd7a1df51d0d4fb73db1795a 100644 (file)
@@ -239,7 +239,7 @@ fn create_function_debug_context(
         instance: Instance<'tcx>,
         sig: ty::FnSig<'tcx>,
         llfn: &'ll Value,
-        mir: &mir::Mir<'_>,
+        mir: &mir::Body<'_>,
     ) -> FunctionDebugContext<&'ll DISubprogram> {
         if self.sess().opts.debuginfo == DebugInfo::None {
             return FunctionDebugContext::DebugInfoDisabled;
@@ -523,7 +523,7 @@ fn create_vtable_metadata(
 
     fn create_mir_scopes(
         &self,
-        mir: &mir::Mir<'_>,
+        mir: &mir::Body<'_>,
         debug_context: &mut FunctionDebugContext<&'ll DISubprogram>,
     ) -> IndexVec<mir::SourceScope, MirDebugScope<&'ll DIScope>> {
         create_scope_map::create_mir_scopes(self, mir, debug_context)
index 09b284052b3c488414f140c4ec9ac96ab66de9d2..57cffa48163e1d6506a857c38776cb9b4d87d21a 100644 (file)
@@ -52,7 +52,6 @@
 use errors::{FatalError, Handler};
 use rustc::dep_graph::WorkProduct;
 use syntax_pos::symbol::InternedString;
-use rustc::mir::mono::Stats;
 pub use llvm_util::target_features;
 use std::any::Any;
 use std::sync::{mpsc, Arc};
@@ -130,8 +129,8 @@ fn compile_codegen_unit<'a, 'tcx: 'a>(
         &self,
         tcx: TyCtxt<'a, 'tcx, 'tcx>,
         cgu_name: InternedString,
-    ) -> Stats {
-        base::compile_codegen_unit(tcx, cgu_name)
+    ) {
+        base::compile_codegen_unit(tcx, cgu_name);
     }
     fn target_machine_factory(
         &self,
index 74c41969268e929f58fdacf495679cfdc32aa00f..5abff2d8ec35042a08f4cae7a56dbddf8cb4df15 100644 (file)
@@ -13,7 +13,7 @@
 use rustc::dep_graph::cgu_reuse_tracker::CguReuseTracker;
 use rustc::middle::cstore::EncodedMetadata;
 use rustc::session::config::{self, OutputFilenames, OutputType, Passes, Lto,
-                             Sanitizer, PgoGenerate};
+                             Sanitizer, SwitchWithOptPath};
 use rustc::session::Session;
 use rustc::util::nodemap::FxHashMap;
 use rustc::hir::def_id::{CrateNum, LOCAL_CRATE};
@@ -56,7 +56,7 @@ pub struct ModuleConfig {
     /// Some(level) to optimize binary size, or None to not affect program size.
     pub opt_size: Option<config::OptLevel>,
 
-    pub pgo_gen: PgoGenerate,
+    pub pgo_gen: SwitchWithOptPath,
     pub pgo_use: Option<PathBuf>,
 
     // Flags indicating which outputs to produce.
@@ -94,7 +94,7 @@ fn new(passes: Vec<String>) -> ModuleConfig {
             opt_level: None,
             opt_size: None,
 
-            pgo_gen: PgoGenerate::Disabled,
+            pgo_gen: SwitchWithOptPath::Disabled,
             pgo_use: None,
 
             emit_no_opt_bc: false,
index 0b037f872475decc13b8adb23623f665d4c9b25f..172b5b39987d43247f137f5039361318c3ebe749 100644 (file)
@@ -20,7 +20,7 @@
 use rustc::middle::cstore::EncodedMetadata;
 use rustc::middle::lang_items::StartFnLangItem;
 use rustc::middle::weak_lang_items;
-use rustc::mir::mono::{Stats, CodegenUnitNameBuilder};
+use rustc::mir::mono::CodegenUnitNameBuilder;
 use rustc::ty::{self, Ty, TyCtxt};
 use rustc::ty::layout::{self, Align, TyLayout, LayoutOf, VariantIdx, HasTyCtxt};
 use rustc::ty::query::Providers;
@@ -28,7 +28,6 @@
 use rustc::util::common::{time, print_time_passes_entry};
 use rustc::session::config::{self, EntryFnType, Lto};
 use rustc::session::Session;
-use rustc_mir::monomorphize::item::DefPathBasedNames;
 use rustc_mir::monomorphize::Instance;
 use rustc_mir::monomorphize::partitioning::{CodegenUnit, CodegenUnitExt};
 use rustc::util::nodemap::FxHashMap;
 
 use crate::mir::operand::OperandValue;
 
-use std::marker::PhantomData;
-
-pub struct StatRecorder<'a, 'tcx, Cx: 'a + CodegenMethods<'tcx>> {
-    cx: &'a Cx,
-    name: Option<String>,
-    istart: usize,
-    _marker: PhantomData<&'tcx ()>,
-}
-
-impl<'a, 'tcx, Cx: CodegenMethods<'tcx>> StatRecorder<'a, 'tcx, Cx> {
-    pub fn new(cx: &'a Cx, name: String) -> Self {
-        let istart = cx.stats().borrow().n_llvm_insns;
-        StatRecorder {
-            cx,
-            name: Some(name),
-            istart,
-            _marker: PhantomData,
-        }
-    }
-}
-
-impl<'a, 'tcx, Cx: CodegenMethods<'tcx>> Drop for StatRecorder<'a, 'tcx, Cx> {
-    fn drop(&mut self) {
-        if self.cx.sess().codegen_stats() {
-            let mut stats = self.cx.stats().borrow_mut();
-            let iend = stats.n_llvm_insns;
-            stats.fn_stats.push((self.name.take().unwrap(), iend - self.istart));
-            stats.n_fns += 1;
-            // Reset LLVM insn count to avoid compound costs.
-            stats.n_llvm_insns = self.istart;
-        }
-    }
-}
-
 pub fn bin_op_to_icmp_predicate(op: hir::BinOpKind,
                                 signed: bool)
                                 -> IntPredicate {
@@ -408,15 +373,6 @@ pub fn codegen_instance<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
     cx: &'a Bx::CodegenCx,
     instance: Instance<'tcx>,
 ) {
-    let _s = if cx.sess().codegen_stats() {
-        let mut instance_name = String::new();
-        DefPathBasedNames::new(cx.tcx(), true, true)
-            .push_def_path(instance.def_id(), &mut instance_name);
-        Some(StatRecorder::new(cx, instance_name))
-    } else {
-        None
-    };
-
     // this is an info! to allow collecting monomorphization statistics
     // and to allow finding the last function before LLVM aborts from
     // release builds.
@@ -428,8 +384,6 @@ pub fn codegen_instance<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
     let lldecl = cx.instances().borrow().get(&instance).cloned().unwrap_or_else(||
         bug!("Instance `{:?}` not already declared", instance));
 
-    cx.stats().borrow_mut().n_closures += 1;
-
     let mir = cx.tcx().instance_mir(instance.def);
     mir::codegen_mir::<Bx>(cx, lldecl, &mir, instance, sig);
 }
@@ -653,7 +607,6 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
     };
 
     let mut total_codegen_time = Duration::new(0, 0);
-    let mut all_stats = Stats::default();
 
     for cgu in codegen_units.into_iter() {
         ongoing_codegen.wait_for_signal_to_codegen_item();
@@ -666,8 +619,7 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
             CguReuse::No => {
                 tcx.sess.profiler(|p| p.start_activity(format!("codegen {}", cgu.name())));
                 let start_time = Instant::now();
-                let stats = backend.compile_codegen_unit(tcx, *cgu.name());
-                all_stats.extend(stats);
+                backend.compile_codegen_unit(tcx, *cgu.name());
                 total_codegen_time += start_time.elapsed();
                 tcx.sess.profiler(|p| p.end_activity(format!("codegen {}", cgu.name())));
                 false
@@ -701,28 +653,6 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
 
     symbol_names_test::report_symbol_names(tcx);
 
-    if tcx.sess.codegen_stats() {
-        println!("--- codegen stats ---");
-        println!("n_glues_created: {}", all_stats.n_glues_created);
-        println!("n_null_glues: {}", all_stats.n_null_glues);
-        println!("n_real_glues: {}", all_stats.n_real_glues);
-
-        println!("n_fns: {}", all_stats.n_fns);
-        println!("n_inlines: {}", all_stats.n_inlines);
-        println!("n_closures: {}", all_stats.n_closures);
-        println!("fn stats:");
-        all_stats.fn_stats.sort_by_key(|&(_, insns)| insns);
-        for &(ref name, insns) in all_stats.fn_stats.iter() {
-            println!("{} insns, {}", insns, *name);
-        }
-    }
-
-    if tcx.sess.count_llvm_insns() {
-        for (k, v) in all_stats.llvm_insns.iter() {
-            println!("{:7} {}", *v, *k);
-        }
-    }
-
     ongoing_codegen.check_for_errors(tcx.sess);
 
     assert_and_save_dep_graph(tcx);
index 06d7b6c78f14bffa866945f2a03f251030180e73..bb6a13ed15a52cdeb3f3485ac6c69b56825456e4 100644 (file)
@@ -18,7 +18,7 @@ pub fn non_ssa_locals<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
     let mir = fx.mir;
     let mut analyzer = LocalAnalyzer::new(fx);
 
-    analyzer.visit_mir(mir);
+    analyzer.visit_body(mir);
 
     for (index, ty) in mir.local_decls.iter().map(|l| l.ty).enumerate() {
         let ty = fx.monomorphize(&ty);
@@ -272,9 +272,9 @@ pub fn funclet_bb(self, for_bb: mir::BasicBlock) -> Option<mir::BasicBlock> {
     }
 }
 
-pub fn cleanup_kinds<'a, 'tcx>(mir: &mir::Mir<'tcx>) -> IndexVec<mir::BasicBlock, CleanupKind> {
+pub fn cleanup_kinds<'a, 'tcx>(mir: &mir::Body<'tcx>) -> IndexVec<mir::BasicBlock, CleanupKind> {
     fn discover_masters<'tcx>(result: &mut IndexVec<mir::BasicBlock, CleanupKind>,
-                              mir: &mir::Mir<'tcx>) {
+                              mir: &mir::Body<'tcx>) {
         for (bb, data) in mir.basic_blocks().iter_enumerated() {
             match data.terminator().kind {
                 TerminatorKind::Goto { .. } |
@@ -304,7 +304,7 @@ fn discover_masters<'tcx>(result: &mut IndexVec<mir::BasicBlock, CleanupKind>,
     }
 
     fn propagate<'tcx>(result: &mut IndexVec<mir::BasicBlock, CleanupKind>,
-                       mir: &mir::Mir<'tcx>) {
+                       mir: &mir::Body<'tcx>) {
         let mut funclet_succs = IndexVec::from_elem(None, mir.basic_blocks());
 
         let mut set_successor = |funclet: mir::BasicBlock, succ| {
index fed12c9a29fd2d9f8d31c3e71aaff2365576b58e..4a43201dedf3716979d9dbd9791664273f47822a 100644 (file)
@@ -1,6 +1,6 @@
 use rustc::ty::{self, Ty, TypeFoldable, UpvarSubsts};
 use rustc::ty::layout::{TyLayout, HasTyCtxt, FnTypeExt};
-use rustc::mir::{self, Mir};
+use rustc::mir::{self, Body};
 use rustc::session::config::DebugInfo;
 use rustc_mir::monomorphize::Instance;
 use rustc_target::abi::call::{FnType, PassMode, IgnoreMode};
@@ -27,7 +27,7 @@
 pub struct FunctionCx<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>> {
     instance: Instance<'tcx>,
 
-    mir: &'a mir::Mir<'tcx>,
+    mir: &'a mir::Body<'tcx>,
 
     debug_context: FunctionDebugContext<Bx::DIScope>,
 
@@ -196,7 +196,7 @@ fn new_operand<Bx: BuilderMethods<'a, 'tcx, Value = V>>(
 pub fn codegen_mir<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
     cx: &'a Bx::CodegenCx,
     llfn: Bx::Value,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     instance: Instance<'tcx>,
     sig: ty::FnSig<'tcx>,
 ) {
@@ -360,7 +360,7 @@ pub fn codegen_mir<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
 }
 
 fn create_funclets<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     bx: &mut Bx,
     cleanup_kinds: &IndexVec<mir::BasicBlock, CleanupKind>,
     block_bxs: &IndexVec<mir::BasicBlock, Bx::BasicBlock>)
index 670b6c472698d23a16e0acaf05186eb04d9c4c93..cd32d6f484d730f671a650f06edb4c284954db8a 100644 (file)
@@ -396,22 +396,20 @@ pub fn codegen_place(
         let cx = self.cx;
         let tcx = self.cx.tcx();
 
-        if let mir::Place::Base(mir::PlaceBase::Local(index)) = *place {
-            match self.locals[index] {
-                LocalRef::Place(place) => {
-                    return place;
-                }
-                LocalRef::UnsizedPlace(place) => {
-                    return bx.load_operand(place).deref(cx);
-                }
-                LocalRef::Operand(..) => {
-                    bug!("using operand local {:?} as place", place);
+        let result = match *place {
+            mir::Place::Base(mir::PlaceBase::Local(index)) => {
+                match self.locals[index] {
+                    LocalRef::Place(place) => {
+                        return place;
+                    }
+                    LocalRef::UnsizedPlace(place) => {
+                        return bx.load_operand(place).deref(cx);
+                    }
+                    LocalRef::Operand(..) => {
+                        bug!("using operand local {:?} as place", place);
+                    }
                 }
             }
-        }
-
-        let result = match *place {
-            mir::Place::Base(mir::PlaceBase::Local(_)) => bug!(), // handled above
             mir::Place::Base(
                 mir::PlaceBase::Static(
                     box mir::Static { ty, kind: mir::StaticKind::Promoted(promoted) }
index 530eba516a6c0c4a00094498a47424482809700d..0466b47cf148f8c680d49563ca8948ce58921207 100644 (file)
@@ -5,7 +5,6 @@
 use super::CodegenObject;
 use rustc::middle::allocator::AllocatorKind;
 use rustc::middle::cstore::EncodedMetadata;
-use rustc::mir::mono::Stats;
 use rustc::session::{Session, config};
 use rustc::ty::TyCtxt;
 use rustc_codegen_utils::codegen_backend::CodegenBackend;
@@ -49,7 +48,7 @@ fn compile_codegen_unit<'a, 'tcx: 'a>(
         &self,
         tcx: TyCtxt<'a, 'tcx, 'tcx>,
         cgu_name: InternedString,
-    ) -> Stats;
+    );
     // If find_features is true this won't access `sess.crate_types` by assuming
     // that `is_pie_binary` is false. When we discover LLVM target features
     // `sess.crate_types` is uninitialized so we cannot access it.
index aadffc5932ba856d8d2dc790687ce271d8d96858..37b7a15e2ba5e3331ea4da590cf17d02bdee7e35 100644 (file)
@@ -22,12 +22,12 @@ fn create_function_debug_context(
         instance: Instance<'tcx>,
         sig: ty::FnSig<'tcx>,
         llfn: Self::Value,
-        mir: &mir::Mir<'_>,
+        mir: &mir::Body<'_>,
     ) -> FunctionDebugContext<Self::DIScope>;
 
     fn create_mir_scopes(
         &self,
-        mir: &mir::Mir<'_>,
+        mir: &mir::Body<'_>,
         debug_context: &mut FunctionDebugContext<Self::DIScope>,
     ) -> IndexVec<mir::SourceScope, MirDebugScope<Self::DIScope>>;
     fn extend_scope_to_file(
index 2797dd89f5b1599c3958122f7e8899ab07d18e12..5ea86df6e9459cc76fcb3e0c5dfb007b65003b84 100644 (file)
@@ -1,5 +1,4 @@
 use super::BackendTypes;
-use rustc::mir::mono::Stats;
 use rustc::session::Session;
 use rustc::ty::{self, Instance, Ty};
 use rustc::util::nodemap::FxHashMap;
@@ -17,8 +16,6 @@ fn vtables(
     fn eh_personality(&self) -> Self::Value;
     fn eh_unwind_resume(&self) -> Self::Value;
     fn sess(&self) -> &Session;
-    fn stats(&self) -> &RefCell<Stats>;
-    fn consume_stats(self) -> RefCell<Stats>;
     fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>>;
     fn used_statics(&self) -> &RefCell<Vec<Self::Value>>;
     fn set_frame_pointer_elimination(&self, llfn: Self::Value);
index 864071629078aab7e011b94c60b296f0cbf5c818..211d725e39d57a824ede97f95eb3cc4b97a9ffc3 100644 (file)
@@ -443,7 +443,7 @@ fn print_const(
         ct: &'tcx ty::Const<'tcx>,
     ) -> Result<Self::Const, Self::Error> {
         // only print integers
-        if let ConstValue::Scalar(Scalar::Bits { .. }) = ct.val {
+        if let ConstValue::Scalar(Scalar::Raw { .. }) = ct.val {
             if ct.ty.is_integral() {
                 return self.pretty_print_const(ct);
             }
@@ -629,6 +629,9 @@ fn write_str(&mut self, s: &str) -> fmt::Result {
                 // for ':' and '-'
                 '-' | ':' => self.path.temp_buf.push('.'),
 
+                // Avoid segmentation fault on some platforms, see #60925.
+                'm' if self.path.temp_buf.ends_with(".llv") => self.path.temp_buf.push_str("$6d$"),
+
                 // These are legal symbols
                 'a'..='z' | 'A'..='Z' | '0'..='9' | '_' | '.' | '$' => self.path.temp_buf.push(c),
 
index 359b89f683dc4ea7cc9f4da87e0579aa0862f2c5..c7f6e54c3d56b1dd713af054614859256a7721bb 100644 (file)
@@ -212,6 +212,11 @@ fn sub_one(&self) -> Self {
             fn add_usize(&self, u: usize) -> Option<Self> {
                 Idx::index(*self).checked_add(u).map(Self::new)
             }
+
+            #[inline]
+            fn sub_usize(&self, u: usize) -> Option<Self> {
+                Idx::index(*self).checked_sub(u).map(Self::new)
+            }
         }
 
         impl From<$type> for u32 {
index 890d2c5ce0b80e2f534138073036c5b2853e7834..e1112a1557771c7e4b7f6fa4c34ba452801ec52f 100644 (file)
@@ -162,6 +162,7 @@ fn suggests_using_colors(self) -> bool {
     }
 }
 
+/// Handles the writing of `HumanReadableErrorType::Default` and `HumanReadableErrorType::Short`
 pub struct EmitterWriter {
     dst: Destination,
     sm: Option<Lrc<SourceMapperDyn>>,
@@ -170,7 +171,8 @@ pub struct EmitterWriter {
     ui_testing: bool,
 }
 
-struct FileWithAnnotatedLines {
+#[derive(Debug)]
+pub struct FileWithAnnotatedLines {
     file: Lrc<SourceFile>,
     lines: Vec<Line>,
     multiline_depth: usize,
@@ -221,169 +223,6 @@ fn maybe_anonymized(&self, line_num: usize) -> String {
         }
     }
 
-    fn preprocess_annotations(&mut self, msp: &MultiSpan) -> Vec<FileWithAnnotatedLines> {
-        fn add_annotation_to_file(file_vec: &mut Vec<FileWithAnnotatedLines>,
-                                  file: Lrc<SourceFile>,
-                                  line_index: usize,
-                                  ann: Annotation) {
-
-            for slot in file_vec.iter_mut() {
-                // Look through each of our files for the one we're adding to
-                if slot.file.name == file.name {
-                    // See if we already have a line for it
-                    for line_slot in &mut slot.lines {
-                        if line_slot.line_index == line_index {
-                            line_slot.annotations.push(ann);
-                            return;
-                        }
-                    }
-                    // We don't have a line yet, create one
-                    slot.lines.push(Line {
-                        line_index,
-                        annotations: vec![ann],
-                    });
-                    slot.lines.sort();
-                    return;
-                }
-            }
-            // This is the first time we're seeing the file
-            file_vec.push(FileWithAnnotatedLines {
-                file,
-                lines: vec![Line {
-                                line_index,
-                                annotations: vec![ann],
-                            }],
-                multiline_depth: 0,
-            });
-        }
-
-        let mut output = vec![];
-        let mut multiline_annotations = vec![];
-
-        if let Some(ref sm) = self.sm {
-            for span_label in msp.span_labels() {
-                if span_label.span.is_dummy() {
-                    continue;
-                }
-
-                let lo = sm.lookup_char_pos(span_label.span.lo());
-                let mut hi = sm.lookup_char_pos(span_label.span.hi());
-
-                // Watch out for "empty spans". If we get a span like 6..6, we
-                // want to just display a `^` at 6, so convert that to
-                // 6..7. This is degenerate input, but it's best to degrade
-                // gracefully -- and the parser likes to supply a span like
-                // that for EOF, in particular.
-
-                if lo.col_display == hi.col_display && lo.line == hi.line {
-                    hi.col_display += 1;
-                }
-
-                let ann_type = if lo.line != hi.line {
-                    let ml = MultilineAnnotation {
-                        depth: 1,
-                        line_start: lo.line,
-                        line_end: hi.line,
-                        start_col: lo.col_display,
-                        end_col: hi.col_display,
-                        is_primary: span_label.is_primary,
-                        label: span_label.label.clone(),
-                        overlaps_exactly: false,
-                    };
-                    multiline_annotations.push((lo.file.clone(), ml.clone()));
-                    AnnotationType::Multiline(ml)
-                } else {
-                    AnnotationType::Singleline
-                };
-                let ann = Annotation {
-                    start_col: lo.col_display,
-                    end_col: hi.col_display,
-                    is_primary: span_label.is_primary,
-                    label: span_label.label.clone(),
-                    annotation_type: ann_type,
-                };
-
-                if !ann.is_multiline() {
-                    add_annotation_to_file(&mut output, lo.file, lo.line, ann);
-                }
-            }
-        }
-
-        // Find overlapping multiline annotations, put them at different depths
-        multiline_annotations.sort_by_key(|&(_, ref ml)| (ml.line_start, ml.line_end));
-        for item in multiline_annotations.clone() {
-            let ann = item.1;
-            for item in multiline_annotations.iter_mut() {
-                let ref mut a = item.1;
-                // Move all other multiline annotations overlapping with this one
-                // one level to the right.
-                if !(ann.same_span(a)) &&
-                    num_overlap(ann.line_start, ann.line_end, a.line_start, a.line_end, true)
-                {
-                    a.increase_depth();
-                } else if ann.same_span(a) && &ann != a {
-                    a.overlaps_exactly = true;
-                } else {
-                    break;
-                }
-            }
-        }
-
-        let mut max_depth = 0;  // max overlapping multiline spans
-        for (file, ann) in multiline_annotations {
-            if ann.depth > max_depth {
-                max_depth = ann.depth;
-            }
-            let mut end_ann = ann.as_end();
-            if !ann.overlaps_exactly {
-                // avoid output like
-                //
-                //  |        foo(
-                //  |   _____^
-                //  |  |_____|
-                //  | ||         bar,
-                //  | ||     );
-                //  | ||      ^
-                //  | ||______|
-                //  |  |______foo
-                //  |         baz
-                //
-                // and instead get
-                //
-                //  |       foo(
-                //  |  _____^
-                //  | |         bar,
-                //  | |     );
-                //  | |      ^
-                //  | |      |
-                //  | |______foo
-                //  |        baz
-                add_annotation_to_file(&mut output, file.clone(), ann.line_start, ann.as_start());
-                // 4 is the minimum vertical length of a multiline span when presented: two lines
-                // of code and two lines of underline. This is not true for the special case where
-                // the beginning doesn't have an underline, but the current logic seems to be
-                // working correctly.
-                let middle = min(ann.line_start + 4, ann.line_end);
-                for line in ann.line_start + 1..middle {
-                    // Every `|` that joins the beginning of the span (`___^`) to the end (`|__^`).
-                    add_annotation_to_file(&mut output, file.clone(), line, ann.as_line());
-                }
-                if middle < ann.line_end - 1 {
-                    for line in ann.line_end - 1..ann.line_end {
-                        add_annotation_to_file(&mut output, file.clone(), line, ann.as_line());
-                    }
-                }
-            } else {
-                end_ann.annotation_type = AnnotationType::Singleline;
-            }
-            add_annotation_to_file(&mut output, file, ann.line_end, end_ann);
-        }
-        for file_vec in output.iter_mut() {
-            file_vec.multiline_depth = max_depth;
-        }
-        output
-    }
-
     fn render_source_line(&self,
                           buffer: &mut StyledBuffer,
                           file: Lrc<SourceFile>,
@@ -1093,9 +932,7 @@ fn emit_message_default(
             }
         }
 
-        // Preprocess all the annotations so that they are grouped by file and by line number
-        // This helps us quickly iterate over the whole message (including secondary file spans)
-        let mut annotated_files = self.preprocess_annotations(msp);
+        let mut annotated_files = FileWithAnnotatedLines::collect_annotations(msp, &self.sm);
 
         // Make sure our primary file comes first
         let (primary_lo, sm) = if let (Some(sm), Some(ref primary_span)) =
@@ -1503,6 +1340,176 @@ fn emit_messages_default(&mut self,
     }
 }
 
+impl FileWithAnnotatedLines {
+    /// Preprocess all the annotations so that they are grouped by file and by line number
+    /// This helps us quickly iterate over the whole message (including secondary file spans)
+    pub fn collect_annotations(
+        msp: &MultiSpan,
+        source_map: &Option<Lrc<SourceMapperDyn>>
+    ) -> Vec<FileWithAnnotatedLines> {
+        fn add_annotation_to_file(file_vec: &mut Vec<FileWithAnnotatedLines>,
+                                  file: Lrc<SourceFile>,
+                                  line_index: usize,
+                                  ann: Annotation) {
+
+            for slot in file_vec.iter_mut() {
+                // Look through each of our files for the one we're adding to
+                if slot.file.name == file.name {
+                    // See if we already have a line for it
+                    for line_slot in &mut slot.lines {
+                        if line_slot.line_index == line_index {
+                            line_slot.annotations.push(ann);
+                            return;
+                        }
+                    }
+                    // We don't have a line yet, create one
+                    slot.lines.push(Line {
+                        line_index,
+                        annotations: vec![ann],
+                    });
+                    slot.lines.sort();
+                    return;
+                }
+            }
+            // This is the first time we're seeing the file
+            file_vec.push(FileWithAnnotatedLines {
+                file,
+                lines: vec![Line {
+                                line_index,
+                                annotations: vec![ann],
+                            }],
+                multiline_depth: 0,
+            });
+        }
+
+        let mut output = vec![];
+        let mut multiline_annotations = vec![];
+
+        if let Some(ref sm) = source_map {
+            for span_label in msp.span_labels() {
+                if span_label.span.is_dummy() {
+                    continue;
+                }
+
+                let lo = sm.lookup_char_pos(span_label.span.lo());
+                let mut hi = sm.lookup_char_pos(span_label.span.hi());
+
+                // Watch out for "empty spans". If we get a span like 6..6, we
+                // want to just display a `^` at 6, so convert that to
+                // 6..7. This is degenerate input, but it's best to degrade
+                // gracefully -- and the parser likes to supply a span like
+                // that for EOF, in particular.
+
+                if lo.col_display == hi.col_display && lo.line == hi.line {
+                    hi.col_display += 1;
+                }
+
+                let ann_type = if lo.line != hi.line {
+                    let ml = MultilineAnnotation {
+                        depth: 1,
+                        line_start: lo.line,
+                        line_end: hi.line,
+                        start_col: lo.col_display,
+                        end_col: hi.col_display,
+                        is_primary: span_label.is_primary,
+                        label: span_label.label.clone(),
+                        overlaps_exactly: false,
+                    };
+                    multiline_annotations.push((lo.file.clone(), ml.clone()));
+                    AnnotationType::Multiline(ml)
+                } else {
+                    AnnotationType::Singleline
+                };
+                let ann = Annotation {
+                    start_col: lo.col_display,
+                    end_col: hi.col_display,
+                    is_primary: span_label.is_primary,
+                    label: span_label.label.clone(),
+                    annotation_type: ann_type,
+                };
+
+                if !ann.is_multiline() {
+                    add_annotation_to_file(&mut output, lo.file, lo.line, ann);
+                }
+            }
+        }
+
+        // Find overlapping multiline annotations, put them at different depths
+        multiline_annotations.sort_by_key(|&(_, ref ml)| (ml.line_start, ml.line_end));
+        for item in multiline_annotations.clone() {
+            let ann = item.1;
+            for item in multiline_annotations.iter_mut() {
+                let ref mut a = item.1;
+                // Move all other multiline annotations overlapping with this one
+                // one level to the right.
+                if !(ann.same_span(a)) &&
+                    num_overlap(ann.line_start, ann.line_end, a.line_start, a.line_end, true)
+                {
+                    a.increase_depth();
+                } else if ann.same_span(a) && &ann != a {
+                    a.overlaps_exactly = true;
+                } else {
+                    break;
+                }
+            }
+        }
+
+        let mut max_depth = 0;  // max overlapping multiline spans
+        for (file, ann) in multiline_annotations {
+            if ann.depth > max_depth {
+                max_depth = ann.depth;
+            }
+            let mut end_ann = ann.as_end();
+            if !ann.overlaps_exactly {
+                // avoid output like
+                //
+                //  |        foo(
+                //  |   _____^
+                //  |  |_____|
+                //  | ||         bar,
+                //  | ||     );
+                //  | ||      ^
+                //  | ||______|
+                //  |  |______foo
+                //  |         baz
+                //
+                // and instead get
+                //
+                //  |       foo(
+                //  |  _____^
+                //  | |         bar,
+                //  | |     );
+                //  | |      ^
+                //  | |      |
+                //  | |______foo
+                //  |        baz
+                add_annotation_to_file(&mut output, file.clone(), ann.line_start, ann.as_start());
+                // 4 is the minimum vertical length of a multiline span when presented: two lines
+                // of code and two lines of underline. This is not true for the special case where
+                // the beginning doesn't have an underline, but the current logic seems to be
+                // working correctly.
+                let middle = min(ann.line_start + 4, ann.line_end);
+                for line in ann.line_start + 1..middle {
+                    // Every `|` that joins the beginning of the span (`___^`) to the end (`|__^`).
+                    add_annotation_to_file(&mut output, file.clone(), line, ann.as_line());
+                }
+                if middle < ann.line_end - 1 {
+                    for line in ann.line_end - 1..ann.line_end {
+                        add_annotation_to_file(&mut output, file.clone(), line, ann.as_line());
+                    }
+                }
+            } else {
+                end_ann.annotation_type = AnnotationType::Singleline;
+            }
+            add_annotation_to_file(&mut output, file, ann.line_end, end_ann);
+        }
+        for file_vec in output.iter_mut() {
+            file_vec.multiline_depth = max_depth;
+        }
+        output
+    }
+}
+
 fn draw_col_separator(buffer: &mut StyledBuffer, line: usize, col: usize) {
     buffer.puts(line, col, "| ", Style::LineNumber);
 }
index 6e32a53c364a6502eb20fda0763111a78f7d63ef..f989ebc6dfd8e0210c707e4523b7a550f176b64f 100644 (file)
@@ -8,7 +8,7 @@ edition = "2018"
 proc-macro = true
 
 [dependencies]
-synstructure = "0.10.1"
+synstructure = "0.10.2"
 syn = { version = "0.15.22", features = ["full"] }
 proc-macro2 = "0.4.24"
 quote = "0.6.10"
index a484928ce6c3663365970bcba5464dde29f38655..10ff606b013a75e582296f04908e2bc5bd6c9644 100644 (file)
@@ -18,7 +18,7 @@
 use rustc::session::Session;
 use rustc::ty::{self, Ty, TyCtxt};
 use rustc::ty::codec::TyDecoder;
-use rustc::mir::Mir;
+use rustc::mir::Body;
 use rustc::util::captures::Captures;
 
 use std::io;
@@ -887,7 +887,7 @@ pub fn is_item_mir_available(&self, id: DefIndex) -> bool {
     pub fn maybe_get_optimized_mir(&self,
                                    tcx: TyCtxt<'a, 'tcx, 'tcx>,
                                    id: DefIndex)
-                                   -> Option<Mir<'tcx>> {
+                                   -> Option<Body<'tcx>> {
         match self.is_proc_macro(id) {
             true => None,
             false => self.entry(id).mir.map(|mir| mir.decode((self, tcx))),
index 5d080de2645e30a4be6925a235c3f59acb81f0ab..588682a2420a94b38437a7a6f8ad0e4b54db2dfb 100644 (file)
@@ -1026,7 +1026,7 @@ fn encode_fn_arg_names(&mut self, param_names: &[ast::Ident]) -> LazySeq<ast::Na
         self.lazy_seq(param_names.iter().map(|ident| ident.name))
     }
 
-    fn encode_optimized_mir(&mut self, def_id: DefId) -> Option<Lazy<mir::Mir<'tcx>>> {
+    fn encode_optimized_mir(&mut self, def_id: DefId) -> Option<Lazy<mir::Body<'tcx>>> {
         debug!("EntryBuilder::encode_mir({:?})", def_id);
         if self.tcx.mir_keys(LOCAL_CRATE).contains(&def_id) {
             let mir = self.tcx.optimized_mir(def_id);
index b9e5bdef27ab4bd1f6735be43ee4e59ed327aedb..2c3291a41d32b6f7f06effc94ed529e1b8de2d86 100644 (file)
@@ -222,7 +222,7 @@ pub struct Entry<'tcx> {
     pub predicates: Option<Lazy<ty::GenericPredicates<'tcx>>>,
     pub predicates_defined_on: Option<Lazy<ty::GenericPredicates<'tcx>>>,
 
-    pub mir: Option<Lazy<mir::Mir<'tcx>>>,
+    pub mir: Option<Lazy<mir::Body<'tcx>>>,
 }
 
 #[derive(Copy, Clone, RustcEncodable, RustcDecodable)]
index 5ced497baa1fdf9f3938e620a4d5eea93988dbd8..d9d6fe0affb32ee82ed8b29b6a829f2f0e0bf381 100644 (file)
@@ -5,7 +5,7 @@
 use crate::dataflow::move_paths::MoveData;
 use rustc::mir::traversal;
 use rustc::mir::visit::{PlaceContext, Visitor, NonUseContext, MutatingUseContext};
-use rustc::mir::{self, Location, Mir, Local};
+use rustc::mir::{self, Location, Body, Local};
 use rustc::ty::{RegionVid, TyCtxt};
 use rustc::util::nodemap::{FxHashMap, FxHashSet};
 use rustc_data_structures::indexed_vec::IndexVec;
@@ -90,7 +90,7 @@ fn fmt(&self, w: &mut fmt::Formatter<'_>) -> fmt::Result {
 impl LocalsStateAtExit {
     fn build(
         locals_are_invalidated_at_exit: bool,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         move_data: &MoveData<'tcx>
     ) -> Self {
         struct HasStorageDead(BitSet<Local>);
@@ -107,7 +107,7 @@ fn visit_local(&mut self, local: &Local, ctx: PlaceContext, _: Location) {
             LocalsStateAtExit::AllAreInvalidated
         } else {
             let mut has_storage_dead = HasStorageDead(BitSet::new_empty(mir.local_decls.len()));
-            has_storage_dead.visit_mir(mir);
+            has_storage_dead.visit_body(mir);
             let mut has_storage_dead_or_moved = has_storage_dead.0;
             for move_out in &move_data.moves {
                 if let Some(index) = move_data.base_local(move_out.path) {
@@ -123,7 +123,7 @@ fn visit_local(&mut self, local: &Local, ctx: PlaceContext, _: Location) {
 impl<'tcx> BorrowSet<'tcx> {
     pub fn build(
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         locals_are_invalidated_at_exit: bool,
         move_data: &MoveData<'tcx>
     ) -> Self {
@@ -163,7 +163,7 @@ pub fn build(
 
 struct GatherBorrows<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     idx_vec: IndexVec<BorrowIndex, BorrowData<'tcx>>,
     location_map: FxHashMap<Location, BorrowIndex>,
     activation_map: FxHashMap<Location, Vec<BorrowIndex>>,
index 8022d1f0c7315dfd38dcd6397fb7d19d609b4e05..e3a79b24cabe8c5cfebe606fa5fa107d60e89a38 100644 (file)
@@ -595,12 +595,11 @@ pub(super) fn describe_place_for_conflicting_borrow(
     ) -> (String, String, String, String) {
         // Define a small closure that we can use to check if the type of a place
         // is a union.
-        let is_union = |place: &Place<'tcx>| -> bool {
-            place.ty(self.mir, self.infcx.tcx).ty
-                .ty_adt_def()
-                .map(|adt| adt.is_union())
-                .unwrap_or(false)
+        let union_ty = |place: &Place<'tcx>| -> Option<Ty<'tcx>> {
+            let ty = place.ty(self.mir, self.infcx.tcx).ty;
+            ty.ty_adt_def().filter(|adt| adt.is_union()).map(|_| ty)
         };
+        let describe_place = |place| self.describe_place(place).unwrap_or_else(|| "_".to_owned());
 
         // Start with an empty tuple, so we can use the functions on `Option` to reduce some
         // code duplication (particularly around returning an empty description in the failure
@@ -619,7 +618,7 @@ pub(super) fn describe_place_for_conflicting_borrow(
                 let mut current = first_borrowed_place;
                 while let Place::Projection(box Projection { base, elem }) = current {
                     match elem {
-                        ProjectionElem::Field(field, _) if is_union(base) => {
+                        ProjectionElem::Field(field, _) if union_ty(base).is_some() => {
                             return Some((base, field));
                         },
                         _ => current = base,
@@ -632,34 +631,32 @@ pub(super) fn describe_place_for_conflicting_borrow(
                 // borrowed place and look for a access to a different field of the same union.
                 let mut current = second_borrowed_place;
                 while let Place::Projection(box Projection { base, elem }) = current {
-                    match elem {
-                        ProjectionElem::Field(field, _) if {
-                            is_union(base) && field != target_field && base == target_base
-                        } => {
-                            let desc_base = self.describe_place(base)
-                                .unwrap_or_else(|| "_".to_owned());
-                            let desc_first = self.describe_place(first_borrowed_place)
-                                .unwrap_or_else(|| "_".to_owned());
-                            let desc_second = self.describe_place(second_borrowed_place)
-                                .unwrap_or_else(|| "_".to_owned());
-
-                            // Also compute the name of the union type, eg. `Foo` so we
-                            // can add a helpful note with it.
-                            let ty = base.ty(self.mir, self.infcx.tcx).ty;
-
-                            return Some((desc_base, desc_first, desc_second, ty.to_string()));
-                        },
-                        _ => current = base,
+                    if let ProjectionElem::Field(field, _) = elem {
+                        if let Some(union_ty) = union_ty(base) {
+                            if field != target_field && base == target_base {
+                                return Some((
+                                    describe_place(base),
+                                    describe_place(first_borrowed_place),
+                                    describe_place(second_borrowed_place),
+                                    union_ty.to_string(),
+                                ));
+                            }
+                        }
                     }
+
+                    current = base;
                 }
                 None
             })
             .unwrap_or_else(|| {
                 // If we didn't find a field access into a union, or both places match, then
                 // only return the description of the first place.
-                let desc_place = self.describe_place(first_borrowed_place)
-                    .unwrap_or_else(|| "_".to_owned());
-                (desc_place, "".to_string(), "".to_string(), "".to_string())
+                (
+                    describe_place(first_borrowed_place),
+                    "".to_string(),
+                    "".to_string(),
+                    "".to_string(),
+                )
             })
     }
 
@@ -1616,7 +1613,7 @@ fn annotate_argument_and_return_for_borrow(
                             );
 
                             // Find the local from the operand.
-                            let assigned_from_local = match assigned_from.local() {
+                            let assigned_from_local = match assigned_from.local_or_deref_local() {
                                 Some(local) => local,
                                 None => continue,
                             };
@@ -1672,7 +1669,7 @@ fn annotate_argument_and_return_for_borrow(
                     );
 
                     // Find the local from the rvalue.
-                    let assigned_from_local = match assigned_from.local() {
+                    let assigned_from_local = match assigned_from.local_or_deref_local() {
                         Some(local) => local,
                         None => continue,
                     };
@@ -1735,7 +1732,7 @@ fn annotate_argument_and_return_for_borrow(
                         assigned_from,
                     );
 
-                    if let Some(assigned_from_local) = assigned_from.local() {
+                    if let Some(assigned_from_local) = assigned_from.local_or_deref_local() {
                         debug!(
                             "annotate_argument_and_return_for_borrow: assigned_from_local={:?}",
                             assigned_from_local,
index ec0359794e7be7f6acbd7086a0e48c20aad73466..5a22c81a5d0578f1d83b52458e1c9b279f73b2f0 100644 (file)
@@ -37,15 +37,15 @@ pub(super) fn add_moved_or_invoked_closure_note(
         diag: &mut DiagnosticBuilder<'_>,
     ) {
         debug!("add_moved_or_invoked_closure_note: location={:?} place={:?}", location, place);
-        let mut target = place.local();
+        let mut target = place.local_or_deref_local();
         for stmt in &self.mir[location.block].statements[location.statement_index..] {
             debug!("add_moved_or_invoked_closure_note: stmt={:?} target={:?}", stmt, target);
             if let StatementKind::Assign(into, box Rvalue::Use(from)) = &stmt.kind {
                 debug!("add_fnonce_closure_note: into={:?} from={:?}", into, from);
                 match from {
                     Operand::Copy(ref place) |
-                    Operand::Move(ref place) if target == place.local() =>
-                        target = into.local(),
+                    Operand::Move(ref place) if target == place.local_or_deref_local() =>
+                        target = into.local_or_deref_local(),
                     _ => {},
                 }
             }
@@ -69,8 +69,8 @@ pub(super) fn add_moved_or_invoked_closure_note(
             if self.infcx.tcx.parent(id) == self.infcx.tcx.lang_items().fn_once_trait() {
                 let closure = match args.first() {
                     Some(Operand::Copy(ref place)) |
-                    Some(Operand::Move(ref place)) if target == place.local() =>
-                        place.local().unwrap(),
+                    Some(Operand::Move(ref place)) if target == place.local_or_deref_local() =>
+                        place.local_or_deref_local().unwrap(),
                     _ => return,
                 };
 
index 20a477576c95c4a7f976d917248571a43e5ef6e3..feade0d2a4aeea4f8c992a8815a184f18804800e 100644 (file)
@@ -1,4 +1,4 @@
-use rustc::mir::{BasicBlock, Location, Mir};
+use rustc::mir::{BasicBlock, Location, Body};
 use rustc_data_structures::indexed_vec::{Idx, IndexVec};
 
 /// Maps between a MIR Location, which identifies a particular
@@ -30,7 +30,7 @@ pub struct LocationIndex {
 }
 
 impl LocationTable {
-    crate fn new(mir: &Mir<'_>) -> Self {
+    crate fn new(mir: &Body<'_>) -> Self {
         let mut num_points = 0;
         let statements_before_block = mir.basic_blocks()
             .iter()
index 437f95e332a3d8d09a8bed37720d47ab487cf3ea..82be2405701d516d971bc8ce1db456d4afd4a770 100644 (file)
@@ -10,7 +10,9 @@
 use rustc::middle::borrowck::SignalledError;
 use rustc::mir::{AggregateKind, BasicBlock, BorrowCheckResult, BorrowKind};
 use rustc::mir::{
-    ClearCrossCrate, Local, Location, Mir, Mutability, Operand, Place, PlaceBase, Static, StaticKind
+    ClearCrossCrate, Local, Location, Body, Mutability, Operand, Place, PlaceBase, Static,
+
+    StaticKind
 };
 use rustc::mir::{Field, Projection, ProjectionElem, Rvalue, Statement, StatementKind};
 use rustc::mir::{Terminator, TerminatorKind};
@@ -118,7 +120,7 @@ fn mir_borrowck<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> BorrowC
     }
 
     let opt_closure_req = tcx.infer_ctxt().enter(|infcx| {
-        let input_mir: &Mir<'_> = &input_mir.borrow();
+        let input_mir: &Body<'_> = &input_mir.borrow();
         do_mir_borrowck(&infcx, input_mir, def_id)
     });
     debug!("mir_borrowck done");
@@ -128,7 +130,7 @@ fn mir_borrowck<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> BorrowC
 
 fn do_mir_borrowck<'a, 'gcx, 'tcx>(
     infcx: &InferCtxt<'a, 'gcx, 'tcx>,
-    input_mir: &Mir<'gcx>,
+    input_mir: &Body<'gcx>,
     def_id: DefId,
 ) -> BorrowCheckResult<'gcx> {
     debug!("do_mir_borrowck(def_id = {:?})", def_id);
@@ -175,7 +177,7 @@ fn do_mir_borrowck<'a, 'gcx, 'tcx>(
     // requires first making our own copy of the MIR. This copy will
     // be modified (in place) to contain non-lexical lifetimes. It
     // will have a lifetime tied to the inference context.
-    let mut mir: Mir<'tcx> = input_mir.clone();
+    let mut mir: Body<'tcx> = input_mir.clone();
     let free_regions = nll::replace_regions_in_mir(infcx, def_id, param_env, &mut mir);
     let mir = &mir; // no further changes
     let location_table = &LocationTable::new(mir);
@@ -451,7 +453,7 @@ fn downgrade_if_error(diag: &mut Diagnostic) {
 
 pub struct MirBorrowckCtxt<'cx, 'gcx: 'tcx, 'tcx: 'cx> {
     infcx: &'cx InferCtxt<'cx, 'gcx, 'tcx>,
-    mir: &'cx Mir<'tcx>,
+    mir: &'cx Body<'tcx>,
     mir_def_id: DefId,
     move_data: &'cx MoveData<'tcx>,
 
@@ -537,7 +539,7 @@ pub struct MirBorrowckCtxt<'cx, 'gcx: 'tcx, 'tcx: 'cx> {
 impl<'cx, 'gcx, 'tcx> DataflowResultsConsumer<'cx, 'tcx> for MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
     type FlowState = Flows<'cx, 'gcx, 'tcx>;
 
-    fn mir(&self) -> &'cx Mir<'tcx> {
+    fn mir(&self) -> &'cx Body<'tcx> {
         self.mir
     }
 
index 16fbc8d6bb2997dfcb3e53fd13100af3aac9488d..a292115707d8eee80957ffa28ec2af5d5262bacf 100644 (file)
@@ -1,6 +1,6 @@
 use rustc::hir;
 use rustc::hir::Node;
-use rustc::mir::{self, BindingForm, Constant, ClearCrossCrate, Local, Location, Mir};
+use rustc::mir::{self, BindingForm, Constant, ClearCrossCrate, Local, Location, Body};
 use rustc::mir::{
     Mutability, Operand, Place, PlaceBase, Projection, ProjectionElem, Static, StaticKind,
 };
@@ -562,7 +562,7 @@ fn suggest_ampmut_self<'cx, 'gcx, 'tcx>(
 // by trying (3.), then (2.) and finally falling back on (1.).
 fn suggest_ampmut<'cx, 'gcx, 'tcx>(
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     local: Local,
     local_decl: &mir::LocalDecl<'tcx>,
     opt_ty_info: Option<Span>,
index b0e395cbbdfb5772ff815d399b230629b7886d5d..b485f37b78c2d8c5bfe35e6caf42b799c3e8cbc4 100644 (file)
@@ -6,7 +6,7 @@
 use rustc::infer::InferCtxt;
 use rustc::mir::visit::TyContext;
 use rustc::mir::visit::Visitor;
-use rustc::mir::{BasicBlock, BasicBlockData, Location, Mir, Place, PlaceBase, Rvalue};
+use rustc::mir::{BasicBlock, BasicBlockData, Location, Body, Place, PlaceBase, Rvalue};
 use rustc::mir::{SourceInfo, Statement, Terminator};
 use rustc::mir::UserTypeProjection;
 use rustc::ty::fold::TypeFoldable;
@@ -18,7 +18,7 @@ pub(super) fn generate_constraints<'cx, 'gcx, 'tcx>(
     liveness_constraints: &mut LivenessValues<RegionVid>,
     all_facts: &mut Option<AllFacts>,
     location_table: &LocationTable,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     borrow_set: &BorrowSet<'tcx>,
 ) {
     let mut cg = ConstraintGeneration {
index 9a2090d05084d98ec6e73413227e82a40a8a429f..3921246b06d388a8d12fc206b2b5dc5d0696c750 100644 (file)
@@ -5,12 +5,12 @@
 use crate::borrow_check::nll::ToRegionVid;
 use crate::util::liveness::{self, DefUse};
 use rustc::mir::visit::{MirVisitable, PlaceContext, Visitor};
-use rustc::mir::{Local, Location, Mir};
+use rustc::mir::{Local, Location, Body};
 use rustc::ty::{RegionVid, TyCtxt};
 use rustc_data_structures::fx::FxHashSet;
 
 crate fn find<'tcx>(
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     regioncx: &Rc<RegionInferenceContext<'tcx>>,
     tcx: TyCtxt<'_, '_, 'tcx>,
     region_vid: RegionVid,
@@ -28,7 +28,7 @@
 }
 
 struct UseFinder<'cx, 'gcx: 'tcx, 'tcx: 'cx> {
-    mir: &'cx Mir<'tcx>,
+    mir: &'cx Body<'tcx>,
     regioncx: &'cx Rc<RegionInferenceContext<'tcx>>,
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     region_vid: RegionVid,
@@ -100,7 +100,7 @@ fn def_use(&self, location: Location, thing: &dyn MirVisitable<'tcx>) -> Option<
 }
 
 struct DefUseVisitor<'cx, 'gcx: 'tcx, 'tcx: 'cx> {
-    mir: &'cx Mir<'tcx>,
+    mir: &'cx Body<'tcx>,
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     region_vid: RegionVid,
     def_use_result: Option<DefUseResult>,
index 6bca470bf3e5f8928f967b84059b585bf1215c3c..60c46b36f5f06bca6e025bb0b5c8a9147f2ad954 100644 (file)
@@ -6,7 +6,7 @@
 use crate::borrow_check::nll::ConstraintDescription;
 use crate::borrow_check::{MirBorrowckCtxt, WriteKind};
 use rustc::mir::{
-    CastKind, ConstraintCategory, FakeReadCause, Local, Location, Mir, Operand, Place, PlaceBase,
+    CastKind, ConstraintCategory, FakeReadCause, Local, Location, Body, Operand, Place, PlaceBase,
     Projection, ProjectionElem, Rvalue, Statement, StatementKind, TerminatorKind,
 };
 use rustc::ty::{self, TyCtxt};
@@ -54,7 +54,7 @@ pub(in crate::borrow_check) fn is_explained(&self) -> bool {
     pub(in crate::borrow_check) fn add_explanation_to_diagnostic<'cx, 'gcx, 'tcx>(
         &self,
         tcx: TyCtxt<'cx, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         err: &mut DiagnosticBuilder<'_>,
         borrow_desc: &str,
         borrow_span: Option<Span>,
index e3ab48ccff15b0a3f812fa77122c4996b9e89dcb..017f4d48c120050d2d833539a246913634e15933 100644 (file)
@@ -11,7 +11,7 @@
 use crate::dataflow::indexes::BorrowIndex;
 use rustc::ty::TyCtxt;
 use rustc::mir::visit::Visitor;
-use rustc::mir::{BasicBlock, Location, Mir, Place, PlaceBase, Rvalue};
+use rustc::mir::{BasicBlock, Location, Body, Place, PlaceBase, Rvalue};
 use rustc::mir::{Statement, StatementKind};
 use rustc::mir::TerminatorKind;
 use rustc::mir::{Operand, BorrowKind};
@@ -21,7 +21,7 @@ pub(super) fn generate_invalidates<'cx, 'gcx, 'tcx>(
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     all_facts: &mut Option<AllFacts>,
     location_table: &LocationTable,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     borrow_set: &BorrowSet<'tcx>,
 ) {
     if all_facts.is_none() {
@@ -39,7 +39,7 @@ pub(super) fn generate_invalidates<'cx, 'gcx, 'tcx>(
             mir,
             dominators,
         };
-        ig.visit_mir(mir);
+        ig.visit_body(mir);
     }
 }
 
@@ -47,7 +47,7 @@ struct InvalidationGenerator<'cx, 'tcx: 'cx, 'gcx: 'tcx> {
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     all_facts: &'cx mut AllFacts,
     location_table: &'cx LocationTable,
-    mir: &'cx Mir<'tcx>,
+    mir: &'cx Body<'tcx>,
     dominators: Dominators<BasicBlock>,
     borrow_set: &'cx BorrowSet<'tcx>,
 }
index fa490c108c8965f647caaa8a6c7509834d45fc14..0fb1705c8c294748864f778bd6bfa2521360de72 100644 (file)
@@ -11,7 +11,7 @@
 use crate::borrow_check::Upvar;
 use rustc::hir::def_id::DefId;
 use rustc::infer::InferCtxt;
-use rustc::mir::{ClosureOutlivesSubject, ClosureRegionRequirements, Mir};
+use rustc::mir::{ClosureOutlivesSubject, ClosureRegionRequirements, Body};
 use rustc::ty::{self, RegionKind, RegionVid};
 use rustc_errors::Diagnostic;
 use std::fmt::Debug;
@@ -50,7 +50,7 @@ pub(in crate::borrow_check) fn replace_regions_in_mir<'cx, 'gcx, 'tcx>(
     infcx: &InferCtxt<'cx, 'gcx, 'tcx>,
     def_id: DefId,
     param_env: ty::ParamEnv<'tcx>,
-    mir: &mut Mir<'tcx>,
+    mir: &mut Body<'tcx>,
 ) -> UniversalRegions<'tcx> {
     debug!("replace_regions_in_mir(def_id={:?})", def_id);
 
@@ -73,7 +73,7 @@ pub(in crate::borrow_check) fn compute_regions<'cx, 'gcx, 'tcx>(
     infcx: &InferCtxt<'cx, 'gcx, 'tcx>,
     def_id: DefId,
     universal_regions: UniversalRegions<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     upvars: &[Upvar],
     location_table: &LocationTable,
     param_env: ty::ParamEnv<'gcx>,
@@ -213,7 +213,7 @@ pub(in crate::borrow_check) fn compute_regions<'cx, 'gcx, 'tcx>(
 fn dump_mir_results<'a, 'gcx, 'tcx>(
     infcx: &InferCtxt<'a, 'gcx, 'tcx>,
     source: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     regioncx: &RegionInferenceContext<'_>,
     closure_region_requirements: &Option<ClosureRegionRequirements<'_>>,
 ) {
@@ -273,7 +273,7 @@ fn dump_mir_results<'a, 'gcx, 'tcx>(
 
 fn dump_annotation<'a, 'gcx, 'tcx>(
     infcx: &InferCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     mir_def_id: DefId,
     regioncx: &RegionInferenceContext<'tcx>,
     closure_region_requirements: &Option<ClosureRegionRequirements<'_>>,
index 18ca105070e8f9149b4c5342775cc914f7626184..db43ea0558cc7b6b4a3f82c362421f1cb3c4de0b 100644 (file)
@@ -9,7 +9,7 @@
 use rustc::infer::error_reporting::nice_region_error::NiceRegionError;
 use rustc::infer::InferCtxt;
 use rustc::infer::NLLRegionVariableOrigin;
-use rustc::mir::{ConstraintCategory, Location, Mir};
+use rustc::mir::{ConstraintCategory, Location, Body};
 use rustc::ty::{self, RegionVid};
 use rustc_data_structures::indexed_vec::IndexVec;
 use rustc_errors::{Diagnostic, DiagnosticBuilder};
@@ -62,7 +62,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
     /// path to blame.
     fn best_blame_constraint(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         from_region: RegionVid,
         target_test: impl Fn(RegionVid) -> bool,
     ) -> (ConstraintCategory, bool, Span) {
@@ -237,7 +237,7 @@ fn find_constraint_paths_between_regions(
     /// Here we would be invoked with `fr = 'a` and `outlived_fr = `'b`.
     pub(super) fn report_error(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         infcx: &InferCtxt<'_, '_, 'tcx>,
         mir_def_id: DefId,
@@ -357,7 +357,7 @@ fn provides_universal_region(&self, r: RegionVid, fr1: RegionVid, fr2: RegionVid
     /// ```
     fn report_fnmut_error(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         infcx: &InferCtxt<'_, '_, 'tcx>,
         mir_def_id: DefId,
@@ -422,7 +422,7 @@ fn report_fnmut_error(
     /// ```
     fn report_escaping_data_error(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         infcx: &InferCtxt<'_, '_, 'tcx>,
         mir_def_id: DefId,
@@ -514,7 +514,7 @@ fn report_escaping_data_error(
     /// ```
     fn report_general_error(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         infcx: &InferCtxt<'_, '_, 'tcx>,
         mir_def_id: DefId,
@@ -667,7 +667,7 @@ fn add_static_impl_trait_suggestion(
 
     crate fn free_region_constraint_info(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         infcx: &InferCtxt<'_, '_, 'tcx>,
@@ -724,7 +724,7 @@ fn add_static_impl_trait_suggestion(
     // Finds a good span to blame for the fact that `fr1` outlives `fr2`.
     crate fn find_outlives_blame_span(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         fr1: RegionVid,
         fr2: RegionVid,
     ) -> (ConstraintCategory, Span) {
@@ -735,7 +735,7 @@ fn add_static_impl_trait_suggestion(
 
     fn retrieve_closure_constraint_info(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         constraint: &OutlivesConstraint,
     ) -> (ConstraintCategory, bool, Span) {
         let loc = match constraint.locations {
index f3cfc1a59a9811dfa05376085cd5c7eb5b63fec6..25415039fc80a7b29f731dd2b2b9918f235b6b35 100644 (file)
@@ -7,7 +7,7 @@
 use rustc::hir::def::{Res, DefKind};
 use rustc::hir::def_id::DefId;
 use rustc::infer::InferCtxt;
-use rustc::mir::Mir;
+use rustc::mir::Body;
 use rustc::ty::subst::{SubstsRef, UnpackedKind};
 use rustc::ty::{self, RegionKind, RegionVid, Ty, TyCtxt};
 use rustc::ty::print::RegionHighlightMode;
@@ -152,7 +152,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
     crate fn give_region_a_name(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         fr: RegionVid,
@@ -332,7 +332,7 @@ fn get_named_span(
     fn give_name_if_anonymous_region_appears_in_arguments(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         mir_def_id: DefId,
         fr: RegionVid,
         counter: &mut usize,
@@ -360,7 +360,7 @@ fn give_name_if_anonymous_region_appears_in_arguments(
     fn give_name_if_we_can_match_hir_ty_from_argument(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         mir_def_id: DefId,
         needle_fr: RegionVid,
         argument_ty: Ty<'tcx>,
@@ -406,7 +406,7 @@ fn give_name_if_we_can_match_hir_ty_from_argument(
     fn give_name_if_we_cannot_match_hir_ty(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         needle_fr: RegionVid,
         argument_ty: Ty<'tcx>,
         counter: &mut usize,
@@ -676,7 +676,7 @@ fn give_name_if_anonymous_region_appears_in_upvars(
     fn give_name_if_anonymous_region_appears_in_output(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         mir_def_id: DefId,
         fr: RegionVid,
         counter: &mut usize,
@@ -736,7 +736,7 @@ fn give_name_if_anonymous_region_appears_in_output(
     fn give_name_if_anonymous_region_appears_in_yield_ty(
         &self,
         infcx: &InferCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         mir_def_id: DefId,
         fr: RegionVid,
         counter: &mut usize,
index d8f34233839b9796d77f437ff6a2fb7603a84235..c02a492c34100295380e27095bf8a16570957eec 100644 (file)
@@ -1,7 +1,7 @@
 use crate::borrow_check::nll::region_infer::RegionInferenceContext;
 use crate::borrow_check::nll::ToRegionVid;
 use crate::borrow_check::Upvar;
-use rustc::mir::{Local, Mir};
+use rustc::mir::{Local, Body};
 use rustc::ty::{RegionVid, TyCtxt};
 use rustc_data_structures::indexed_vec::Idx;
 use syntax::source_map::Span;
@@ -11,7 +11,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
     crate fn get_var_name_and_span_for_region(
         &self,
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         fr: RegionVid,
     ) -> Option<(Option<Symbol>, Span)> {
@@ -120,7 +120,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
     /// declared.
     crate fn get_argument_name_and_span_for_region(
         &self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         argument_index: usize,
     ) -> (Option<Symbol>, Span) {
         let implicit_inputs = self.universal_regions.defining_ty.implicit_inputs();
index 9dd18ab76a5f2268a7d908e255afb2f1e694e148..4a00571feb11045c59749994892ca7e0fc16aeeb 100644 (file)
@@ -13,7 +13,7 @@
 use rustc::infer::{InferCtxt, NLLRegionVariableOrigin, RegionVariableOrigin};
 use rustc::mir::{
     ClosureOutlivesRequirement, ClosureOutlivesSubject, ClosureRegionRequirements,
-    ConstraintCategory, Local, Location, Mir,
+    ConstraintCategory, Local, Location, Body,
 };
 use rustc::ty::{self, subst::SubstsRef, RegionVid, Ty, TyCtxt, TypeFoldable};
 use rustc::util::common::{self, ErrorReported};
@@ -185,7 +185,7 @@ pub(crate) fn new(
         universal_regions: Rc<UniversalRegions<'tcx>>,
         placeholder_indices: Rc<PlaceholderIndices>,
         universal_region_relations: Rc<UniversalRegionRelations<'tcx>>,
-        _mir: &Mir<'tcx>,
+        _mir: &Body<'tcx>,
         outlives_constraints: ConstraintSet,
         closure_bounds_mapping: FxHashMap<
             Location,
@@ -400,7 +400,7 @@ pub fn to_region_vid(&self, r: ty::Region<'tcx>) -> RegionVid {
     pub(super) fn solve<'gcx>(
         &mut self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         errors_buffer: &mut Vec<Diagnostic>,
@@ -416,7 +416,7 @@ pub(super) fn solve<'gcx>(
     fn solve_inner<'gcx>(
         &mut self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         errors_buffer: &mut Vec<Diagnostic>,
@@ -468,7 +468,7 @@ fn solve_inner<'gcx>(
     /// for each region variable until all the constraints are
     /// satisfied. Note that some values may grow **too** large to be
     /// feasible, but we check this later.
-    fn propagate_constraints(&mut self, _mir: &Mir<'tcx>) {
+    fn propagate_constraints(&mut self, _mir: &Body<'tcx>) {
         debug!("propagate_constraints()");
 
         debug!("propagate_constraints: constraints={:#?}", {
@@ -581,7 +581,7 @@ fn add_incompatible_universe(&mut self, scc: ConstraintSccIndex) {
     fn check_type_tests<'gcx>(
         &self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         mir_def_id: DefId,
         mut propagated_outlives_requirements: Option<&mut Vec<ClosureOutlivesRequirement<'gcx>>>,
         errors_buffer: &mut Vec<Diagnostic>,
@@ -725,7 +725,7 @@ pub fn to_error_region_vid(&self, r: RegionVid) -> Option<RegionVid> {
     fn try_promote_type_test<'gcx>(
         &self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         type_test: &TypeTest<'tcx>,
         propagated_outlives_requirements: &mut Vec<ClosureOutlivesRequirement<'gcx>>,
     ) -> bool {
@@ -944,7 +944,7 @@ fn universal_upper_bound(&self, r: RegionVid) -> RegionVid {
     fn eval_verify_bound(
         &self,
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         generic_ty: Ty<'tcx>,
         lower_bound: RegionVid,
         verify_bound: &VerifyBound<'tcx>,
@@ -977,7 +977,7 @@ fn eval_verify_bound(
     fn eval_if_eq(
         &self,
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         generic_ty: Ty<'tcx>,
         lower_bound: RegionVid,
         test_ty: Ty<'tcx>,
@@ -1037,7 +1037,7 @@ fn normalize_to_scc_representatives<T>(&self, tcx: TyCtxt<'_, '_, 'tcx>, value:
     // Evaluate whether `sup_region: sub_region @ point`.
     fn eval_outlives(
         &self,
-        _mir: &Mir<'tcx>,
+        _mir: &Body<'tcx>,
         sup_region: RegionVid,
         sub_region: RegionVid,
     ) -> bool {
@@ -1105,7 +1105,7 @@ fn eval_outlives(
     fn check_universal_regions<'gcx>(
         &self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         mut propagated_outlives_requirements: Option<&mut Vec<ClosureOutlivesRequirement<'gcx>>>,
@@ -1150,7 +1150,7 @@ fn check_universal_regions<'gcx>(
     fn check_universal_region<'gcx>(
         &self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         longer_fr: RegionVid,
@@ -1216,7 +1216,7 @@ fn check_universal_region_relation(
         longer_fr: RegionVid,
         shorter_fr: RegionVid,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         upvars: &[Upvar],
         mir_def_id: DefId,
         propagated_outlives_requirements: &mut Option<&mut Vec<ClosureOutlivesRequirement<'gcx>>>,
@@ -1282,7 +1282,7 @@ fn check_universal_region_relation(
     fn check_bound_universal_region<'gcx>(
         &self,
         infcx: &InferCtxt<'_, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         _mir_def_id: DefId,
         longer_fr: RegionVid,
         placeholder: ty::PlaceholderRegion,
index 2101447965a15f705d92b5a89a40dfdca51204fe..8822d7bb373934b4fb3129ca492a41c854e399d7 100644 (file)
@@ -1,4 +1,4 @@
-use rustc::mir::{BasicBlock, Location, Mir};
+use rustc::mir::{BasicBlock, Location, Body};
 use rustc::ty::{self, RegionVid};
 use rustc_data_structures::bit_set::{HybridBitSet, SparseBitMatrix};
 use rustc_data_structures::fx::FxHashMap;
@@ -20,7 +20,7 @@
 }
 
 impl RegionValueElements {
-    crate fn new(mir: &Mir<'_>) -> Self {
+    crate fn new(mir: &Body<'_>) -> Self {
         let mut num_points = 0;
         let statements_before_block: IndexVec<BasicBlock, usize> = mir.basic_blocks()
             .iter()
@@ -92,7 +92,7 @@ impl RegionValueElements {
     /// Pushes all predecessors of `index` onto `stack`.
     crate fn push_predecessors(
         &self,
-        mir: &Mir<'_>,
+        mir: &Body<'_>,
         index: PointIndex,
         stack: &mut Vec<PointIndex>,
     ) {
index 58e567c39a9bb74ae157f100ad53299dcea282a6..a3b142c2ffcc309fa7e4c398ce53d4a4de8dbc20 100644 (file)
@@ -1,17 +1,17 @@
 use rustc::ty::subst::SubstsRef;
 use rustc::ty::{self, ClosureSubsts, GeneratorSubsts, Ty, TypeFoldable};
-use rustc::mir::{Location, Mir};
+use rustc::mir::{Location, Body};
 use rustc::mir::visit::{MutVisitor, TyContext};
 use rustc::infer::{InferCtxt, NLLRegionVariableOrigin};
 
 /// Replaces all free regions appearing in the MIR with fresh
 /// inference variables, returning the number of variables created.
-pub fn renumber_mir<'tcx>(infcx: &InferCtxt<'_, '_, 'tcx>, mir: &mut Mir<'tcx>) {
+pub fn renumber_mir<'tcx>(infcx: &InferCtxt<'_, '_, 'tcx>, mir: &mut Body<'tcx>) {
     debug!("renumber_mir()");
     debug!("renumber_mir: mir.arg_count={:?}", mir.arg_count);
 
     let mut visitor = NLLVisitor { infcx };
-    visitor.visit_mir(mir);
+    visitor.visit_body(mir);
 }
 
 /// Replaces all regions appearing in `value` with fresh inference
@@ -47,12 +47,12 @@ fn renumber_regions<T>(&mut self, value: &T) -> T
 }
 
 impl<'a, 'gcx, 'tcx> MutVisitor<'tcx> for NLLVisitor<'a, 'gcx, 'tcx> {
-    fn visit_mir(&mut self, mir: &mut Mir<'tcx>) {
+    fn visit_body(&mut self, mir: &mut Body<'tcx>) {
         for promoted in mir.promoted.iter_mut() {
-            self.visit_mir(promoted);
+            self.visit_body(promoted);
         }
 
-        self.super_mir(mir);
+        self.super_body(mir);
     }
 
     fn visit_ty(&mut self, ty: &mut Ty<'tcx>, ty_context: TyContext) {
index 50828c294fa1b8d83f9d2bb00caa38ed0fd919ac..120088e1784d432d44407764847d557e33296c9e 100644 (file)
@@ -20,7 +20,7 @@
 impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
     pub(super) fn equate_inputs_and_outputs(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         universal_regions: &UniversalRegions<'tcx>,
         normalized_inputs_and_output: &[Ty<'tcx>],
     ) {
index 6ba41806a313f3e43a047d18f01dc64c161a43ed..e1a7b9babd48a7f16b08c5c4488335f0b3ce58a1 100644 (file)
@@ -1,7 +1,7 @@
 use crate::borrow_check::nll::region_infer::values::{PointIndex, RegionValueElements};
 use crate::util::liveness::{categorize, DefUse};
 use rustc::mir::visit::{PlaceContext, Visitor};
-use rustc::mir::{Local, Location, Mir};
+use rustc::mir::{Local, Location, Body};
 use rustc_data_structures::indexed_vec::{Idx, IndexVec};
 use rustc_data_structures::vec_linked_list as vll;
 
@@ -60,7 +60,7 @@ impl LocalUseMap {
     crate fn build(
         live_locals: &Vec<Local>,
         elements: &RegionValueElements,
-        mir: &Mir<'_>,
+        mir: &Body<'_>,
     ) -> Self {
         let nones = IndexVec::from_elem_n(None, mir.local_decls.len());
         let mut local_use_map = LocalUseMap {
@@ -81,7 +81,7 @@ impl LocalUseMap {
             elements,
             locals_with_use_data,
         }
-        .visit_mir(mir);
+        .visit_body(mir);
 
         local_use_map
     }
index 58a164b38f9119e0f221d4f4f914d7208561eeb4..3cefab36e23516575649f6d14ebdef2c732f9644 100644 (file)
@@ -7,7 +7,7 @@
 use crate::dataflow::move_paths::MoveData;
 use crate::dataflow::FlowAtLocation;
 use crate::dataflow::MaybeInitializedPlaces;
-use rustc::mir::{Local, Mir};
+use rustc::mir::{Local, Body};
 use rustc::ty::{RegionVid, TyCtxt};
 use rustc_data_structures::fx::FxHashSet;
 use std::rc::Rc;
@@ -27,7 +27,7 @@
 /// performed before
 pub(super) fn generate<'gcx, 'tcx>(
     typeck: &mut TypeChecker<'_, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     elements: &Rc<RegionValueElements>,
     flow_inits: &mut FlowAtLocation<'tcx, MaybeInitializedPlaces<'_, 'gcx, 'tcx>>,
     move_data: &MoveData<'tcx>,
@@ -77,7 +77,7 @@ pub(super) fn generate<'gcx, 'tcx>(
 fn compute_live_locals(
     tcx: TyCtxt<'_, '_, 'tcx>,
     free_regions: &FxHashSet<RegionVid>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
 ) -> Vec<Local> {
     let live_locals: Vec<Local> = mir
         .local_decls
index 87e9a704fac1e60d26d5fe9b02d2a488cb2dce60..345780c4760eb45a642e45625d32993f29df5231 100644 (file)
@@ -7,7 +7,7 @@
 use crate::dataflow::move_paths::MoveData;
 use crate::dataflow::{FlowAtLocation, FlowsAtLocation, MaybeInitializedPlaces};
 use rustc::infer::canonical::QueryRegionConstraint;
-use rustc::mir::{BasicBlock, ConstraintCategory, Local, Location, Mir};
+use rustc::mir::{BasicBlock, ConstraintCategory, Local, Location, Body};
 use rustc::traits::query::dropck_outlives::DropckOutlivesResult;
 use rustc::traits::query::type_op::outlives::DropckOutlives;
 use rustc::traits::query::type_op::TypeOp;
@@ -32,7 +32,7 @@
 /// this respects `#[may_dangle]` annotations).
 pub(super) fn trace(
     typeck: &mut TypeChecker<'_, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     elements: &Rc<RegionValueElements>,
     flow_inits: &mut FlowAtLocation<'tcx, MaybeInitializedPlaces<'_, 'gcx, 'tcx>>,
     move_data: &MoveData<'tcx>,
@@ -72,7 +72,7 @@ struct LivenessContext<'me, 'typeck, 'flow, 'gcx, 'tcx>
     elements: &'me RegionValueElements,
 
     /// MIR we are analyzing.
-    mir: &'me Mir<'tcx>,
+    mir: &'me Body<'tcx>,
 
     /// Mapping to/from the various indices used for initialization tracking.
     move_data: &'me MoveData<'tcx>,
index de8e75ca277ee78e54bf0056773510b617a32572..ad3b2f985d7023cf0dae1d51fea3918b237e2203 100644 (file)
@@ -112,7 +112,7 @@ macro_rules! span_mirbug_and_err {
 pub(crate) fn type_check<'gcx, 'tcx>(
     infcx: &InferCtxt<'_, 'gcx, 'tcx>,
     param_env: ty::ParamEnv<'gcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     mir_def_id: DefId,
     universal_regions: &Rc<UniversalRegions<'tcx>>,
     location_table: &LocationTable,
@@ -179,7 +179,7 @@ fn type_check_internal<'a, 'gcx, 'tcx, R>(
     infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
     mir_def_id: DefId,
     param_env: ty::ParamEnv<'gcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     region_bound_pairs: &'a RegionBoundPairs<'tcx>,
     implicit_region_bound: ty::Region<'tcx>,
     borrowck_context: &'a mut BorrowCheckContext<'a, 'tcx>,
@@ -198,7 +198,7 @@ fn type_check_internal<'a, 'gcx, 'tcx, R>(
     );
     let errors_reported = {
         let mut verifier = TypeVerifier::new(&mut checker, mir);
-        verifier.visit_mir(mir);
+        verifier.visit_body(mir);
         verifier.errors_reported
     };
 
@@ -253,7 +253,7 @@ enum FieldAccessError {
 /// is a problem.
 struct TypeVerifier<'a, 'b: 'a, 'gcx: 'tcx, 'tcx: 'b> {
     cx: &'a mut TypeChecker<'b, 'gcx, 'tcx>,
-    mir: &'b Mir<'tcx>,
+    mir: &'b Body<'tcx>,
     last_span: Span,
     mir_def_id: DefId,
     errors_reported: bool,
@@ -368,7 +368,7 @@ fn visit_local_decl(&mut self, local: Local, local_decl: &LocalDecl<'tcx>) {
         }
     }
 
-    fn visit_mir(&mut self, mir: &Mir<'tcx>) {
+    fn visit_body(&mut self, mir: &Body<'tcx>) {
         self.sanitize_type(&"return type", mir.return_ty());
         for local_decl in &mir.local_decls {
             self.sanitize_type(local_decl, local_decl.ty);
@@ -376,12 +376,12 @@ fn visit_mir(&mut self, mir: &Mir<'tcx>) {
         if self.errors_reported {
             return;
         }
-        self.super_mir(mir);
+        self.super_body(mir);
     }
 }
 
 impl<'a, 'b, 'gcx, 'tcx> TypeVerifier<'a, 'b, 'gcx, 'tcx> {
-    fn new(cx: &'a mut TypeChecker<'b, 'gcx, 'tcx>, mir: &'b Mir<'tcx>) -> Self {
+    fn new(cx: &'a mut TypeChecker<'b, 'gcx, 'tcx>, mir: &'b Body<'tcx>) -> Self {
         TypeVerifier {
             mir,
             mir_def_id: cx.mir_def_id,
@@ -538,7 +538,7 @@ fn sanitize_place(
         })
     }
 
-    fn sanitize_promoted(&mut self, promoted_mir: &'b Mir<'tcx>, location: Location) {
+    fn sanitize_promoted(&mut self, promoted_mir: &'b Body<'tcx>, location: Location) {
         // Determine the constraints from the promoted MIR by running the type
         // checker on the promoted MIR, then transfer the constraints back to
         // the main MIR, changing the locations to the provided location.
@@ -562,7 +562,7 @@ fn sanitize_promoted(&mut self, promoted_mir: &'b Mir<'tcx>, location: Location)
             &mut closure_bounds
         );
 
-        self.visit_mir(promoted_mir);
+        self.visit_body(promoted_mir);
 
         if !self.errors_reported {
             // if verifier failed, don't do further checks to avoid ICEs
@@ -969,7 +969,7 @@ pub fn from_location(&self) -> Option<Location> {
     }
 
     /// Gets a span representing the location.
-    pub fn span(&self, mir: &Mir<'_>) -> Span {
+    pub fn span(&self, mir: &Body<'_>) -> Span {
         match self {
             Locations::All(span) => *span,
             Locations::Single(l) => mir.source_info(*l).span,
@@ -980,7 +980,7 @@ pub fn span(&self, mir: &Mir<'_>) -> Span {
 impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
     fn new(
         infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
-        mir: &'a Mir<'tcx>,
+        mir: &'a Body<'tcx>,
         mir_def_id: DefId,
         param_env: ty::ParamEnv<'gcx>,
         region_bound_pairs: &'a RegionBoundPairs<'tcx>,
@@ -1263,7 +1263,7 @@ fn eq_opaque_type_and_type(
                         debug!(
                             "eq_opaque_type_and_type: concrete_ty={:?}={:?} opaque_defn_ty={:?}",
                             opaque_decl.concrete_ty,
-                            infcx.resolve_type_vars_if_possible(&opaque_decl.concrete_ty),
+                            infcx.resolve_vars_if_possible(&opaque_decl.concrete_ty),
                             opaque_defn_ty
                         );
                         obligations.add(infcx
@@ -1317,7 +1317,7 @@ fn tcx(&self) -> TyCtxt<'a, 'gcx, 'tcx> {
         self.infcx.tcx
     }
 
-    fn check_stmt(&mut self, mir: &Mir<'tcx>, stmt: &Statement<'tcx>, location: Location) {
+    fn check_stmt(&mut self, mir: &Body<'tcx>, stmt: &Statement<'tcx>, location: Location) {
         debug!("check_stmt: {:?}", stmt);
         let tcx = self.tcx();
         match stmt.kind {
@@ -1456,7 +1456,7 @@ fn check_stmt(&mut self, mir: &Mir<'tcx>, stmt: &Statement<'tcx>, location: Loca
 
     fn check_terminator(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         term: &Terminator<'tcx>,
         term_location: Location,
     ) {
@@ -1618,7 +1618,7 @@ fn check_terminator(
 
     fn check_call_dest(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         term: &Terminator<'tcx>,
         sig: &ty::FnSig<'tcx>,
         destination: &Option<(Place<'tcx>, BasicBlock)>,
@@ -1687,7 +1687,7 @@ fn check_call_dest(
 
     fn check_call_inputs(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         term: &Terminator<'tcx>,
         sig: &ty::FnSig<'tcx>,
         args: &[Operand<'tcx>],
@@ -1728,7 +1728,7 @@ fn check_call_inputs(
         }
     }
 
-    fn check_iscleanup(&mut self, mir: &Mir<'tcx>, block_data: &BasicBlockData<'tcx>) {
+    fn check_iscleanup(&mut self, mir: &Body<'tcx>, block_data: &BasicBlockData<'tcx>) {
         let is_cleanup = block_data.is_cleanup;
         self.last_span = block_data.terminator().source_info.span;
         match block_data.terminator().kind {
@@ -1820,7 +1820,7 @@ fn check_iscleanup(&mut self, mir: &Mir<'tcx>, block_data: &BasicBlockData<'tcx>
 
     fn assert_iscleanup(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         ctxt: &dyn fmt::Debug,
         bb: BasicBlock,
         iscleanuppad: bool,
@@ -1836,7 +1836,7 @@ fn assert_iscleanup(
         }
     }
 
-    fn check_local(&mut self, mir: &Mir<'tcx>, local: Local, local_decl: &LocalDecl<'tcx>) {
+    fn check_local(&mut self, mir: &Body<'tcx>, local: Local, local_decl: &LocalDecl<'tcx>) {
         match mir.local_kind(local) {
             LocalKind::ReturnPointer | LocalKind::Arg => {
                 // return values of normal functions are required to be
@@ -1938,7 +1938,7 @@ fn aggregate_field_ty(
         }
     }
 
-    fn check_rvalue(&mut self, mir: &Mir<'tcx>, rvalue: &Rvalue<'tcx>, location: Location) {
+    fn check_rvalue(&mut self, mir: &Body<'tcx>, rvalue: &Rvalue<'tcx>, location: Location) {
         let tcx = self.tcx();
 
         match rvalue {
@@ -2274,7 +2274,7 @@ fn rvalue_user_ty(&self, rvalue: &Rvalue<'tcx>) -> Option<UserTypeAnnotationInde
 
     fn check_aggregate_rvalue(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         rvalue: &Rvalue<'tcx>,
         aggregate_kind: &AggregateKind<'tcx>,
         operands: &[Operand<'tcx>],
@@ -2332,7 +2332,7 @@ fn check_aggregate_rvalue(
     /// - `borrowed_place`: the place `P` being borrowed
     fn add_reborrow_constraint(
         &mut self,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         location: Location,
         borrow_region: ty::Region<'tcx>,
         borrowed_place: &Place<'tcx>,
@@ -2621,7 +2621,7 @@ fn prove_predicate(
         })
     }
 
-    fn typeck_mir(&mut self, mir: &Mir<'tcx>) {
+    fn typeck_mir(&mut self, mir: &Body<'tcx>) {
         self.last_span = mir.span;
         debug!("run_on_mir: {:?}", mir.span);
 
index caef8d8bc5a925820b1f7b1ec86581757113d220..557d235c23f0555b8ced991aa4b5b93d61f7edef 100644 (file)
@@ -2,7 +2,7 @@
 use crate::borrow_check::places_conflict;
 use crate::borrow_check::AccessDepth;
 use crate::dataflow::indexes::BorrowIndex;
-use rustc::mir::{BasicBlock, Location, Mir, Place, PlaceBase};
+use rustc::mir::{BasicBlock, Location, Body, Place, PlaceBase};
 use rustc::mir::{ProjectionElem, BorrowKind};
 use rustc::ty::TyCtxt;
 use rustc_data_structures::graph::dominators::Dominators;
@@ -25,7 +25,7 @@ pub(super) enum Control {
 pub(super) fn each_borrow_involving_path<'a, 'tcx, 'gcx: 'tcx, F, I, S> (
     s: &mut S,
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     _location: Location,
     access_place: (AccessDepth, &Place<'tcx>),
     borrow_set: &BorrowSet<'tcx>,
index 9ad0e936e1b2d7b4283bd0b0c5f8f2134106eb8e..9306e88e9ae9c804704a2a015a31700566d86c22 100644 (file)
@@ -1,6 +1,6 @@
 use rustc::hir;
 use rustc::mir::ProjectionElem;
-use rustc::mir::{Mir, Place, PlaceBase, Mutability, Static, StaticKind};
+use rustc::mir::{Body, Place, PlaceBase, Mutability, Static, StaticKind};
 use rustc::ty::{self, TyCtxt};
 use crate::borrow_check::borrow_set::LocalsStateAtExit;
 
@@ -13,7 +13,7 @@
     fn ignore_borrow(
         &self,
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         locals_state_at_exit: &LocalsStateAtExit,
         ) -> bool;
 }
@@ -22,7 +22,7 @@ impl<'tcx> PlaceExt<'tcx> for Place<'tcx> {
     fn ignore_borrow(
         &self,
         tcx: TyCtxt<'_, '_, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         locals_state_at_exit: &LocalsStateAtExit,
     ) -> bool {
         self.iterate(|place_base, place_projection| {
index c9e8d9894783b7c55ab17672431f01f4409b4311..74da3f96653e4314612c044c4f3e1414528e1cbc 100644 (file)
@@ -3,7 +3,7 @@
 use crate::borrow_check::{Deep, Shallow, AccessDepth};
 use rustc::hir;
 use rustc::mir::{
-    BorrowKind, Mir, Place, PlaceBase, Projection, ProjectionElem, ProjectionsIter,
+    BorrowKind, Body, Place, PlaceBase, Projection, ProjectionElem, ProjectionsIter,
     StaticKind
 };
 use rustc::ty::{self, TyCtxt};
@@ -26,7 +26,7 @@
 /// dataflow).
 crate fn places_conflict<'gcx, 'tcx>(
     tcx: TyCtxt<'_, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     borrow_place: &Place<'tcx>,
     access_place: &Place<'tcx>,
     bias: PlaceConflictBias,
@@ -48,7 +48,7 @@
 /// order to make the conservative choice and preserve soundness.
 pub(super) fn borrow_conflicts_with_place<'gcx, 'tcx>(
     tcx: TyCtxt<'_, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     borrow_place: &Place<'tcx>,
     borrow_kind: BorrowKind,
     access_place: &Place<'tcx>,
@@ -85,7 +85,7 @@ pub(super) fn borrow_conflicts_with_place<'gcx, 'tcx>(
 
 fn place_components_conflict<'gcx, 'tcx>(
     tcx: TyCtxt<'_, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     borrow_projections: (&PlaceBase<'tcx>, ProjectionsIter<'_, 'tcx>),
     borrow_kind: BorrowKind,
     access_projections: (&PlaceBase<'tcx>, ProjectionsIter<'_, 'tcx>),
@@ -367,7 +367,7 @@ fn place_base_conflict<'a, 'gcx: 'tcx, 'tcx>(
 // between `elem1` and `elem2`.
 fn place_projection_conflict<'a, 'gcx: 'tcx, 'tcx>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     pi1: &Projection<'tcx>,
     pi2: &Projection<'tcx>,
     bias: PlaceConflictBias,
index 866f1cf994e69669508e953f4d0424263837d7c6..0e1abeba70dffb0a834faa654fcea54c746905bc 100644 (file)
@@ -11,7 +11,7 @@
 
 use rustc::hir;
 use rustc::ty::{self, TyCtxt};
-use rustc::mir::{Mir, Place, PlaceBase, ProjectionElem};
+use rustc::mir::{Body, Place, PlaceBase, ProjectionElem};
 
 pub trait IsPrefixOf<'tcx> {
     fn is_prefix_of(&self, other: &Place<'tcx>) -> bool;
@@ -38,7 +38,7 @@ fn is_prefix_of(&self, other: &Place<'tcx>) -> bool {
 
 
 pub(super) struct Prefixes<'cx, 'gcx: 'tcx, 'tcx: 'cx> {
-    mir: &'cx Mir<'tcx>,
+    mir: &'cx Body<'tcx>,
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     kind: PrefixSet,
     next: Option<&'cx Place<'tcx>>,
index f4866fad9a5fd8c720714ceb1941913f25c34023..abfc2f9466c8ed74aca33687e7b421ec51aff0cc 100644 (file)
@@ -34,7 +34,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
                 never_initialized_mut_locals: &mut never_initialized_mut_locals,
                 mbcx: self,
             };
-            visitor.visit_mir(visitor.mbcx.mir);
+            visitor.visit_body(visitor.mbcx.mir);
         }
 
         // Take the union of the existed `used_mut` set with those variables we've found were
index 07a9f294fb68cd455919ee2a63fa429b1053ff4d..685db7713cac16dd5f3e713e3b5db6e44d02e74e 100644 (file)
@@ -528,7 +528,7 @@ fn limit_capture_mutability(
             }) => {
                 // Not projected from the implicit `self` in a closure.
                 debug_assert!(
-                    match base.local() {
+                    match base.local_or_deref_local() {
                         Some(local) => local == Local::new(1),
                         None => false,
                     },
index 55b5d5d1471ac0ff8907c407f57835134ee368e9..5797f9c34786617d01d834d833da6768e8212f74 100644 (file)
@@ -26,7 +26,7 @@
 use super::lints;
 
 /// Construct the MIR for a given `DefId`.
-pub fn mir_build<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Mir<'tcx> {
+pub fn mir_build<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Body<'tcx> {
     let id = tcx.hir().as_local_hir_id(def_id).unwrap();
 
     // Figure out what primary body this item has.
@@ -164,14 +164,14 @@ pub fn mir_build<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Mir<'t
             build::construct_const(cx, body_id, return_ty, return_ty_span)
         };
 
-        // Convert the Mir to global types.
+        // Convert the `mir::Body` to global types.
         let mut globalizer = GlobalizeMir {
             tcx,
             span: mir.span
         };
-        globalizer.visit_mir(&mut mir);
+        globalizer.visit_body(&mut mir);
         let mir = unsafe {
-            mem::transmute::<Mir<'_>, Mir<'tcx>>(mir)
+            mem::transmute::<Body<'_>, Body<'tcx>>(mir)
         };
 
         mir_util::dump_mir(tcx, None, "mir_map", &0,
@@ -236,22 +236,22 @@ fn visit_substs(&mut self, substs: &mut SubstsRef<'tcx>, _: Location) {
 fn create_constructor_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                                      ctor_id: hir::HirId,
                                      v: &'tcx hir::VariantData)
-                                     -> Mir<'tcx>
+                                     -> Body<'tcx>
 {
     let span = tcx.hir().span_by_hir_id(ctor_id);
     if let hir::VariantData::Tuple(ref fields, ctor_id) = *v {
         tcx.infer_ctxt().enter(|infcx| {
             let mut mir = shim::build_adt_ctor(&infcx, ctor_id, fields, span);
 
-            // Convert the Mir to global types.
+            // Convert the `mir::Body` to global types.
             let tcx = infcx.tcx.global_tcx();
             let mut globalizer = GlobalizeMir {
                 tcx,
                 span: mir.span
             };
-            globalizer.visit_mir(&mut mir);
+            globalizer.visit_body(&mut mir);
             let mir = unsafe {
-                mem::transmute::<Mir<'_>, Mir<'tcx>>(mir)
+                mem::transmute::<Body<'_>, Body<'tcx>>(mir)
             };
 
             mir_util::dump_mir(tcx, None, "mir_map", &0,
@@ -628,7 +628,7 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>,
                                    yield_ty: Option<Ty<'gcx>>,
                                    return_ty_span: Span,
                                    body: &'gcx hir::Body)
-                                   -> Mir<'tcx>
+                                   -> Body<'tcx>
     where A: Iterator<Item=ArgInfo<'gcx>>
 {
     let arguments: Vec<_> = arguments.collect();
@@ -748,7 +748,7 @@ fn construct_const<'a, 'gcx, 'tcx>(
     body_id: hir::BodyId,
     const_ty: Ty<'tcx>,
     const_ty_span: Span,
-) -> Mir<'tcx> {
+) -> Body<'tcx> {
     let tcx = hir.tcx();
     let owner_id = tcx.hir().body_owner(body_id);
     let span = tcx.hir().span(owner_id);
@@ -787,7 +787,7 @@ fn construct_const<'a, 'gcx, 'tcx>(
 
 fn construct_error<'a, 'gcx, 'tcx>(hir: Cx<'a, 'gcx, 'tcx>,
                                    body_id: hir::BodyId)
-                                   -> Mir<'tcx> {
+                                   -> Body<'tcx> {
     let owner_id = hir.tcx().hir().body_owner(body_id);
     let span = hir.tcx().hir().span(owner_id);
     let ty = hir.tcx().types.err;
@@ -849,14 +849,14 @@ fn new(hir: Cx<'a, 'gcx, 'tcx>,
 
     fn finish(self,
               yield_ty: Option<Ty<'tcx>>)
-              -> Mir<'tcx> {
+              -> Body<'tcx> {
         for (index, block) in self.cfg.basic_blocks.iter().enumerate() {
             if block.terminator.is_none() {
                 span_bug!(self.fn_span, "no terminator on block {:?}", index);
             }
         }
 
-        Mir::new(
+        Body::new(
             self.cfg.basic_blocks,
             self.source_scopes,
             ClearCrossCrate::Set(self.source_scope_local_data),
index c43bc41ba685ec7d1b1881fa6d4bf0223bab11f2..0637c7b0588827de149d11319a5176731e1fb8fc 100644 (file)
@@ -55,7 +55,7 @@ pub(crate) fn mk_eval_cx<'a, 'mir, 'tcx>(
 pub(crate) fn eval_promoted<'a, 'mir, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     cid: GlobalId<'tcx>,
-    mir: &'mir mir::Mir<'tcx>,
+    mir: &'mir mir::Body<'tcx>,
     param_env: ty::ParamEnv<'tcx>,
 ) -> EvalResult<'tcx, MPlaceTy<'tcx>> {
     let span = tcx.def_span(cid.instance.def_id());
@@ -115,7 +115,7 @@ fn op_to_const<'tcx>(
                     ecx.tcx.alloc_map.lock().unwrap_memory(ptr.alloc_id),
                     ptr.offset.bytes(),
                 ),
-                Scalar::Bits { .. } => (
+                Scalar::Raw { .. } => (
                     ecx.tcx.intern_const_alloc(Allocation::from_byte_aligned_bytes(b"", ())),
                     0,
                 ),
@@ -137,7 +137,7 @@ fn op_to_const<'tcx>(
 fn eval_body_using_ecx<'mir, 'tcx>(
     ecx: &mut CompileTimeEvalContext<'_, 'mir, 'tcx>,
     cid: GlobalId<'tcx>,
-    mir: &'mir mir::Mir<'tcx>,
+    mir: &'mir mir::Body<'tcx>,
     param_env: ty::ParamEnv<'tcx>,
 ) -> EvalResult<'tcx, MPlaceTy<'tcx>> {
     debug!("eval_body_using_ecx: {:?}, {:?}", cid, param_env);
@@ -331,7 +331,7 @@ fn find_fn(
         args: &[OpTy<'tcx>],
         dest: Option<PlaceTy<'tcx>>,
         ret: Option<mir::BasicBlock>,
-    ) -> EvalResult<'tcx, Option<&'mir mir::Mir<'tcx>>> {
+    ) -> EvalResult<'tcx, Option<&'mir mir::Body<'tcx>>> {
         debug!("eval_fn_call: {:?}", instance);
         // Only check non-glue functions
         if let ty::InstanceDef::Item(def_id) = instance.def {
index 66ca4b4dc8922aff37035690aaa216ff20b5c338..f9d88ab879596f916438b9d240730ad324ac80ba 100644 (file)
@@ -1,4 +1,4 @@
-use rustc::mir::{self, Mir, Location};
+use rustc::mir::{self, Body, Location};
 use rustc::ty::{self, TyCtxt};
 use crate::util::elaborate_drops::DropFlagState;
 
@@ -47,7 +47,7 @@ pub fn move_path_children_matching<'tcx, F>(move_data: &MoveData<'tcx>,
 //
 // FIXME: we have to do something for moving slice patterns.
 fn place_contents_drop_state_cannot_differ<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-                                                            mir: &Mir<'tcx>,
+                                                            mir: &Body<'tcx>,
                                                             place: &mir::Place<'tcx>) -> bool {
     let ty = place.ty(mir, tcx).ty;
     match ty.sty {
@@ -74,7 +74,7 @@ fn place_contents_drop_state_cannot_differ<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx,
 
 pub(crate) fn on_lookup_result_bits<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     move_data: &MoveData<'tcx>,
     lookup_result: LookupResult,
     each_child: F)
@@ -92,7 +92,7 @@ pub(crate) fn on_lookup_result_bits<'a, 'gcx, 'tcx, F>(
 
 pub(crate) fn on_all_children_bits<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     move_data: &MoveData<'tcx>,
     move_path_index: MovePathIndex,
     mut each_child: F)
@@ -100,7 +100,7 @@ pub(crate) fn on_all_children_bits<'a, 'gcx, 'tcx, F>(
 {
     fn is_terminal_path<'a, 'gcx, 'tcx>(
         tcx: TyCtxt<'a, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         move_data: &MoveData<'tcx>,
         path: MovePathIndex) -> bool
     {
@@ -110,7 +110,7 @@ fn is_terminal_path<'a, 'gcx, 'tcx>(
 
     fn on_all_children_bits<'a, 'gcx, 'tcx, F>(
         tcx: TyCtxt<'a, 'gcx, 'tcx>,
-        mir: &Mir<'tcx>,
+        mir: &Body<'tcx>,
         move_data: &MoveData<'tcx>,
         move_path_index: MovePathIndex,
         each_child: &mut F)
@@ -133,7 +133,7 @@ fn on_all_children_bits<'a, 'gcx, 'tcx, F>(
 
 pub(crate) fn on_all_drop_children_bits<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     ctxt: &MoveDataParamEnv<'gcx, 'tcx>,
     path: MovePathIndex,
     mut each_child: F)
@@ -156,7 +156,7 @@ pub(crate) fn on_all_drop_children_bits<'a, 'gcx, 'tcx, F>(
 
 pub(crate) fn drop_flag_effects_for_function_entry<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     ctxt: &MoveDataParamEnv<'gcx, 'tcx>,
     mut callback: F)
     where F: FnMut(MovePathIndex, DropFlagState)
@@ -173,7 +173,7 @@ pub(crate) fn drop_flag_effects_for_function_entry<'a, 'gcx, 'tcx, F>(
 
 pub(crate) fn drop_flag_effects_for_location<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     ctxt: &MoveDataParamEnv<'gcx, 'tcx>,
     loc: Location,
     mut callback: F)
@@ -205,7 +205,7 @@ pub(crate) fn drop_flag_effects_for_location<'a, 'gcx, 'tcx, F>(
 
 pub(crate) fn for_location_inits<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     move_data: &MoveData<'tcx>,
     loc: Location,
     mut callback: F)
index d68377681f1ca935ad6a2cc4468a320059c4b483..4965f1a585d482aad4e9d6f2b0569d047879ae39 100644 (file)
@@ -1,7 +1,7 @@
 //! Hook into libgraphviz for rendering dataflow graphs for MIR.
 
 use rustc::hir::def_id::DefId;
-use rustc::mir::{BasicBlock, Mir};
+use rustc::mir::{BasicBlock, Body};
 
 use std::fs;
 use std::io;
@@ -17,7 +17,7 @@
 pub trait MirWithFlowState<'tcx> {
     type BD: BitDenotation<'tcx>;
     fn def_id(&self) -> DefId;
-    fn mir(&self) -> &Mir<'tcx>;
+    fn mir(&self) -> &Body<'tcx>;
     fn flow_state(&self) -> &DataflowState<'tcx, Self::BD>;
 }
 
@@ -26,7 +26,7 @@ impl<'a, 'tcx, BD> MirWithFlowState<'tcx> for DataflowBuilder<'a, 'tcx, BD>
 {
     type BD = BD;
     fn def_id(&self) -> DefId { self.def_id }
-    fn mir(&self) -> &Mir<'tcx> { self.flow_state.mir() }
+    fn mir(&self) -> &Body<'tcx> { self.flow_state.mir() }
     fn flow_state(&self) -> &DataflowState<'tcx, Self::BD> { &self.flow_state.flow_state }
 }
 
@@ -59,7 +59,7 @@ pub(crate) fn print_borrowck_graph_to<'a, 'tcx, BD, P>(
 #[derive(Copy, Clone, PartialEq, Eq, Debug)]
 pub struct Edge { source: BasicBlock, index: usize }
 
-fn outgoing(mir: &Mir<'_>, bb: BasicBlock) -> Vec<Edge> {
+fn outgoing(mir: &Body<'_>, bb: BasicBlock) -> Vec<Edge> {
     (0..mir[bb].terminator().successors().count())
         .map(|index| Edge { source: bb, index: index}).collect()
 }
@@ -124,7 +124,7 @@ fn node_label_internal<W: io::Write>(&self,
                                          n: &Node,
                                          w: &mut W,
                                          block: BasicBlock,
-                                         mir: &Mir<'_>) -> io::Result<()> {
+                                         mir: &Body<'_>) -> io::Result<()> {
         // Header rows
         const HDRS: [&str; 4] = ["ENTRY", "MIR", "BLOCK GENS", "BLOCK KILLS"];
         const HDR_FMT: &str = "bgcolor=\"grey\"";
@@ -149,7 +149,7 @@ fn node_label_verbose_row<W: io::Write>(&self,
                                             n: &Node,
                                             w: &mut W,
                                             block: BasicBlock,
-                                            mir: &Mir<'_>)
+                                            mir: &Body<'_>)
                                             -> io::Result<()> {
         let i = n.index();
 
@@ -199,7 +199,7 @@ fn node_label_final_row<W: io::Write>(&self,
                                           n: &Node,
                                           w: &mut W,
                                           block: BasicBlock,
-                                          mir: &Mir<'_>)
+                                          mir: &Body<'_>)
                                           -> io::Result<()> {
         let i = n.index();
 
index 65cbc83fbcb84edb7337bb89f873bb30e4d9dac6..47af10a1c5023072d6431a02073a8514e6263d44 100644 (file)
 /// immovable generators.
 #[derive(Copy, Clone)]
 pub struct HaveBeenBorrowedLocals<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 }
 
 impl<'a, 'tcx: 'a> HaveBeenBorrowedLocals<'a, 'tcx> {
-    pub fn new(mir: &'a Mir<'tcx>)
+    pub fn new(mir: &'a Body<'tcx>)
                -> Self {
         HaveBeenBorrowedLocals { mir }
     }
 
-    pub fn mir(&self) -> &Mir<'tcx> {
+    pub fn mir(&self) -> &Body<'tcx> {
         self.mir
     }
 }
index 43cb0ed4565fe6f38b100c9b79c0168358b49941..99051fb37f1488b9e91ada1e849971d2a75d4326 100644 (file)
@@ -1,7 +1,7 @@
 use crate::borrow_check::borrow_set::{BorrowSet, BorrowData};
 use crate::borrow_check::place_ext::PlaceExt;
 
-use rustc::mir::{self, Location, Place, PlaceBase, Mir};
+use rustc::mir::{self, Location, Place, PlaceBase, Body};
 use rustc::ty::TyCtxt;
 use rustc::ty::RegionVid;
 
@@ -31,7 +31,7 @@ pub struct BorrowIndex {
 /// borrows in compact bitvectors.
 pub struct Borrows<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 
     borrow_set: Rc<BorrowSet<'tcx>>,
     borrows_out_of_scope_at_location: FxHashMap<Location, Vec<BorrowIndex>>,
@@ -48,7 +48,7 @@ struct StackEntry {
 }
 
 fn precompute_borrows_out_of_scope<'tcx>(
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     regioncx: &Rc<RegionInferenceContext<'tcx>>,
     borrows_out_of_scope_at_location: &mut FxHashMap<Location, Vec<BorrowIndex>>,
     borrow_index: BorrowIndex,
@@ -136,7 +136,7 @@ fn precompute_borrows_out_of_scope<'tcx>(
 impl<'a, 'gcx, 'tcx> Borrows<'a, 'gcx, 'tcx> {
     crate fn new(
         tcx: TyCtxt<'a, 'gcx, 'tcx>,
-        mir: &'a Mir<'tcx>,
+        mir: &'a Body<'tcx>,
         nonlexical_regioncx: Rc<RegionInferenceContext<'tcx>>,
         borrow_set: &Rc<BorrowSet<'tcx>>,
     ) -> Self {
index 03d55b84f32e260f38dce78551558c77388c331f..4f3b180edd111812323a536db9e87da2cc3a7a09 100644 (file)
@@ -3,7 +3,7 @@
 //! zero-sized structure.
 
 use rustc::ty::TyCtxt;
-use rustc::mir::{self, Mir, Location};
+use rustc::mir::{self, Body, Location};
 use rustc_data_structures::bit_set::{BitSet, BitSetOperator};
 use rustc_data_structures::indexed_vec::Idx;
 
 /// places that would require a dynamic drop-flag at that statement.
 pub struct MaybeInitializedPlaces<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>,
 }
 
 impl<'a, 'gcx: 'tcx, 'tcx> MaybeInitializedPlaces<'a, 'gcx, 'tcx> {
     pub fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-               mir: &'a Mir<'tcx>,
+               mir: &'a Body<'tcx>,
                mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>)
                -> Self
     {
@@ -120,13 +120,13 @@ fn move_data(&self) -> &MoveData<'tcx> { &self.mdpe.move_data }
 /// places that would require a dynamic drop-flag at that statement.
 pub struct MaybeUninitializedPlaces<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>,
 }
 
 impl<'a, 'gcx, 'tcx> MaybeUninitializedPlaces<'a, 'gcx, 'tcx> {
     pub fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-               mir: &'a Mir<'tcx>,
+               mir: &'a Body<'tcx>,
                mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>)
                -> Self
     {
@@ -174,13 +174,13 @@ fn move_data(&self) -> &MoveData<'tcx> { &self.mdpe.move_data }
 /// that would require a dynamic drop-flag at that statement.
 pub struct DefinitelyInitializedPlaces<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>,
 }
 
 impl<'a, 'gcx, 'tcx: 'a> DefinitelyInitializedPlaces<'a, 'gcx, 'tcx> {
     pub fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-               mir: &'a Mir<'tcx>,
+               mir: &'a Body<'tcx>,
                mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>)
                -> Self
     {
@@ -223,13 +223,13 @@ fn move_data(&self) -> &MoveData<'tcx> { &self.mdpe.move_data }
 /// ```
 pub struct EverInitializedPlaces<'a, 'gcx: 'tcx, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>,
 }
 
 impl<'a, 'gcx: 'tcx, 'tcx: 'a> EverInitializedPlaces<'a, 'gcx, 'tcx> {
     pub fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-               mir: &'a Mir<'tcx>,
+               mir: &'a Body<'tcx>,
                mdpe: &'a MoveDataParamEnv<'gcx, 'tcx>)
                -> Self
     {
index 3bf11c57379c24fcc2dad7781c358c233cee79db..0fb66032a171dd085f299a8e860c138289d4083e 100644 (file)
@@ -5,16 +5,16 @@
 
 #[derive(Copy, Clone)]
 pub struct MaybeStorageLive<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 }
 
 impl<'a, 'tcx: 'a> MaybeStorageLive<'a, 'tcx> {
-    pub fn new(mir: &'a Mir<'tcx>)
+    pub fn new(mir: &'a Body<'tcx>)
                -> Self {
         MaybeStorageLive { mir }
     }
 
-    pub fn mir(&self) -> &Mir<'tcx> {
+    pub fn mir(&self) -> &Body<'tcx> {
         self.mir
     }
 }
@@ -46,8 +46,10 @@ fn terminator_effect(&self,
                          sets: &mut BlockSets<'_, Local>,
                          loc: Location) {
         match &self.mir[loc.block].terminator().kind {
-            TerminatorKind::Drop { location, .. } => if let Some(l) = location.local() {
-                sets.kill(l);
+            TerminatorKind::Drop { location, .. } => {
+                if let Some(l) = location.local_or_deref_local() {
+                    sets.kill(l);
+                }
             }
             _ => (),
         }
index a9d23a0afeabcc3a6ef79a0fd9ddd1ccea0ac1ad..26bad0cb04d7061271f9b85deefd1b2bae33aff3 100644 (file)
@@ -7,7 +7,7 @@
 
 use rustc::hir::def_id::DefId;
 use rustc::ty::{self, TyCtxt};
-use rustc::mir::{self, Mir, BasicBlock, BasicBlockData, Location, Statement, Terminator};
+use rustc::mir::{self, Body, BasicBlock, BasicBlockData, Location, Statement, Terminator};
 use rustc::mir::traversal;
 use rustc::session::Session;
 
@@ -122,7 +122,7 @@ pub struct MoveDataParamEnv<'gcx, 'tcx> {
 }
 
 pub(crate) fn do_dataflow<'a, 'gcx, 'tcx, BD, P>(tcx: TyCtxt<'a, 'gcx, 'tcx>,
-                                                 mir: &'a Mir<'tcx>,
+                                                 mir: &'a Body<'tcx>,
                                                  def_id: DefId,
                                                  attributes: &[ast::Attribute],
                                                  dead_unwinds: &BitSet<BasicBlock>,
@@ -343,13 +343,13 @@ fn process_basic_block(&mut self, bb: BasicBlock, flow_state: &mut Self::FlowSta
 
     // Delegated Hooks: Provide access to the MIR and process the flow state.
 
-    fn mir(&self) -> &'a Mir<'tcx>;
+    fn mir(&self) -> &'a Body<'tcx>;
 }
 
 pub fn state_for_location<'tcx, T: BitDenotation<'tcx>>(loc: Location,
                                                         analysis: &T,
                                                         result: &DataflowResults<'tcx, T>,
-                                                        mir: &Mir<'tcx>)
+                                                        mir: &Body<'tcx>)
     -> BitSet<T::Idx> {
     let mut on_entry = result.sets().on_entry_set_for(loc.block.index()).to_owned();
     let mut kill_set = on_entry.to_hybrid();
@@ -384,7 +384,7 @@ pub struct DataflowAnalysis<'a, 'tcx: 'a, O> where O: BitDenotation<'tcx>
 {
     flow_state: DataflowState<'tcx, O>,
     dead_unwinds: &'a BitSet<mir::BasicBlock>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 }
 
 impl<'a, 'tcx: 'a, O> DataflowAnalysis<'a, 'tcx, O> where O: BitDenotation<'tcx>
@@ -393,7 +393,7 @@ pub fn results(self) -> DataflowResults<'tcx, O> {
         DataflowResults(self.flow_state)
     }
 
-    pub fn mir(&self) -> &'a Mir<'tcx> { self.mir }
+    pub fn mir(&self) -> &'a Body<'tcx> { self.mir }
 }
 
 pub struct DataflowResults<'tcx, O>(pub(crate) DataflowState<'tcx, O>) where O: BitDenotation<'tcx>;
@@ -697,7 +697,7 @@ fn propagate_call_return(
 
 impl<'a, 'tcx, D> DataflowAnalysis<'a, 'tcx, D> where D: BitDenotation<'tcx>
 {
-    pub fn new(mir: &'a Mir<'tcx>,
+    pub fn new(mir: &'a Body<'tcx>,
                dead_unwinds: &'a BitSet<mir::BasicBlock>,
                denotation: D) -> Self where D: InitialFlow {
         let bits_per_block = denotation.bits_per_block();
index ab0a2d87302c8fab064cecb9a3fde0f2f1dda68d..816a269625399e7706a946a4658287c1c816c0f1 100644 (file)
 use super::IllegalMoveOriginKind::*;
 
 struct MoveDataBuilder<'a, 'gcx: 'tcx, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
     data: MoveData<'tcx>,
     errors: Vec<(Place<'tcx>, MoveError<'tcx>)>,
 }
 
 impl<'a, 'gcx, 'tcx> MoveDataBuilder<'a, 'gcx, 'tcx> {
-    fn new(mir: &'a Mir<'tcx>, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> Self {
+    fn new(mir: &'a Body<'tcx>, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> Self {
         let mut move_paths = IndexVec::new();
         let mut path_map = IndexVec::new();
         let mut init_path_map = IndexVec::new();
@@ -203,7 +203,7 @@ fn finalize(
 }
 
 pub(super) fn gather_moves<'a, 'gcx, 'tcx>(
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     tcx: TyCtxt<'a, 'gcx, 'tcx>
 ) -> Result<MoveData<'tcx>, (MoveData<'tcx>, Vec<(Place<'tcx>, MoveError<'tcx>)>)> {
     let mut builder = MoveDataBuilder::new(mir, tcx);
index 7aaf44a8a890ee9e33ceddf0676191b285325018..0d20040d0d2d7d187fec366870ef3bc0129dcca9 100644 (file)
@@ -138,7 +138,7 @@ fn index_mut(&mut self, index: Location) -> &mut Self::Output {
 }
 
 impl<T> LocationMap<T> where T: Default + Clone {
-    fn new(mir: &Mir<'_>) -> Self {
+    fn new(mir: &Body<'_>) -> Self {
         LocationMap {
             map: mir.basic_blocks().iter().map(|block| {
                 vec![T::default(); block.statements.len()+1]
@@ -205,7 +205,7 @@ fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
 }
 
 impl Init {
-    crate fn span<'gcx>(&self, mir: &Mir<'gcx>) -> Span {
+    crate fn span<'gcx>(&self, mir: &Body<'gcx>) -> Span {
         match self.location {
             InitLocation::Argument(local) => mir.local_decls[local].source_info.span,
             InitLocation::Statement(location) => mir.source_info(location).span,
@@ -306,7 +306,7 @@ fn cannot_move_out_of(location: Location, kind: IllegalMoveOriginKind<'tcx>) ->
 }
 
 impl<'a, 'gcx, 'tcx> MoveData<'tcx> {
-    pub fn gather_moves(mir: &Mir<'tcx>, tcx: TyCtxt<'a, 'gcx, 'tcx>)
+    pub fn gather_moves(mir: &Body<'tcx>, tcx: TyCtxt<'a, 'gcx, 'tcx>)
                         -> Result<Self, (Self, Vec<(Place<'tcx>, MoveError<'tcx>)>)> {
         builder::gather_moves(mir, tcx)
     }
index d2c86d36238e1eeb76358dfe8e9cb0cd32f71a69..69df36348a69e6ffbe47801b1d71cabda1f14a0f 100644 (file)
@@ -1,5 +1,5 @@
 use syntax::ast;
-use rustc::ty::{self, Ty, TyCtxt, ParamEnv};
+use rustc::ty::{self, Ty, TyCtxt, ParamEnv, layout::Size};
 use syntax_pos::symbol::Symbol;
 use rustc::mir::interpret::{ConstValue, Scalar};
 
         trace!("trunc {} with size {} and shift {}", n, width.bits(), 128 - width.bits());
         let result = truncate(n, width);
         trace!("trunc result: {}", result);
-        Ok(ConstValue::Scalar(Scalar::Bits {
-            bits: result,
-            size: width.bytes() as u8,
-        }))
+        Ok(ConstValue::Scalar(Scalar::from_uint(result, width)))
     };
 
     use rustc::mir::interpret::*;
             let id = tcx.allocate_bytes(data);
             ConstValue::Scalar(Scalar::Ptr(id.into()))
         },
-        LitKind::Byte(n) => ConstValue::Scalar(Scalar::Bits {
-            bits: n as u128,
-            size: 1,
-        }),
+        LitKind::Byte(n) => ConstValue::Scalar(Scalar::from_uint(n, Size::from_bytes(1))),
         LitKind::Int(n, _) if neg => {
             let n = n as i128;
             let n = n.overflowing_neg().0;
@@ -84,7 +78,7 @@ fn parse_float<'tcx>(
     let num = num.as_str();
     use rustc_apfloat::ieee::{Single, Double};
     use rustc_apfloat::Float;
-    let (bits, size) = match fty {
+    let (data, size) = match fty {
         ast::FloatTy::F32 => {
             num.parse::<f32>().map_err(|_| ())?;
             let mut f = num.parse::<Single>().unwrap_or_else(|e| {
@@ -107,5 +101,5 @@ fn parse_float<'tcx>(
         }
     };
 
-    Ok(ConstValue::Scalar(Scalar::Bits { bits, size }))
+    Ok(ConstValue::Scalar(Scalar::from_uint(data, Size::from_bytes(size))))
 }
index 9798d7e8a16ddb81e379d93a28046bcb6f453447..80f64e85f9cf9201c11937dd66bbcfc24a8afaeb 100644 (file)
@@ -44,7 +44,7 @@ pub struct Cx<'a, 'gcx: 'a + 'tcx, 'tcx: 'a> {
     /// Whether this constant/function needs overflow checks.
     check_overflow: bool,
 
-    /// See field with the same name on `Mir`.
+    /// See field with the same name on `mir::Body`.
     control_flow_destroyed: Vec<(Span, String)>,
 }
 
index 2512525b4bb7e56ffff5caf4384f65870625d77d..76b11ac2fe6463a4515782d743e1a2b30dc018ee 100644 (file)
@@ -6,7 +6,7 @@
 
 use rustc_apfloat::ieee::{Single, Double};
 use rustc::mir::interpret::{
-    Scalar, EvalResult, Pointer, PointerArithmetic, InterpError, truncate
+    Scalar, EvalResult, Pointer, PointerArithmetic, InterpError,
 };
 use rustc::mir::CastKind;
 use rustc_apfloat::Float;
@@ -135,29 +135,13 @@ pub(super) fn cast_scalar(
         use rustc::ty::TyKind::*;
         trace!("Casting {:?}: {:?} to {:?}", val, src_layout.ty, dest_layout.ty);
 
-        match val {
-            Scalar::Ptr(ptr) => self.cast_from_ptr(ptr, dest_layout.ty),
-            Scalar::Bits { bits, size } => {
-                debug_assert_eq!(size as u64, src_layout.size.bytes());
-                debug_assert_eq!(truncate(bits, Size::from_bytes(size.into())), bits,
-                    "Unexpected value of size {} before casting", size);
-
-                let res = match src_layout.ty.sty {
-                    Float(fty) => self.cast_from_float(bits, fty, dest_layout.ty)?,
-                    _ => self.cast_from_int(bits, src_layout, dest_layout)?,
-                };
-
-                // Sanity check
-                match res {
-                    Scalar::Ptr(_) => bug!("Fabricated a ptr value from an int...?"),
-                    Scalar::Bits { bits, size } => {
-                        debug_assert_eq!(size as u64, dest_layout.size.bytes());
-                        debug_assert_eq!(truncate(bits, Size::from_bytes(size.into())), bits,
-                            "Unexpected value of size {} after casting", size);
-                    }
+        match val.to_bits_or_ptr(src_layout.size, self) {
+            Err(ptr) => self.cast_from_ptr(ptr, dest_layout.ty),
+            Ok(data) => {
+                match src_layout.ty.sty {
+                    Float(fty) => self.cast_from_float(data, fty, dest_layout.ty),
+                    _ => self.cast_from_int(data, src_layout, dest_layout),
                 }
-                // Done
-                Ok(res)
             }
         }
     }
@@ -177,7 +161,7 @@ fn cast_from_int(
         trace!("cast_from_int: {}, {}, {}", v, src_layout.ty, dest_layout.ty);
         use rustc::ty::TyKind::*;
         match dest_layout.ty.sty {
-            Int(_) | Uint(_) => {
+            Int(_) | Uint(_) | RawPtr(_) => {
                 let v = self.truncate(v, dest_layout);
                 Ok(Scalar::from_uint(v, dest_layout.size))
             }
@@ -205,15 +189,6 @@ fn cast_from_int(
                 Ok(Scalar::from_uint(v, Size::from_bytes(4)))
             },
 
-            // No alignment check needed for raw pointers.
-            // But we have to truncate to target ptr size.
-            RawPtr(_) => {
-                Ok(Scalar::from_uint(
-                    self.truncate_to_ptr(v).0,
-                    self.pointer_size(),
-                ))
-            },
-
             // Casts to bool are not permitted by rustc, no need to handle them here.
             _ => err!(Unimplemented(format!("int to {:?} cast", dest_layout.ty))),
         }
index 2f89740876db10b86e577e65ef8dd082631d08c9..d3cbd2bcc03a52e0cd688805be5ff89862494b08 100644 (file)
@@ -53,7 +53,7 @@ pub struct Frame<'mir, 'tcx: 'mir, Tag=(), Extra=()> {
     // Function and callsite information
     ////////////////////////////////////////////////////////////////////////////////
     /// The MIR for the function called on this frame.
-    pub mir: &'mir mir::Mir<'tcx>,
+    pub mir: &'mir mir::Body<'tcx>,
 
     /// The def_id and substs of the current function.
     pub instance: ty::Instance<'tcx>,
@@ -244,7 +244,7 @@ pub fn frame_mut(&mut self) -> &mut Frame<'mir, 'tcx, M::PointerTag, M::FrameExt
     }
 
     #[inline(always)]
-    pub(super) fn mir(&self) -> &'mir mir::Mir<'tcx> {
+    pub(super) fn mir(&self) -> &'mir mir::Body<'tcx> {
         self.frame().mir
     }
 
@@ -294,7 +294,7 @@ pub fn type_is_freeze(&self, ty: Ty<'tcx>) -> bool {
     pub fn load_mir(
         &self,
         instance: ty::InstanceDef<'tcx>,
-    ) -> EvalResult<'tcx, &'tcx mir::Mir<'tcx>> {
+    ) -> EvalResult<'tcx, &'tcx mir::Body<'tcx>> {
         // do not continue if typeck errors occurred (can only occur in local crate)
         let did = instance.def_id();
         if did.is_local()
@@ -472,7 +472,7 @@ pub fn push_stack_frame(
         &mut self,
         instance: ty::Instance<'tcx>,
         span: source_map::Span,
-        mir: &'mir mir::Mir<'tcx>,
+        mir: &'mir mir::Body<'tcx>,
         return_place: Option<PlaceTy<'tcx, M::PointerTag>>,
         return_to_block: StackPopCleanup,
     ) -> EvalResult<'tcx> {
index 288ffbf3cd616f57839f8858a17fa1cea76c6674..873c2d2ec6088b1e01e94947b7770e3b6cdecb55 100644 (file)
@@ -117,7 +117,7 @@ fn find_fn(
         args: &[OpTy<'tcx, Self::PointerTag>],
         dest: Option<PlaceTy<'tcx, Self::PointerTag>>,
         ret: Option<mir::BasicBlock>,
-    ) -> EvalResult<'tcx, Option<&'mir mir::Mir<'tcx>>>;
+    ) -> EvalResult<'tcx, Option<&'mir mir::Body<'tcx>>>;
 
     /// Directly process an intrinsic without pushing a stack frame.
     /// If this returns successfully, the engine will take care of jumping to the next block.
index 0cd258825acb8f14a5a47661c288bab45ee7423d..65a3b04c8b152f1c26eb0762e92eb7dd58a61152 100644 (file)
@@ -12,7 +12,6 @@
 
 use rustc::ty::{self, Instance, ParamEnv, query::TyCtxtAt};
 use rustc::ty::layout::{Align, TargetDataLayout, Size, HasDataLayout};
-pub use rustc::mir::interpret::{truncate, write_target_uint, read_target_uint};
 use rustc_data_structures::fx::{FxHashSet, FxHashMap};
 
 use syntax::ast::Mutability;
@@ -248,23 +247,21 @@ pub fn check_align(
         required_align: Align
     ) -> EvalResult<'tcx> {
         // Check non-NULL/Undef, extract offset
-        let (offset, alloc_align) = match ptr {
-            Scalar::Ptr(ptr) => {
+        let (offset, alloc_align) = match ptr.to_bits_or_ptr(self.pointer_size(), self) {
+            Err(ptr) => {
                 // check this is not NULL -- which we can ensure only if this is in-bounds
                 // of some (potentially dead) allocation.
                 let align = self.check_bounds_ptr(ptr, InboundsCheck::MaybeDead,
                                                   CheckInAllocMsg::NullPointerTest)?;
                 (ptr.offset.bytes(), align)
             }
-            Scalar::Bits { bits, size } => {
-                assert_eq!(size as u64, self.pointer_size().bytes());
-                assert!(bits < (1u128 << self.pointer_size().bits()));
+            Ok(data) => {
                 // check this is not NULL
-                if bits == 0 {
+                if data == 0 {
                     return err!(InvalidNullPointerUsage);
                 }
                 // the "base address" is 0 and hence always aligned
-                (bits as u64, required_align)
+                (data as u64, required_align)
             }
         };
         // Check alignment
index c03b35c40c6db2e0a3f1063cc1ddacf2e54b4f9f..289379f34a9a3bb8771d4dfe0253f7e97689fde4 100644 (file)
@@ -641,19 +641,20 @@ pub fn read_discriminant(
             } => {
                 let variants_start = niche_variants.start().as_u32() as u128;
                 let variants_end = niche_variants.end().as_u32() as u128;
-                match raw_discr {
-                    ScalarMaybeUndef::Scalar(Scalar::Ptr(ptr)) => {
+                let raw_discr = raw_discr.not_undef()
+                    .map_err(|_| InterpError::InvalidDiscriminant(ScalarMaybeUndef::Undef))?;
+                match raw_discr.to_bits_or_ptr(discr_val.layout.size, self) {
+                    Err(ptr) => {
                         // The niche must be just 0 (which an inbounds pointer value never is)
                         let ptr_valid = niche_start == 0 && variants_start == variants_end &&
                             self.memory.check_bounds_ptr(ptr, InboundsCheck::MaybeDead,
                                                          CheckInAllocMsg::NullPointerTest).is_ok();
                         if !ptr_valid {
-                            return err!(InvalidDiscriminant(raw_discr.erase_tag()));
+                            return err!(InvalidDiscriminant(raw_discr.erase_tag().into()));
                         }
                         (dataful_variant.as_u32() as u128, dataful_variant)
                     },
-                    ScalarMaybeUndef::Scalar(Scalar::Bits { bits: raw_discr, size }) => {
-                        assert_eq!(size as u64, discr_val.layout.size.bytes());
+                    Ok(raw_discr) => {
                         let adjusted_discr = raw_discr.wrapping_sub(niche_start)
                             .wrapping_add(variants_start);
                         if variants_start <= adjusted_discr && adjusted_discr <= variants_end {
@@ -668,8 +669,6 @@ pub fn read_discriminant(
                             (dataful_variant.as_u32() as u128, dataful_variant)
                         }
                     },
-                    ScalarMaybeUndef::Undef =>
-                        return err!(InvalidDiscriminant(ScalarMaybeUndef::Undef)),
                 }
             }
         })
index 57d5ab71ecafd3922a6dda794f2bb5505ff87454..0ae4e90b7c24d57afb72319874960c5893f79c6e 100644 (file)
@@ -686,7 +686,7 @@ fn write_immediate_no_validate(
                 Immediate::Scalar(ScalarMaybeUndef::Scalar(Scalar::Ptr(_))) =>
                     assert_eq!(self.pointer_size(), dest.layout.size,
                         "Size mismatch when writing pointer"),
-                Immediate::Scalar(ScalarMaybeUndef::Scalar(Scalar::Bits { size, .. })) =>
+                Immediate::Scalar(ScalarMaybeUndef::Scalar(Scalar::Raw { size, .. })) =>
                     assert_eq!(Size::from_bytes(size.into()), dest.layout.size,
                         "Size mismatch when writing bits"),
                 Immediate::Scalar(ScalarMaybeUndef::Undef) => {}, // undef can have any size
index 83bd3666b3d3b3d24d9fe3350879dae133391b17..c0bc7ce6b39ad09af7c5d7e790fef386c4f68a78 100644 (file)
@@ -186,9 +186,9 @@ impl<'a, Ctx> Snapshot<'a, Ctx> for Scalar
     fn snapshot(&self, ctx: &'a Ctx) -> Self::Item {
         match self {
             Scalar::Ptr(p) => Scalar::Ptr(p.snapshot(ctx)),
-            Scalar::Bits{ size, bits } => Scalar::Bits {
+            Scalar::Raw{ size, data } => Scalar::Raw {
+                data: *data,
                 size: *size,
-                bits: *bits,
             },
         }
     }
index f9401d9763506d67b36579ce89eab5cc34367ae5..072c6f4fd90e8e9641bcf2264246bc025050f2ab 100644 (file)
@@ -480,8 +480,8 @@ fn visit_scalar(
                 wrapping_range_format(&layout.valid_range, max_hi),
             )
         );
-        let bits = match value {
-            Scalar::Ptr(ptr) => {
+        let bits = match value.to_bits_or_ptr(op.layout.size, self.ecx) {
+            Err(ptr) => {
                 if lo == 1 && hi == max_hi {
                     // only NULL is not allowed.
                     // We can call `check_align` to check non-NULL-ness, but have to also look
@@ -509,10 +509,8 @@ fn visit_scalar(
                     );
                 }
             }
-            Scalar::Bits { bits, size } => {
-                assert_eq!(size as u64, op.layout.size.bytes());
-                bits
-            }
+            Ok(data) =>
+                data
         };
         // Now compare. This is slightly subtle because this is a special "wrap-around" range.
         if wrapping_range_contains(&layout.valid_range, bits) {
index 51ceb2a01c3a428d48593209c0fcf8af3a7e5bad..cbfc89934718600c9337c4b40e0b81fab9bc4a6b 100644 (file)
@@ -3,12 +3,12 @@
 use rustc::hir::intravisit::FnKind;
 use rustc::hir::map::blocks::FnLikeNode;
 use rustc::lint::builtin::UNCONDITIONAL_RECURSION;
-use rustc::mir::{self, Mir, TerminatorKind};
+use rustc::mir::{self, Body, TerminatorKind};
 use rustc::ty::{self, AssocItem, AssocItemContainer, Instance, TyCtxt};
 use rustc::ty::subst::InternalSubsts;
 
 pub fn check(tcx: TyCtxt<'a, 'tcx, 'tcx>,
-             mir: &Mir<'tcx>,
+             mir: &Body<'tcx>,
              def_id: DefId) {
     let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
 
@@ -19,7 +19,7 @@ pub fn check(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 
 fn check_fn_for_unconditional_recursion(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                                         fn_kind: FnKind<'_>,
-                                        mir: &Mir<'tcx>,
+                                        mir: &Body<'tcx>,
                                         def_id: DefId) {
     if let FnKind::Closure(_) = fn_kind {
         // closures can't recur, so they don't matter.
index b90db7646d4929f1be224ccc83f112cfefbac787..c1131336f3636a08606c48c619eba604eaec4464 100644 (file)
@@ -517,7 +517,7 @@ fn check_type_length_limit<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 
 struct MirNeighborCollector<'a, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &'a mir::Mir<'tcx>,
+    mir: &'a mir::Body<'tcx>,
     output: &'a mut Vec<MonoItem<'tcx>>,
     param_substs: SubstsRef<'tcx>,
 }
@@ -1218,7 +1218,7 @@ fn collect_neighbours<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
         mir: &mir,
         output,
         param_substs: instance.substs,
-    }.visit_mir(&mir);
+    }.visit_body(&mir);
     let param_env = ty::ParamEnv::reveal_all();
     for i in 0..mir.promoted.len() {
         use rustc_data_structures::indexed_vec::Idx;
index 12a1659e043c6b641acc90eb67faea6eee7b73f6..087f8779b6916fb896a82e47525dba45bf040694 100644 (file)
@@ -28,7 +28,7 @@ pub fn provide(providers: &mut Providers<'_>) {
 
 fn make_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                        instance: ty::InstanceDef<'tcx>)
-                       -> &'tcx Mir<'tcx>
+                       -> &'tcx Body<'tcx>
 {
     debug!("make_shim({:?})", instance);
 
@@ -169,7 +169,7 @@ fn local_decls_for_sig<'tcx>(sig: &ty::FnSig<'tcx>, span: Span)
 fn build_drop_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                              def_id: DefId,
                              ty: Option<Ty<'tcx>>)
-                             -> Mir<'tcx>
+                             -> Body<'tcx>
 {
     debug!("build_drop_shim(def_id={:?}, ty={:?})", def_id, ty);
 
@@ -202,7 +202,7 @@ fn build_drop_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
     block(&mut blocks, TerminatorKind::Goto { target: return_block });
     block(&mut blocks, TerminatorKind::Return);
 
-    let mut mir = Mir::new(
+    let mut mir = Body::new(
         blocks,
         IndexVec::from_elem_n(
             SourceScopeData { span: span, parent_scope: None }, 1
@@ -256,7 +256,7 @@ fn build_drop_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 }
 
 pub struct DropShimElaborator<'a, 'tcx: 'a> {
-    pub mir: &'a Mir<'tcx>,
+    pub mir: &'a Body<'tcx>,
     pub patch: MirPatch<'tcx>,
     pub tcx: TyCtxt<'a, 'tcx, 'tcx>,
     pub param_env: ty::ParamEnv<'tcx>,
@@ -272,7 +272,7 @@ impl<'a, 'tcx> DropElaborator<'a, 'tcx> for DropShimElaborator<'a, 'tcx> {
     type Path = ();
 
     fn patch(&mut self) -> &mut MirPatch<'tcx> { &mut self.patch }
-    fn mir(&self) -> &'a Mir<'tcx> { self.mir }
+    fn mir(&self) -> &'a Body<'tcx> { self.mir }
     fn tcx(&self) -> TyCtxt<'a, 'tcx, 'tcx> { self.tcx }
     fn param_env(&self) -> ty::ParamEnv<'tcx> { self.param_env }
 
@@ -309,7 +309,7 @@ fn array_subpath(&self, _path: Self::Path, _index: u32, _size: u32) -> Option<Se
 fn build_clone_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                               def_id: DefId,
                               self_ty: Ty<'tcx>)
-                              -> Mir<'tcx>
+                              -> Body<'tcx>
 {
     debug!("build_clone_shim(def_id={:?})", def_id);
 
@@ -371,8 +371,8 @@ fn new(tcx: TyCtxt<'a, 'tcx, 'tcx>,
         }
     }
 
-    fn into_mir(self) -> Mir<'tcx> {
-        Mir::new(
+    fn into_mir(self) -> Body<'tcx> {
+        Body::new(
             self.blocks,
             IndexVec::from_elem_n(
                 SourceScopeData { span: self.span, parent_scope: None }, 1
@@ -696,7 +696,7 @@ fn build_call_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                              rcvr_adjustment: Adjustment,
                              call_kind: CallKind,
                              untuple_args: Option<&[Ty<'tcx>]>)
-                             -> Mir<'tcx>
+                             -> Body<'tcx>
 {
     debug!("build_call_shim(def_id={:?}, rcvr_adjustment={:?}, \
             call_kind={:?}, untuple_args={:?})",
@@ -821,7 +821,7 @@ fn build_call_shim<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
         block(&mut blocks, vec![], TerminatorKind::Resume, true);
     }
 
-    let mut mir = Mir::new(
+    let mut mir = Body::new(
         blocks,
         IndexVec::from_elem_n(
             SourceScopeData { span: span, parent_scope: None }, 1
@@ -846,7 +846,7 @@ pub fn build_adt_ctor<'a, 'gcx, 'tcx>(infcx: &infer::InferCtxt<'a, 'gcx, 'tcx>,
                                       ctor_id: hir::HirId,
                                       fields: &[hir::StructField],
                                       span: Span)
-                                      -> Mir<'tcx>
+                                      -> Body<'tcx>
 {
     let tcx = infcx.tcx;
     let gcx = tcx.global_tcx();
@@ -900,7 +900,7 @@ pub fn build_adt_ctor<'a, 'gcx, 'tcx>(infcx: &infer::InferCtxt<'a, 'gcx, 'tcx>,
         is_cleanup: false
     };
 
-    Mir::new(
+    Body::new(
         IndexVec::from_elem_n(start_block, 1),
         IndexVec::from_elem_n(
             SourceScopeData { span: span, parent_scope: None }, 1
index 88042d64e96b7271b3600d884dcf73165bb6667b..712e9b1fe25059021e4d0275d73bc2dd42d503ac 100644 (file)
@@ -34,13 +34,13 @@ impl MirPass for AddCallGuards {
     fn run_pass<'a, 'tcx>(&self,
                           _tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         self.add_call_guards(mir);
     }
 }
 
 impl AddCallGuards {
-    pub fn add_call_guards(&self, mir: &mut Mir<'_>) {
+    pub fn add_call_guards(&self, mir: &mut Body<'_>) {
         let pred_count: IndexVec<_, _> =
             mir.predecessors().iter().map(|ps| ps.len()).collect();
 
index b6436ec70eef24ff64f77a32594b07671fbf0313..f7a4bf759545cf9903cd22997e2d42226839ccea 100644 (file)
@@ -43,7 +43,7 @@ impl MirPass for AddMovesForPackedDrops {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>)
+                          mir: &mut Body<'tcx>)
     {
         debug!("add_moves_for_packed_drops({:?} @ {:?})", src, mir.span);
         add_moves_for_packed_drops(tcx, mir, src.def_id());
@@ -52,7 +52,7 @@ fn run_pass<'a, 'tcx>(&self,
 
 pub fn add_moves_for_packed_drops<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &mut Mir<'tcx>,
+    mir: &mut Body<'tcx>,
     def_id: DefId)
 {
     let patch = add_moves_for_packed_drops_patch(tcx, mir, def_id);
@@ -61,7 +61,7 @@ pub fn add_moves_for_packed_drops<'a, 'tcx>(
 
 fn add_moves_for_packed_drops_patch<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     def_id: DefId)
     -> MirPatch<'tcx>
 {
@@ -92,7 +92,7 @@ fn add_moves_for_packed_drops_patch<'a, 'tcx>(
 
 fn add_move_for_packed_drop<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     patch: &mut MirPatch<'tcx>,
     terminator: &Terminator<'tcx>,
     loc: Location,
index 32c9953ee9e08be29bf2147e4928a5fe9aed6013..23319f7055183e2ceb3360705d560fa00a87c3b9 100644 (file)
@@ -77,7 +77,7 @@ impl MirPass for AddRetag {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>)
+                          mir: &mut Body<'tcx>)
     {
         if !tcx.sess.opts.debugging_opts.mir_emit_retag {
             return;
index 394d1f06029cb6459f2e579b50d770d9dddbd32a..8ec8a8fa12eeced2231e51515b8268f3e83397fc 100644 (file)
@@ -19,7 +19,7 @@
 use crate::util;
 
 pub struct UnsafetyChecker<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     const_context: bool,
     min_const_fn: bool,
     source_scope_local_data: &'a IndexVec<SourceScope, SourceScopeLocalData>,
@@ -36,7 +36,7 @@ impl<'a, 'gcx, 'tcx> UnsafetyChecker<'a, 'tcx> {
     fn new(
         const_context: bool,
         min_const_fn: bool,
-        mir: &'a Mir<'tcx>,
+        mir: &'a Body<'tcx>,
         source_scope_local_data: &'a IndexVec<SourceScope, SourceScopeLocalData>,
         tcx: TyCtxt<'a, 'tcx, 'tcx>,
         param_env: ty::ParamEnv<'tcx>,
@@ -538,7 +538,7 @@ fn unsafety_check_result<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId)
     let mut checker = UnsafetyChecker::new(
         const_context, min_const_fn,
         mir, source_scope_local_data, tcx, param_env);
-    checker.visit_mir(mir);
+    checker.visit_body(mir);
 
     check_unused_unsafe(tcx, def_id, &checker.used_unsafe, &mut checker.inherited_blocks);
     UnsafetyCheckResult {
index 64fd0b1365690a1864546f8224983806bf246fe9..63a1b059d90178ed14e8f63a2d49cae988c30c9d 100644 (file)
@@ -16,7 +16,7 @@
 //! [`FakeRead`]: rustc::mir::StatementKind::FakeRead
 //! [`Nop`]: rustc::mir::StatementKind::Nop
 
-use rustc::mir::{BorrowKind, Rvalue, Location, Mir};
+use rustc::mir::{BorrowKind, Rvalue, Location, Body};
 use rustc::mir::{Statement, StatementKind};
 use rustc::mir::visit::MutVisitor;
 use rustc::ty::TyCtxt;
@@ -30,9 +30,9 @@ impl MirPass for CleanupNonCodegenStatements {
     fn run_pass<'a, 'tcx>(&self,
                           _tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let mut delete = DeleteNonCodegenStatements;
-        delete.visit_mir(mir);
+        delete.visit_body(mir);
     }
 }
 
index 11022be097cfd9e68799ee720d02d1007fc575e8..728ea41a9d8e9534d31535061a33e34266a59df6 100644 (file)
@@ -3,7 +3,7 @@
 
 use rustc::hir::def::DefKind;
 use rustc::mir::{
-    AggregateKind, Constant, Location, Place, PlaceBase, Mir, Operand, Rvalue, Local,
+    AggregateKind, Constant, Location, Place, PlaceBase, Body, Operand, Rvalue, Local,
     NullOp, UnOp, StatementKind, Statement, LocalKind, Static, StaticKind,
     TerminatorKind, Terminator,  ClearCrossCrate, SourceInfo, BinOp, ProjectionElem,
     SourceScope, SourceScopeLocalData, LocalDecl, Promoted,
@@ -33,7 +33,7 @@ impl MirPass for ConstProp {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         // will be evaluated by miri and produce its errors there
         if source.promoted.is_some() {
             return;
@@ -63,7 +63,7 @@ fn run_pass<'a, 'tcx>(&self,
         // That would require an uniform one-def no-mutation analysis
         // and RPO (or recursing when needing the value of a local).
         let mut optimization_finder = ConstPropagator::new(mir, tcx, source);
-        optimization_finder.visit_mir(mir);
+        optimization_finder.visit_body(mir);
 
         // put back the data we stole from `mir`
         std::mem::replace(
@@ -91,7 +91,7 @@ struct ConstPropagator<'a, 'mir, 'tcx:'a+'mir> {
     param_env: ParamEnv<'tcx>,
     source_scope_local_data: ClearCrossCrate<IndexVec<SourceScope, SourceScopeLocalData>>,
     local_decls: IndexVec<Local, LocalDecl<'tcx>>,
-    promoted: IndexVec<Promoted, Mir<'tcx>>,
+    promoted: IndexVec<Promoted, Body<'tcx>>,
 }
 
 impl<'a, 'b, 'tcx> LayoutOf for ConstPropagator<'a, 'b, 'tcx> {
@@ -119,7 +119,7 @@ fn tcx<'c>(&'c self) -> TyCtxt<'c, 'tcx, 'tcx> {
 
 impl<'a, 'mir, 'tcx> ConstPropagator<'a, 'mir, 'tcx> {
     fn new(
-        mir: &mut Mir<'tcx>,
+        mir: &mut Body<'tcx>,
         tcx: TyCtxt<'a, 'tcx, 'tcx>,
         source: MirSource<'tcx>,
     ) -> ConstPropagator<'a, 'mir, 'tcx> {
@@ -143,7 +143,7 @@ fn new(
             can_const_prop,
             places: IndexVec::from_elem(None, &mir.local_decls),
             source_scope_local_data,
-            //FIXME(wesleywiser) we can't steal this because `Visitor::super_visit_mir()` needs it
+            //FIXME(wesleywiser) we can't steal this because `Visitor::super_visit_body()` needs it
             local_decls: mir.local_decls.clone(),
             promoted,
         }
@@ -382,10 +382,7 @@ fn const_prop(
                 type_size_of(self.tcx, self.param_env, ty).and_then(|n| Some(
                     ImmTy {
                         imm: Immediate::Scalar(
-                            Scalar::Bits {
-                                bits: n as u128,
-                                size: self.tcx.data_layout.pointer_size.bytes() as u8,
-                            }.into()
+                            Scalar::from_uint(n, self.tcx.data_layout.pointer_size).into()
                         ),
                         layout: self.tcx.layout_of(self.param_env.and(self.tcx.types.usize)).ok()?,
                     }.into()
@@ -572,7 +569,7 @@ struct CanConstProp {
 
 impl CanConstProp {
     /// returns true if `local` can be propagated
-    fn check(mir: &Mir<'_>) -> IndexVec<Local, bool> {
+    fn check(mir: &Body<'_>) -> IndexVec<Local, bool> {
         let mut cpv = CanConstProp {
             can_const_prop: IndexVec::from_elem(true, &mir.local_decls),
             found_assignment: IndexVec::from_elem(false, &mir.local_decls),
@@ -589,7 +586,7 @@ fn check(mir: &Mir<'_>) -> IndexVec<Local, bool> {
                 trace!("local {:?} can't be propagated because it's not a temporary", local);
             }
         }
-        cpv.visit_mir(mir);
+        cpv.visit_body(mir);
         cpv.can_const_prop
     }
 }
@@ -713,18 +710,18 @@ fn visit_terminator(
                                     .eval_operand(len, source_info)
                                     .expect("len must be const");
                                 let len = match self.ecx.read_scalar(len) {
-                                    Ok(ScalarMaybeUndef::Scalar(Scalar::Bits {
-                                        bits, ..
-                                    })) => bits,
+                                    Ok(ScalarMaybeUndef::Scalar(Scalar::Raw {
+                                        data, ..
+                                    })) => data,
                                     other => bug!("const len not primitive: {:?}", other),
                                 };
                                 let index = self
                                     .eval_operand(index, source_info)
                                     .expect("index must be const");
                                 let index = match self.ecx.read_scalar(index) {
-                                    Ok(ScalarMaybeUndef::Scalar(Scalar::Bits {
-                                        bits, ..
-                                    })) => bits,
+                                    Ok(ScalarMaybeUndef::Scalar(Scalar::Raw {
+                                        data, ..
+                                    })) => data,
                                     other => bug!("const index not primitive: {:?}", other),
                                 };
                                 format!(
index dfe2e991ba97bf9e118ef5029c856d3bcea7e62a..c48d2d295711a495f59d94713a15566a64cfa755 100644 (file)
@@ -20,7 +20,7 @@
 //! future.
 
 use rustc::mir::{
-    Constant, Local, LocalKind, Location, Place, PlaceBase, Mir, Operand, Rvalue, StatementKind
+    Constant, Local, LocalKind, Location, Place, PlaceBase, Body, Operand, Rvalue, StatementKind
 };
 use rustc::mir::visit::MutVisitor;
 use rustc::ty::TyCtxt;
@@ -33,7 +33,7 @@ impl MirPass for CopyPropagation {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         // We only run when the MIR optimization level is > 1.
         // This avoids a slow pass, and messing up debug info.
         if tcx.sess.opts.debugging_opts.mir_opt_level <= 1 {
@@ -135,7 +135,7 @@ fn run_pass<'a, 'tcx>(&self,
 }
 
 fn eliminate_self_assignments(
-    mir: &mut Mir<'_>,
+    mir: &mut Body<'_>,
     def_use_analysis: &DefUseAnalysis,
 ) -> bool {
     let mut changed = false;
@@ -177,7 +177,7 @@ enum Action<'tcx> {
 }
 
 impl<'tcx> Action<'tcx> {
-    fn local_copy(mir: &Mir<'tcx>, def_use_analysis: &DefUseAnalysis, src_place: &Place<'tcx>)
+    fn local_copy(mir: &Body<'tcx>, def_use_analysis: &DefUseAnalysis, src_place: &Place<'tcx>)
                   -> Option<Action<'tcx>> {
         // The source must be a local.
         let src_local = if let Place::Base(PlaceBase::Local(local)) = *src_place {
@@ -232,7 +232,7 @@ fn constant(src_constant: &Constant<'tcx>) -> Option<Action<'tcx>> {
     }
 
     fn perform(self,
-               mir: &mut Mir<'tcx>,
+               mir: &mut Body<'tcx>,
                def_use_analysis: &DefUseAnalysis,
                dest_local: Local,
                location: Location)
index 9215356daa484f405a299e73bda2a635c8e58276..7da37f956cedd2fc23c0468acd17caaaac5514c3 100644 (file)
@@ -10,7 +10,7 @@ impl MirPass for Deaggregator {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let (basic_blocks, local_decls) = mir.basic_blocks_and_local_decls_mut();
         let local_decls = &*local_decls;
         for bb in basic_blocks {
index 81e48fe2dbe3bb33d9495bef7ed428000f36e934..ebb65094a306df2681a4cfdef5dbb4e24fd29eff 100644 (file)
@@ -5,7 +5,7 @@
 use std::fs::File;
 use std::io;
 
-use rustc::mir::Mir;
+use rustc::mir::Body;
 use rustc::session::config::{OutputFilenames, OutputType};
 use rustc::ty::TyCtxt;
 use crate::transform::{MirPass, MirSource};
@@ -21,7 +21,7 @@ fn name<'a>(&'a self) -> Cow<'a, str> {
     fn run_pass<'a, 'tcx>(&self,
                           _tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _source: MirSource<'tcx>,
-                          _mir: &mut Mir<'tcx>)
+                          _mir: &mut Body<'tcx>)
     {
     }
 }
@@ -42,7 +42,7 @@ pub fn on_mir_pass<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                              pass_num: &dyn fmt::Display,
                              pass_name: &str,
                              source: MirSource<'tcx>,
-                             mir: &Mir<'tcx>,
+                             mir: &Body<'tcx>,
                              is_after: bool) {
     if mir_util::dump_enabled(tcx, pass_name, source) {
         mir_util::dump_mir(tcx,
index 6320cb442481448da19a9385b22d3dbce41a3c78..c833af29c36f0ed1427be0ac03b7830649d52ee1 100644 (file)
@@ -24,7 +24,7 @@ impl MirPass for ElaborateDrops {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>)
+                          mir: &mut Body<'tcx>)
     {
         debug!("elaborate_drops({:?} @ {:?})", src, mir.span);
 
@@ -79,7 +79,7 @@ fn run_pass<'a, 'tcx>(&self,
 /// that can't drop anything.
 fn find_dead_unwinds<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     def_id: hir::def_id::DefId,
     env: &MoveDataParamEnv<'tcx, 'tcx>)
     -> BitSet<BasicBlock>
@@ -143,7 +143,7 @@ struct InitializationData {
 impl InitializationData {
     fn apply_location<'a,'tcx>(&mut self,
                                tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                               mir: &Mir<'tcx>,
+                               mir: &Body<'tcx>,
                                env: &MoveDataParamEnv<'tcx, 'tcx>,
                                loc: Location)
     {
@@ -186,7 +186,7 @@ fn patch(&mut self) -> &mut MirPatch<'tcx> {
         &mut self.ctxt.patch
     }
 
-    fn mir(&self) -> &'a Mir<'tcx> {
+    fn mir(&self) -> &'a Body<'tcx> {
         self.ctxt.mir
     }
 
@@ -291,7 +291,7 @@ fn get_drop_flag(&mut self, path: Self::Path) -> Option<Operand<'tcx>> {
 
 struct ElaborateDropsCtxt<'a, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     env: &'a MoveDataParamEnv<'tcx, 'tcx>,
     flow_inits: DataflowResults<'tcx, MaybeInitializedPlaces<'a, 'tcx, 'tcx>>,
     flow_uninits:  DataflowResults<'tcx, MaybeUninitializedPlaces<'a, 'tcx, 'tcx>>,
index 7c2ff94b75d86f86d8feb74fa0765bc1bb59e758..ffc5bba6d608660c4b10e4f6df4f448a314ec729 100644 (file)
@@ -53,7 +53,7 @@ impl MirPass for EraseRegions {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
-        EraseRegionsVisitor::new(tcx).visit_mir(mir);
+                          mir: &mut Body<'tcx>) {
+        EraseRegionsVisitor::new(tcx).visit_body(mir);
     }
 }
index ab2f2933a969e62519c2e65714d10a0db0b7f6e9..f36ede4e8d9cdcce31ae31210a718efafd986b2a 100644 (file)
@@ -210,7 +210,7 @@ fn set_discr(&self, state_disc: VariantIdx, source_info: SourceInfo) -> Statemen
     }
 
     // Create a statement which reads the discriminant into a temporary
-    fn get_discr(&self, mir: &mut Mir<'tcx>) -> (Statement<'tcx>, Place<'tcx>) {
+    fn get_discr(&self, mir: &mut Body<'tcx>) -> (Statement<'tcx>, Place<'tcx>) {
         let temp_decl = LocalDecl::new_internal(self.tcx.types.isize, mir.span);
         let local_decls_len = mir.local_decls.push(temp_decl);
         let temp = Place::Base(PlaceBase::Local(local_decls_len));
@@ -304,7 +304,7 @@ fn visit_basic_block_data(&mut self,
 fn make_generator_state_argument_indirect<'a, 'tcx>(
                 tcx: TyCtxt<'a, 'tcx, 'tcx>,
                 def_id: DefId,
-                mir: &mut Mir<'tcx>) {
+                mir: &mut Body<'tcx>) {
     let gen_ty = mir.local_decls.raw[1].ty;
 
     let region = ty::ReFree(ty::FreeRegion {
@@ -323,12 +323,12 @@ fn make_generator_state_argument_indirect<'a, 'tcx>(
     mir.local_decls.raw[1].ty = ref_gen_ty;
 
     // Add a deref to accesses of the generator state
-    DerefArgVisitor.visit_mir(mir);
+    DerefArgVisitor.visit_body(mir);
 }
 
 fn make_generator_state_argument_pinned<'a, 'tcx>(
                 tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                mir: &mut Mir<'tcx>) {
+                mir: &mut Body<'tcx>) {
     let ref_gen_ty = mir.local_decls.raw[1].ty;
 
     let pin_did = tcx.lang_items().pin_type().unwrap();
@@ -340,12 +340,12 @@ fn make_generator_state_argument_pinned<'a, 'tcx>(
     mir.local_decls.raw[1].ty = pin_ref_gen_ty;
 
     // Add the Pin field access to accesses of the generator state
-    PinArgVisitor { ref_gen_ty }.visit_mir(mir);
+    PinArgVisitor { ref_gen_ty }.visit_body(mir);
 }
 
 fn replace_result_variable<'tcx>(
     ret_ty: Ty<'tcx>,
-    mir: &mut Mir<'tcx>,
+    mir: &mut Body<'tcx>,
 ) -> Local {
     let source_info = source_info(mir);
     let new_ret = LocalDecl {
@@ -366,7 +366,7 @@ fn replace_result_variable<'tcx>(
     RenameLocalVisitor {
         from: RETURN_PLACE,
         to: new_ret_local,
-    }.visit_mir(mir);
+    }.visit_body(mir);
 
     new_ret_local
 }
@@ -387,7 +387,7 @@ fn visit_statement(&mut self,
 
 fn locals_live_across_suspend_points(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     source: MirSource<'tcx>,
     movable: bool,
 ) -> (
@@ -408,7 +408,7 @@ fn locals_live_across_suspend_points(
     // Find the MIR locals which do not use StorageLive/StorageDead statements.
     // The storage of these locals are always live.
     let mut ignored = StorageIgnored(BitSet::new_filled(mir.local_decls.len()));
-    ignored.visit_mir(mir);
+    ignored.visit_body(mir);
 
     // Calculate the MIR locals which have been previously
     // borrowed (even if they are still active).
@@ -503,7 +503,7 @@ fn compute_layout<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                             upvars: &Vec<Ty<'tcx>>,
                             interior: Ty<'tcx>,
                             movable: bool,
-                            mir: &mut Mir<'tcx>)
+                            mir: &mut Body<'tcx>)
     -> (FxHashMap<Local, (Ty<'tcx>, VariantIdx, usize)>,
         GeneratorLayout<'tcx>,
         FxHashMap<BasicBlock, liveness::LiveVarSet>)
@@ -576,7 +576,7 @@ fn compute_layout<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
     (remap, layout, storage_liveness)
 }
 
-fn insert_switch<'a, 'tcx>(mir: &mut Mir<'tcx>,
+fn insert_switch<'a, 'tcx>(mir: &mut Body<'tcx>,
                            cases: Vec<(usize, BasicBlock)>,
                            transform: &TransformVisitor<'a, 'tcx>,
                            default: TerminatorKind<'tcx>) {
@@ -608,7 +608,7 @@ fn insert_switch<'a, 'tcx>(mir: &mut Mir<'tcx>,
 
 fn elaborate_generator_drops<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                                        def_id: DefId,
-                                       mir: &mut Mir<'tcx>) {
+                                       mir: &mut Body<'tcx>) {
     use crate::util::elaborate_drops::{elaborate_drop, Unwind};
     use crate::util::patch::MirPatch;
     use crate::shim::DropShimElaborator;
@@ -663,8 +663,8 @@ fn create_generator_drop_shim<'a, 'tcx>(
                 def_id: DefId,
                 source: MirSource<'tcx>,
                 gen_ty: Ty<'tcx>,
-                mir: &Mir<'tcx>,
-                drop_clean: BasicBlock) -> Mir<'tcx> {
+                mir: &Body<'tcx>,
+                drop_clean: BasicBlock) -> Body<'tcx> {
     let mut mir = mir.clone();
 
     let source_info = source_info(&mir);
@@ -734,7 +734,7 @@ fn create_generator_drop_shim<'a, 'tcx>(
     mir
 }
 
-fn insert_term_block<'tcx>(mir: &mut Mir<'tcx>, kind: TerminatorKind<'tcx>) -> BasicBlock {
+fn insert_term_block<'tcx>(mir: &mut Body<'tcx>, kind: TerminatorKind<'tcx>) -> BasicBlock {
     let term_block = BasicBlock::new(mir.basic_blocks().len());
     let source_info = source_info(mir);
     mir.basic_blocks_mut().push(BasicBlockData {
@@ -749,7 +749,7 @@ fn insert_term_block<'tcx>(mir: &mut Mir<'tcx>, kind: TerminatorKind<'tcx>) -> B
 }
 
 fn insert_panic_block<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                                mir: &mut Mir<'tcx>,
+                                mir: &mut Body<'tcx>,
                                 message: AssertMessage<'tcx>) -> BasicBlock {
     let assert_block = BasicBlock::new(mir.basic_blocks().len());
     let term = TerminatorKind::Assert {
@@ -783,7 +783,7 @@ fn create_generator_resume_function<'a, 'tcx>(
         transform: TransformVisitor<'a, 'tcx>,
         def_id: DefId,
         source: MirSource<'tcx>,
-        mir: &mut Mir<'tcx>) {
+        mir: &mut Body<'tcx>) {
     // Poison the generator when it unwinds
     for block in mir.basic_blocks_mut() {
         let source_info = block.terminator().source_info;
@@ -821,14 +821,14 @@ fn create_generator_resume_function<'a, 'tcx>(
     dump_mir(tcx, None, "generator_resume", &0, source, mir, |_, _| Ok(()) );
 }
 
-fn source_info<'a, 'tcx>(mir: &Mir<'tcx>) -> SourceInfo {
+fn source_info<'a, 'tcx>(mir: &Body<'tcx>) -> SourceInfo {
     SourceInfo {
         span: mir.span,
         scope: OUTERMOST_SOURCE_SCOPE,
     }
 }
 
-fn insert_clean_drop<'a, 'tcx>(mir: &mut Mir<'tcx>) -> BasicBlock {
+fn insert_clean_drop<'a, 'tcx>(mir: &mut Body<'tcx>) -> BasicBlock {
     let return_block = insert_term_block(mir, TerminatorKind::Return);
 
     // Create a block to destroy an unresumed generators. This can only destroy upvars.
@@ -851,7 +851,7 @@ fn insert_clean_drop<'a, 'tcx>(mir: &mut Mir<'tcx>) -> BasicBlock {
     drop_clean
 }
 
-fn create_cases<'a, 'tcx, F>(mir: &mut Mir<'tcx>,
+fn create_cases<'a, 'tcx, F>(mir: &mut Body<'tcx>,
                           transform: &TransformVisitor<'a, 'tcx>,
                           target: F) -> Vec<(usize, BasicBlock)>
     where F: Fn(&SuspensionPoint) -> Option<BasicBlock> {
@@ -895,7 +895,7 @@ impl MirPass for StateTransform {
     fn run_pass<'a, 'tcx>(&self,
                     tcx: TyCtxt<'a, 'tcx, 'tcx>,
                     source: MirSource<'tcx>,
-                    mir: &mut Mir<'tcx>) {
+                    mir: &mut Body<'tcx>) {
         let yield_ty = if let Some(yield_ty) = mir.yield_ty {
             yield_ty
         } else {
@@ -959,7 +959,7 @@ fn run_pass<'a, 'tcx>(&self,
             new_ret_local,
             discr_ty,
         };
-        transform.visit_mir(mir);
+        transform.visit_body(mir);
 
         // Update our MIR struct to reflect the changed we've made
         mir.yield_ty = None;
index 782af3024ad2c448b1fb6f776e199decad28cdf1..0fac6868f57d3cd5900fbf51e5609a5b5d5325dd 100644 (file)
@@ -41,7 +41,7 @@ impl MirPass for Inline {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         if tcx.sess.opts.debugging_opts.mir_opt_level >= 2 {
             Inliner { tcx, source }.run_pass(mir);
         }
@@ -54,7 +54,7 @@ struct Inliner<'a, 'tcx: 'a> {
 }
 
 impl<'a, 'tcx> Inliner<'a, 'tcx> {
-    fn run_pass(&self, caller_mir: &mut Mir<'tcx>) {
+    fn run_pass(&self, caller_mir: &mut Body<'tcx>) {
         // Keep a queue of callsites to try inlining on. We take
         // advantage of the fact that queries detect cycles here to
         // allow us to try and fetch the fully optimized MIR of a
@@ -171,7 +171,7 @@ fn run_pass(&self, caller_mir: &mut Mir<'tcx>) {
     fn get_valid_function_call(&self,
                                bb: BasicBlock,
                                bb_data: &BasicBlockData<'tcx>,
-                               caller_mir: &Mir<'tcx>,
+                               caller_mir: &Body<'tcx>,
                                param_env: ParamEnv<'tcx>,
     ) -> Option<CallSite<'tcx>> {
         // Don't inline calls that are in cleanup blocks.
@@ -204,7 +204,7 @@ fn get_valid_function_call(&self,
 
     fn consider_optimizing(&self,
                            callsite: CallSite<'tcx>,
-                           callee_mir: &Mir<'tcx>)
+                           callee_mir: &Body<'tcx>)
                            -> bool
     {
         debug!("consider_optimizing({:?})", callsite);
@@ -216,7 +216,7 @@ fn consider_optimizing(&self,
 
     fn should_inline(&self,
                      callsite: CallSite<'tcx>,
-                     callee_mir: &Mir<'tcx>)
+                     callee_mir: &Body<'tcx>)
                      -> bool
     {
         debug!("should_inline({:?})", callsite);
@@ -394,8 +394,8 @@ fn should_inline(&self,
 
     fn inline_call(&self,
                    callsite: CallSite<'tcx>,
-                   caller_mir: &mut Mir<'tcx>,
-                   mut callee_mir: Mir<'tcx>) -> bool {
+                   caller_mir: &mut Body<'tcx>,
+                   mut callee_mir: Body<'tcx>) -> bool {
         let terminator = caller_mir[callsite.bb].terminator.take().unwrap();
         match terminator.kind {
             // FIXME: Handle inlining of diverging calls
@@ -531,7 +531,7 @@ fn make_call_args(
         &self,
         args: Vec<Operand<'tcx>>,
         callsite: &CallSite<'tcx>,
-        caller_mir: &mut Mir<'tcx>,
+        caller_mir: &mut Body<'tcx>,
     ) -> Vec<Local> {
         let tcx = self.tcx;
 
@@ -601,7 +601,7 @@ fn create_temp_if_necessary(
         &self,
         arg: Operand<'tcx>,
         callsite: &CallSite<'tcx>,
-        caller_mir: &mut Mir<'tcx>,
+        caller_mir: &mut Body<'tcx>,
     ) -> Local {
         // FIXME: Analysis of the usage of the arguments to avoid
         // unnecessary temporaries.
index 8187a81f0edab4c3f1731ea423f9d82189956b07..1b92b1acac55d6e46eb11960f330305473cac2a7 100644 (file)
@@ -1,6 +1,7 @@
 //! Performs various peephole optimizations.
 
-use rustc::mir::{Constant, Location, Place, PlaceBase, Mir, Operand, ProjectionElem, Rvalue, Local};
+use rustc::mir::{Constant, Location, Place, PlaceBase, Body, Operand, ProjectionElem, Rvalue,
+    Local};
 use rustc::mir::visit::{MutVisitor, Visitor};
 use rustc::ty::{self, TyCtxt};
 use rustc::util::nodemap::{FxHashMap, FxHashSet};
@@ -14,7 +15,7 @@ impl MirPass for InstCombine {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         // We only run when optimizing MIR (at any level).
         if tcx.sess.opts.debugging_opts.mir_opt_level == 0 {
             return
@@ -25,12 +26,12 @@ fn run_pass<'a, 'tcx>(&self,
         // `Place::ty()`).
         let optimizations = {
             let mut optimization_finder = OptimizationFinder::new(mir, tcx);
-            optimization_finder.visit_mir(mir);
+            optimization_finder.visit_body(mir);
             optimization_finder.optimizations
         };
 
         // Then carry out those optimizations.
-        MutVisitor::visit_mir(&mut InstCombineVisitor { optimizations }, mir);
+        MutVisitor::visit_body(&mut InstCombineVisitor { optimizations }, mir);
     }
 }
 
@@ -63,13 +64,13 @@ fn visit_rvalue(&mut self, rvalue: &mut Rvalue<'tcx>, location: Location) {
 
 /// Finds optimization opportunities on the MIR.
 struct OptimizationFinder<'b, 'a, 'tcx:'a+'b> {
-    mir: &'b Mir<'tcx>,
+    mir: &'b Body<'tcx>,
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     optimizations: OptimizationList<'tcx>,
 }
 
 impl<'b, 'a, 'tcx:'b> OptimizationFinder<'b, 'a, 'tcx> {
-    fn new(mir: &'b Mir<'tcx>, tcx: TyCtxt<'a, 'tcx, 'tcx>) -> OptimizationFinder<'b, 'a, 'tcx> {
+    fn new(mir: &'b Body<'tcx>, tcx: TyCtxt<'a, 'tcx, 'tcx>) -> OptimizationFinder<'b, 'a, 'tcx> {
         OptimizationFinder {
             mir,
             tcx,
index fd9d6bb5760b1b0646cf97ece7cda0594b9d9a1a..8c19637a955f158885aabacc815831111d391ec3 100644 (file)
@@ -13,7 +13,7 @@ impl MirPass for Lower128Bit {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let debugging_override = tcx.sess.opts.debugging_opts.lower_128bit_ops;
         let target_default = tcx.sess.host.options.i128_lowering;
         if !debugging_override.unwrap_or(target_default) {
@@ -25,7 +25,7 @@ fn run_pass<'a, 'tcx>(&self,
 }
 
 impl Lower128Bit {
-    fn lower_128bit_ops<'a, 'tcx>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, mir: &mut Mir<'tcx>) {
+    fn lower_128bit_ops<'a, 'tcx>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, mir: &mut Body<'tcx>) {
         let mut new_blocks = Vec::new();
         let cur_len = mir.basic_blocks().len();
 
index b6091644157178fd55a450481d4bb41fdb8a54cd..22b96a9db4750cfbc9033f1c8c8146ddcd7d4117 100644 (file)
@@ -1,6 +1,6 @@
 use crate::build;
 use rustc::hir::def_id::{CrateNum, DefId, LOCAL_CRATE};
-use rustc::mir::{Mir, MirPhase, Promoted};
+use rustc::mir::{Body, MirPhase, Promoted};
 use rustc::ty::{TyCtxt, InstanceDef};
 use rustc::ty::query::Providers;
 use rustc::ty::steal::Steal;
@@ -95,12 +95,12 @@ fn nested_visit_map<'b>(&'b mut self) -> NestedVisitorMap<'b, 'tcx> {
     tcx.arena.alloc(set)
 }
 
-fn mir_built<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Mir<'tcx>> {
+fn mir_built<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Body<'tcx>> {
     let mir = build::mir_build(tcx, def_id);
     tcx.alloc_steal_mir(mir)
 }
 
-/// Where a specific Mir comes from.
+/// Where a specific `mir::Body` comes from.
 #[derive(Debug, Copy, Clone)]
 pub struct MirSource<'tcx> {
     pub instance: InstanceDef<'tcx>,
@@ -145,19 +145,19 @@ fn name<'a>(&'a self) -> Cow<'a, str> {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           source: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>);
+                          mir: &mut Body<'tcx>);
 }
 
 pub fn run_passes(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &mut Mir<'tcx>,
+    mir: &mut Body<'tcx>,
     instance: InstanceDef<'tcx>,
     mir_phase: MirPhase,
     passes: &[&dyn MirPass],
 ) {
     let phase_index = mir_phase.phase_index();
 
-    let run_passes = |mir: &mut Mir<'tcx>, promoted| {
+    let run_passes = |mir: &mut Body<'tcx>, promoted| {
         if mir.phase >= mir_phase {
             return;
         }
@@ -196,7 +196,7 @@ pub fn run_passes(
     }
 }
 
-fn mir_const<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Mir<'tcx>> {
+fn mir_const<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Body<'tcx>> {
     // Unsafety check uses the raw mir, so make sure it is run
     let _ = tcx.unsafety_check_result(def_id);
 
@@ -210,7 +210,7 @@ fn mir_const<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Stea
     tcx.alloc_steal_mir(mir)
 }
 
-fn mir_validated<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Mir<'tcx>> {
+fn mir_validated<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Steal<Body<'tcx>> {
     let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
     if let hir::BodyOwnerKind::Const = tcx.hir().body_owner_kind_by_hir_id(hir_id) {
         // Ensure that we compute the `mir_const_qualif` for constants at
@@ -227,8 +227,8 @@ fn mir_validated<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx
     tcx.alloc_steal_mir(mir)
 }
 
-fn optimized_mir<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Mir<'tcx> {
-    // (Mir-)Borrowck uses `mir_validated`, so we have to force it to
+fn optimized_mir<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> &'tcx Body<'tcx> {
+    // `mir_borrowck` uses `mir_validated`, so we have to force it to
     // execute before we can steal.
     tcx.ensure().mir_borrowck(def_id);
 
index 648f4e65b0d076b9a6b8fa1c1609e10c872a2496..719e22ca1502380b8139279c2afb6579d5f9aea3 100644 (file)
@@ -12,14 +12,14 @@ impl MirPass for NoLandingPads {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         no_landing_pads(tcx, mir)
     }
 }
 
-pub fn no_landing_pads<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, mir: &mut Mir<'tcx>) {
+pub fn no_landing_pads<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, mir: &mut Body<'tcx>) {
     if tcx.sess.no_landing_pads() {
-        NoLandingPads.visit_mir(mir);
+        NoLandingPads.visit_body(mir);
     }
 }
 
index 0bf96c689176bedf8ee41449e9ff582d2508ced4..4b95fbf4b7d2f500cb2a6b100e6eeef33c38d339 100644 (file)
@@ -71,7 +71,7 @@ pub enum Candidate {
 struct TempCollector<'tcx> {
     temps: IndexVec<Local, TempState>,
     span: Span,
-    mir: &'tcx Mir<'tcx>,
+    mir: &'tcx Body<'tcx>,
 }
 
 impl<'tcx> Visitor<'tcx> for TempCollector<'tcx> {
@@ -134,7 +134,7 @@ fn visit_source_info(&mut self, source_info: &SourceInfo) {
     }
 }
 
-pub fn collect_temps(mir: &Mir<'_>,
+pub fn collect_temps(mir: &Body<'_>,
                      rpo: &mut ReversePostorder<'_, '_>) -> IndexVec<Local, TempState> {
     let mut collector = TempCollector {
         temps: IndexVec::from_elem(TempState::Undefined, &mir.local_decls),
@@ -149,8 +149,8 @@ pub fn collect_temps(mir: &Mir<'_>,
 
 struct Promoter<'a, 'tcx: 'a> {
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    source: &'a mut Mir<'tcx>,
-    promoted: Mir<'tcx>,
+    source: &'a mut Body<'tcx>,
+    promoted: Body<'tcx>,
     temps: &'a mut IndexVec<Local, TempState>,
 
     /// If true, all nested temps are also kept in the
@@ -369,7 +369,7 @@ fn visit_local(&mut self,
     }
 }
 
-pub fn promote_candidates<'a, 'tcx>(mir: &mut Mir<'tcx>,
+pub fn promote_candidates<'a, 'tcx>(mir: &mut Body<'tcx>,
                                     tcx: TyCtxt<'a, 'tcx, 'tcx>,
                                     mut temps: IndexVec<Local, TempState>,
                                     candidates: Vec<Candidate>) {
@@ -393,13 +393,13 @@ pub fn promote_candidates<'a, 'tcx>(mir: &mut Mir<'tcx>,
         }
 
 
-        // Declare return place local so that `Mir::new` doesn't complain.
+        // Declare return place local so that `mir::Body::new` doesn't complain.
         let initial_locals = iter::once(
             LocalDecl::new_return_place(tcx.types.never, mir.span)
         ).collect();
 
         let promoter = Promoter {
-            promoted: Mir::new(
+            promoted: Body::new(
                 IndexVec::new(),
                 // FIXME: maybe try to filter this to avoid blowing up
                 // memory usage?
index dca2836839373f9711762e9c34ed251b15a42724..a416792101f73d5d3ac57015b6b9ff93a1ecda2a 100644 (file)
@@ -113,7 +113,7 @@ struct ConstCx<'a, 'tcx> {
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     param_env: ty::ParamEnv<'tcx>,
     mode: Mode,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 
     per_local: PerQualif<BitSet<Local>>,
 }
@@ -619,7 +619,7 @@ fn deref(&self) -> &Self::Target {
 impl<'a, 'tcx> Checker<'a, 'tcx> {
     fn new(tcx: TyCtxt<'a, 'tcx, 'tcx>,
            def_id: DefId,
-           mir: &'a Mir<'tcx>,
+           mir: &'a Body<'tcx>,
            mode: Mode)
            -> Self {
         assert!(def_id.is_local());
@@ -1431,7 +1431,7 @@ fn mir_const_qualif<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
     let mir = &tcx.mir_const(def_id).borrow();
 
     if mir.return_ty().references_error() {
-        tcx.sess.delay_span_bug(mir.span, "mir_const_qualif: Mir had errors");
+        tcx.sess.delay_span_bug(mir.span, "mir_const_qualif: MIR had errors");
         return (1 << IsNotPromotable::IDX, tcx.arena.alloc(BitSet::new_empty(0)));
     }
 
@@ -1444,10 +1444,10 @@ impl MirPass for QualifyAndPromoteConstants {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         // There's not really any point in promoting errorful MIR.
         if mir.return_ty().references_error() {
-            tcx.sess.delay_span_bug(mir.span, "QualifyAndPromoteConstants: Mir had errors");
+            tcx.sess.delay_span_bug(mir.span, "QualifyAndPromoteConstants: MIR had errors");
             return;
         }
 
index a1e2d0683d3800a37f3184e06299d15e80ad0d7c..4811380e238603bec257fef91a51a5595cf37ec4 100644 (file)
@@ -11,7 +11,7 @@
 pub fn is_min_const_fn(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     def_id: DefId,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
 ) -> McfResult {
     let mut current = def_id;
     loop {
@@ -130,7 +130,7 @@ fn check_ty(
 
 fn check_rvalue(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     rvalue: &Rvalue<'tcx>,
     span: Span,
 ) -> McfResult {
@@ -210,7 +210,7 @@ fn check_rvalue(
 
 fn check_statement(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     statement: &Statement<'tcx>,
 ) -> McfResult {
     let span = statement.source_info.span;
@@ -250,7 +250,10 @@ fn check_operand(
     }
 }
 
-fn check_place(place: &Place<'tcx>, span: Span) -> McfResult {
+fn check_place(
+    place: &Place<'tcx>,
+    span: Span,
+) -> McfResult {
     place.iterate(|place_base, place_projection| {
         for proj in place_projection {
             match proj.elem {
@@ -277,7 +280,7 @@ fn check_place(place: &Place<'tcx>, span: Span) -> McfResult {
 
 fn check_terminator(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     terminator: &Terminator<'tcx>,
 ) -> McfResult {
     let span = terminator.source_info.span;
index b7493b25d46503826b4ddebfb87aa0015e1d2ffe..42818a571151e1a25efb409ec527de390c8b6e8c 100644 (file)
@@ -11,7 +11,7 @@
 
 pub fn remove_noop_landing_pads<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    mir: &mut Mir<'tcx>)
+    mir: &mut Body<'tcx>)
 {
     if tcx.sess.no_landing_pads() {
         return
@@ -25,7 +25,7 @@ impl MirPass for RemoveNoopLandingPads {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         remove_noop_landing_pads(tcx, mir);
     }
 }
@@ -34,7 +34,7 @@ impl RemoveNoopLandingPads {
     fn is_nop_landing_pad(
         &self,
         bb: BasicBlock,
-        mir: &Mir<'_>,
+        mir: &Body<'_>,
         nop_landing_pads: &BitSet<BasicBlock>,
     ) -> bool {
         for stmt in &mir[bb].statements {
@@ -86,7 +86,7 @@ fn is_nop_landing_pad(
         }
     }
 
-    fn remove_nop_landing_pads(&self, mir: &mut Mir<'_>) {
+    fn remove_nop_landing_pads(&self, mir: &mut Body<'_>) {
         // make sure there's a single resume block
         let resume_block = {
             let patch = MirPatch::new(mir);
index 7d2dbff996d084148c098ff0ebab4e34c7e468f4..2b3eb9e1edf307ce91a9bef2f3dbe70dee72ac10 100644 (file)
@@ -5,7 +5,7 @@
 
 use rustc::ty::{self, TyCtxt};
 use rustc::hir::def_id::DefId;
-use rustc::mir::{self, Mir, Location};
+use rustc::mir::{self, Body, Location};
 use rustc_data_structures::bit_set::BitSet;
 use crate::transform::{MirPass, MirSource};
 
@@ -26,7 +26,7 @@
 
 impl MirPass for SanityCheck {
     fn run_pass<'a, 'tcx>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                          src: MirSource<'tcx>, mir: &mut Mir<'tcx>) {
+                          src: MirSource<'tcx>, mir: &mut Body<'tcx>) {
         let def_id = src.def_id();
         if !tcx.has_attr(def_id, sym::rustc_mir) {
             debug!("skipping rustc_peek::SanityCheck on {}", tcx.def_path_str(def_id));
@@ -85,7 +85,7 @@ fn run_pass<'a, 'tcx>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>,
 /// expression form above, then that emits an error as well, but those
 /// errors are not intended to be used for unit tests.)
 pub fn sanity_check_via_rustc_peek<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                                                mir: &Mir<'tcx>,
+                                                mir: &Body<'tcx>,
                                                 def_id: DefId,
                                                 _attributes: &[ast::Attribute],
                                                 results: &DataflowResults<'tcx, O>)
@@ -102,7 +102,7 @@ pub fn sanity_check_via_rustc_peek<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 }
 
 fn each_block<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                           mir: &Mir<'tcx>,
+                           mir: &Body<'tcx>,
                            results: &DataflowResults<'tcx, O>,
                            bb: mir::BasicBlock) where
     O: BitDenotation<'tcx, Idx=MovePathIndex> + HasMoveData<'tcx>
index ee16ec7b41cf5e0af70309a5fcf25a76b64e66e3..e7be238e850f22a70dfffa9eb72294c51691a9d0 100644 (file)
@@ -44,7 +44,7 @@ pub fn new(label: &str) -> Self {
     }
 }
 
-pub fn simplify_cfg(mir: &mut Mir<'_>) {
+pub fn simplify_cfg(mir: &mut Body<'_>) {
     CfgSimplifier::new(mir).simplify();
     remove_dead_blocks(mir);
 
@@ -60,7 +60,7 @@ fn name<'a>(&'a self) -> Cow<'a, str> {
     fn run_pass<'a, 'tcx>(&self,
                           _tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         debug!("SimplifyCfg({:?}) - simplifying {:?}", self.label, mir);
         simplify_cfg(mir);
     }
@@ -72,7 +72,7 @@ pub struct CfgSimplifier<'a, 'tcx: 'a> {
 }
 
 impl<'a, 'tcx: 'a> CfgSimplifier<'a, 'tcx> {
-    pub fn new(mir: &'a mut Mir<'tcx>) -> Self {
+    pub fn new(mir: &'a mut Body<'tcx>) -> Self {
         let mut pred_count = IndexVec::from_elem(0u32, mir.basic_blocks());
 
         // we can't use mir.predecessors() here because that counts
@@ -263,7 +263,7 @@ fn strip_nops(&mut self) {
     }
 }
 
-pub fn remove_dead_blocks(mir: &mut Mir<'_>) {
+pub fn remove_dead_blocks(mir: &mut Body<'_>) {
     let mut seen = BitSet::new_empty(mir.basic_blocks().len());
     for (bb, _) in traversal::preorder(mir) {
         seen.insert(bb.index());
@@ -299,9 +299,9 @@ impl MirPass for SimplifyLocals {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let mut marker = DeclMarker { locals: BitSet::new_empty(mir.local_decls.len()) };
-        marker.visit_mir(mir);
+        marker.visit_body(mir);
         // Return pointer and arguments are always live
         marker.locals.insert(RETURN_PLACE);
         for arg in mir.args_iter() {
@@ -317,7 +317,7 @@ fn run_pass<'a, 'tcx>(&self,
 
         let map = make_local_map(&mut mir.local_decls, marker.locals);
         // Update references to all vars and tmps now
-        LocalUpdater { map }.visit_mir(mir);
+        LocalUpdater { map }.visit_body(mir);
         mir.local_decls.shrink_to_fit();
     }
 }
index db73e829c53a7129f93d523b18c98b5577082af6..53949bcfcd707737340477b2943aba88c9915a52 100644 (file)
@@ -22,7 +22,7 @@ fn name<'a>(&'a self) -> Cow<'a, str> {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         for block in mir.basic_blocks_mut() {
             let terminator = block.terminator_mut();
             terminator.kind = match terminator.kind {
index a2433ab838d07ee56be3fc929c90e69550eeb4d1..ee1d2ca2a891ce1907e303fe7e730076d4ea97dd 100644 (file)
@@ -40,18 +40,18 @@ impl MirPass for UniformArrayMoveOut {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let mut patch = MirPatch::new(mir);
         {
             let mut visitor = UniformArrayMoveOutVisitor{mir, patch: &mut patch, tcx};
-            visitor.visit_mir(mir);
+            visitor.visit_body(mir);
         }
         patch.apply(mir);
     }
 }
 
 struct UniformArrayMoveOutVisitor<'a, 'tcx: 'a> {
-    mir: &'a Mir<'tcx>,
+    mir: &'a Body<'tcx>,
     patch: &'a mut MirPatch<'tcx>,
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
 }
@@ -165,14 +165,14 @@ impl MirPass for RestoreSubsliceArrayMoveOut {
     fn run_pass<'a, 'tcx>(&self,
                           tcx: TyCtxt<'a, 'tcx, 'tcx>,
                           _src: MirSource<'tcx>,
-                          mir: &mut Mir<'tcx>) {
+                          mir: &mut Body<'tcx>) {
         let mut patch = MirPatch::new(mir);
         {
             let mut visitor = RestoreDataCollector {
                 locals_use: IndexVec::from_elem(LocalUse::new(), &mir.local_decls),
                 candidates: vec![],
             };
-            visitor.visit_mir(mir);
+            visitor.visit_body(mir);
 
             for candidate in &visitor.candidates {
                 let statement = &mir[candidate.block].statements[candidate.statement_index];
@@ -254,7 +254,7 @@ fn check_and_patch<'tcx>(candidate: Location,
     }
 
     fn try_get_item_source<'a, 'tcx>(local_use: &LocalUse,
-                                     mir: &'a Mir<'tcx>) -> Option<(u32, &'a Place<'tcx>)> {
+                                     mir: &'a Body<'tcx>) -> Option<(u32, &'a Place<'tcx>)> {
         if let Some(location) = local_use.first_use {
             let block = &mir[location.block];
             if block.statements.len() > location.statement_index {
index 7bd61c3a59c94ec09bcfe1788635349c754f4109..c8804dfbaf2619dd5f77099d85c14e713f4d3a13 100644 (file)
@@ -1,5 +1,5 @@
 use rustc::mir::{Local, Location};
-use rustc::mir::Mir;
+use rustc::mir::Body;
 use rustc::mir::visit::PlaceContext;
 use rustc::mir::visit::Visitor;
 
@@ -9,10 +9,10 @@
     fn find_assignments(&self, local: Local) -> Vec<Location>;
 }
 
-impl<'tcx> FindAssignments for Mir<'tcx>{
+impl<'tcx> FindAssignments for Body<'tcx>{
     fn find_assignments(&self, local: Local) -> Vec<Location>{
             let mut visitor = FindLocalAssignmentVisitor{ needle: local, locations: vec![]};
-            visitor.visit_mir(self);
+            visitor.visit_body(self);
             visitor.locations
     }
 }
index 2925005b6674dc1d05c6c9593a4eff749b5d6fd3..ba0190756c54277c43b1f0906d7b2ee5c87c4bc2 100644 (file)
@@ -1,6 +1,6 @@
 //! Def-use analysis.
 
-use rustc::mir::{Local, Location, Mir};
+use rustc::mir::{Local, Location, Body};
 use rustc::mir::visit::{PlaceContext, MutVisitor, Visitor};
 use rustc_data_structures::indexed_vec::IndexVec;
 use std::mem;
@@ -21,19 +21,19 @@ pub struct Use {
 }
 
 impl DefUseAnalysis {
-    pub fn new(mir: &Mir<'_>) -> DefUseAnalysis {
+    pub fn new(mir: &Body<'_>) -> DefUseAnalysis {
         DefUseAnalysis {
             info: IndexVec::from_elem_n(Info::new(), mir.local_decls.len()),
         }
     }
 
-    pub fn analyze(&mut self, mir: &Mir<'_>) {
+    pub fn analyze(&mut self, mir: &Body<'_>) {
         self.clear();
 
         let mut finder = DefUseFinder {
             info: mem::replace(&mut self.info, IndexVec::new()),
         };
-        finder.visit_mir(mir);
+        finder.visit_body(mir);
         self.info = finder.info
     }
 
@@ -47,7 +47,7 @@ pub fn local_info(&self, local: Local) -> &Info {
         &self.info[local]
     }
 
-    fn mutate_defs_and_uses<F>(&self, local: Local, mir: &mut Mir<'_>, mut callback: F)
+    fn mutate_defs_and_uses<F>(&self, local: Local, mir: &mut Body<'_>, mut callback: F)
                                where F: for<'a> FnMut(&'a mut Local,
                                                       PlaceContext,
                                                       Location) {
@@ -61,7 +61,7 @@ fn mutate_defs_and_uses<F>(&self, local: Local, mir: &mut Mir<'_>, mut callback:
     // FIXME(pcwalton): this should update the def-use chains.
     pub fn replace_all_defs_and_uses_with(&self,
                                           local: Local,
-                                          mir: &mut Mir<'_>,
+                                          mir: &mut Body<'_>,
                                           new_local: Local) {
         self.mutate_defs_and_uses(local, mir, |local, _, _| *local = new_local)
     }
@@ -123,7 +123,7 @@ struct MutateUseVisitor<F> {
 }
 
 impl<F> MutateUseVisitor<F> {
-    fn new(query: Local, callback: F, _: &Mir<'_>)
+    fn new(query: Local, callback: F, _: &Body<'_>)
            -> MutateUseVisitor<F>
            where F: for<'a> FnMut(&'a mut Local, PlaceContext, Location) {
         MutateUseVisitor {
index ac5ebc5e2512a9de4b668b184ca70a7442751404..076ba60c6441c5da540fda8630424784236511de 100644 (file)
@@ -74,7 +74,7 @@ pub trait DropElaborator<'a, 'tcx: 'a> : fmt::Debug {
     type Path : Copy + fmt::Debug;
 
     fn patch(&mut self) -> &mut MirPatch<'tcx>;
-    fn mir(&self) -> &'a Mir<'tcx>;
+    fn mir(&self) -> &'a Body<'tcx>;
     fn tcx(&self) -> TyCtxt<'a, 'tcx, 'tcx>;
     fn param_env(&self) -> ty::ParamEnv<'tcx>;
 
index fc4c6b3fd3f244afc5a41d37239e39c31ba8f987..20d92da9ba330e86e6635e145fbf1f3b221e4edd 100644 (file)
@@ -34,7 +34,7 @@ pub fn graphviz_safe_def_name(def_id: DefId) -> String {
 /// Write a graphviz DOT graph of the MIR.
 pub fn write_mir_fn_graphviz<'tcx, W>(tcx: TyCtxt<'_, '_, 'tcx>,
                                       def_id: DefId,
-                                      mir: &Mir<'_>,
+                                      mir: &Body<'_>,
                                       w: &mut W) -> io::Result<()>
     where W: Write
 {
@@ -68,7 +68,7 @@ pub fn write_mir_fn_graphviz<'tcx, W>(tcx: TyCtxt<'_, '_, 'tcx>,
 /// `init` and `fini` are callbacks for emitting additional rows of
 /// data (using HTML enclosed with `<tr>` in the emitted text).
 pub fn write_node_label<W: Write, INIT, FINI>(block: BasicBlock,
-                                              mir: &Mir<'_>,
+                                              mir: &Body<'_>,
                                               w: &mut W,
                                               num_cols: u32,
                                               init: INIT,
@@ -110,7 +110,7 @@ pub fn write_node_label<W: Write, INIT, FINI>(block: BasicBlock,
 }
 
 /// Write a graphviz DOT node for the given basic block.
-fn write_node<W: Write>(block: BasicBlock, mir: &Mir<'_>, w: &mut W) -> io::Result<()> {
+fn write_node<W: Write>(block: BasicBlock, mir: &Body<'_>, w: &mut W) -> io::Result<()> {
     // Start a new node with the label to follow, in one of DOT's pseudo-HTML tables.
     write!(w, r#"    {} [shape="none", label=<"#, node(block))?;
     write_node_label(block, mir, w, 1, |_| Ok(()), |_| Ok(()))?;
@@ -119,7 +119,7 @@ fn write_node<W: Write>(block: BasicBlock, mir: &Mir<'_>, w: &mut W) -> io::Resu
 }
 
 /// Write graphviz DOT edges with labels between the given basic block and all of its successors.
-fn write_edges<W: Write>(source: BasicBlock, mir: &Mir<'_>, w: &mut W) -> io::Result<()> {
+fn write_edges<W: Write>(source: BasicBlock, mir: &Body<'_>, w: &mut W) -> io::Result<()> {
     let terminator = mir[source].terminator();
     let labels = terminator.kind.fmt_successor_labels();
 
@@ -135,7 +135,7 @@ fn write_edges<W: Write>(source: BasicBlock, mir: &Mir<'_>, w: &mut W) -> io::Re
 /// all the variables and temporaries.
 fn write_graph_label<'a, 'gcx, 'tcx, W: Write>(tcx: TyCtxt<'a, 'gcx, 'tcx>,
                                                def_id: DefId,
-                                               mir: &Mir<'_>,
+                                               mir: &Body<'_>,
                                                w: &mut W)
                                                -> io::Result<()> {
     write!(w, "    label=<fn {}(", dot::escape_html(&tcx.def_path_str(def_id)))?;
index 8d9a878fc9e3766aa3f2c92cd01edbb81d1583e6..a3317d3956be43015ffbc99766df5c963fd0beda 100644 (file)
@@ -57,7 +57,7 @@ pub struct LivenessResult {
 /// Computes which local variables are live within the given function
 /// `mir`, including drops.
 pub fn liveness_of_locals<'tcx>(
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
 ) -> LivenessResult {
     let num_live_vars = mir.local_decls.len();
 
@@ -258,7 +258,7 @@ pub fn dump_mir<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     pass_name: &str,
     source: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     result: &LivenessResult,
 ) {
     if !dump_enabled(tcx, pass_name, source) {
@@ -276,7 +276,7 @@ fn dump_matched_mir_node<'a, 'tcx>(
     pass_name: &str,
     node_path: &str,
     source: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     result: &LivenessResult,
 ) {
     let mut file_path = PathBuf::new();
@@ -297,7 +297,7 @@ fn dump_matched_mir_node<'a, 'tcx>(
 pub fn write_mir_fn<'a, 'tcx>(
     tcx: TyCtxt<'a, 'tcx, 'tcx>,
     src: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     w: &mut dyn Write,
     result: &LivenessResult,
 ) -> io::Result<()> {
index 366cd71f6d4e9551646247aefd6414f3ee4878c1..974dda867bc9df5e7a7f0b5fef6dc6e337ee6e98 100644 (file)
@@ -17,7 +17,7 @@ pub struct MirPatch<'tcx> {
 }
 
 impl<'tcx> MirPatch<'tcx> {
-    pub fn new(mir: &Mir<'tcx>) -> Self {
+    pub fn new(mir: &Body<'tcx>) -> Self {
         let mut result = MirPatch {
             patch_map: IndexVec::from_elem(None, mir.basic_blocks()),
             new_blocks: vec![],
@@ -75,7 +75,7 @@ pub fn is_patched(&self, bb: BasicBlock) -> bool {
         self.patch_map[bb].is_some()
     }
 
-    pub fn terminator_loc(&self, mir: &Mir<'tcx>, bb: BasicBlock) -> Location {
+    pub fn terminator_loc(&self, mir: &Body<'tcx>, bb: BasicBlock) -> Location {
         let offset = match bb.index().checked_sub(mir.basic_blocks().len()) {
             Some(index) => self.new_blocks[index].statements.len(),
             None => mir[bb].statements.len()
@@ -127,7 +127,7 @@ pub fn make_nop(&mut self, loc: Location) {
         self.make_nop.push(loc);
     }
 
-    pub fn apply(self, mir: &mut Mir<'tcx>) {
+    pub fn apply(self, mir: &mut Body<'tcx>) {
         debug!("MirPatch: make nops at: {:?}", self.make_nop);
         for loc in self.make_nop {
             mir.make_statement_nop(loc);
@@ -177,7 +177,7 @@ pub fn source_info_for_index(data: &BasicBlockData<'_>, loc: Location) -> Source
         }
     }
 
-    pub fn source_info_for_location(&self, mir: &Mir<'_>, loc: Location) -> SourceInfo {
+    pub fn source_info_for_location(&self, mir: &Body<'_>, loc: Location) -> SourceInfo {
         let data = match loc.block.index().checked_sub(mir.basic_blocks().len()) {
             Some(new) => &self.new_blocks[new],
             None => &mir[loc.block]
index cf90f44e6707fd19edfde4aeb3493bb1db3f9bc0..aec8ce7ced6c7609ee3eb62a6dc4b439c6597d4d 100644 (file)
@@ -68,7 +68,7 @@ pub fn dump_mir<'a, 'gcx, 'tcx, F>(
     pass_name: &str,
     disambiguator: &dyn Display,
     source: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     extra_data: F,
 ) where
     F: FnMut(PassWhere, &mut dyn Write) -> io::Result<()>,
@@ -124,7 +124,7 @@ fn dump_matched_mir_node<'a, 'gcx, 'tcx, F>(
     node_path: &str,
     disambiguator: &dyn Display,
     source: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     mut extra_data: F,
 ) where
     F: FnMut(PassWhere, &mut dyn Write) -> io::Result<()>,
@@ -282,7 +282,7 @@ pub fn write_mir_pretty<'a, 'gcx, 'tcx>(
 pub fn write_mir_fn<'a, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
     src: MirSource<'tcx>,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     extra_data: &mut F,
     w: &mut dyn Write,
 ) -> io::Result<()>
@@ -306,7 +306,7 @@ pub fn write_mir_fn<'a, 'gcx, 'tcx, F>(
 pub fn write_basic_block<'cx, 'gcx, 'tcx, F>(
     tcx: TyCtxt<'cx, 'gcx, 'tcx>,
     block: BasicBlock,
-    mir: &Mir<'tcx>,
+    mir: &Body<'tcx>,
     extra_data: &mut F,
     w: &mut dyn Write,
 ) -> io::Result<()>
@@ -464,7 +464,7 @@ fn comment(tcx: TyCtxt<'_, '_, '_>, SourceInfo { span, scope }: SourceInfo) -> S
 /// Prints local variables in a scope tree.
 fn write_scope_tree(
     tcx: TyCtxt<'_, '_, '_>,
-    mir: &Mir<'_>,
+    mir: &Body<'_>,
     scope_tree: &FxHashMap<SourceScope, Vec<SourceScope>>,
     w: &mut dyn Write,
     parent: SourceScope,
@@ -541,7 +541,7 @@ fn write_scope_tree(
 pub fn write_mir_intro<'a, 'gcx, 'tcx>(
     tcx: TyCtxt<'a, 'gcx, 'tcx>,
     src: MirSource<'tcx>,
-    mir: &Mir<'_>,
+    mir: &Body<'_>,
     w: &mut dyn Write,
 ) -> io::Result<()> {
     write_mir_sig(tcx, src, mir, w)?;
@@ -572,7 +572,7 @@ pub fn write_mir_intro<'a, 'gcx, 'tcx>(
 fn write_mir_sig(
     tcx: TyCtxt<'_, '_, '_>,
     src: MirSource<'tcx>,
-    mir: &Mir<'_>,
+    mir: &Body<'_>,
     w: &mut dyn Write,
 ) -> io::Result<()> {
     use rustc::hir::def::DefKind;
@@ -629,7 +629,7 @@ fn write_mir_sig(
     Ok(())
 }
 
-fn write_user_type_annotations(mir: &Mir<'_>, w: &mut dyn Write) -> io::Result<()> {
+fn write_user_type_annotations(mir: &Body<'_>, w: &mut dyn Write) -> io::Result<()> {
     if !mir.user_type_annotations.is_empty() {
         writeln!(w, "| User Type Annotations")?;
     }
index 68930533a285ca8dd26f13d7fb97417a6e2dd4ba..a08c028390bf7a86b1184a5a118b8b47ed882111 100644 (file)
@@ -1703,8 +1703,13 @@ fn check(&self, item_id: hir::HirId, required_visibility: ty::Visibility)
         }
     }
 
-    fn check_trait_or_impl_item(&self, hir_id: hir::HirId, assoc_item_kind: AssocItemKind,
-                                defaultness: hir::Defaultness, vis: ty::Visibility) {
+    fn check_assoc_item(
+        &self,
+        hir_id: hir::HirId,
+        assoc_item_kind: AssocItemKind,
+        defaultness: hir::Defaultness,
+        vis: ty::Visibility,
+    ) {
         let mut check = self.check(hir_id, vis);
 
         let (check_ty, is_assoc_ty) = match assoc_item_kind {
@@ -1754,8 +1759,12 @@ fn visit_item(&mut self, item: &'tcx hir::Item) {
                 self.check(item.hir_id, item_visibility).generics().predicates();
 
                 for trait_item_ref in trait_item_refs {
-                    self.check_trait_or_impl_item(trait_item_ref.id.hir_id, trait_item_ref.kind,
-                                                  trait_item_ref.defaultness, item_visibility);
+                    self.check_assoc_item(
+                        trait_item_ref.id.hir_id,
+                        trait_item_ref.kind,
+                        trait_item_ref.defaultness,
+                        item_visibility,
+                    );
                 }
             }
             hir::ItemKind::TraitAlias(..) => {
@@ -1803,8 +1812,12 @@ fn visit_item(&mut self, item: &'tcx hir::Item) {
                     } else {
                         impl_vis
                     };
-                    self.check_trait_or_impl_item(impl_item_ref.id.hir_id, impl_item_ref.kind,
-                                                  impl_item_ref.defaultness, impl_item_vis);
+                    self.check_assoc_item(
+                        impl_item_ref.id.hir_id,
+                        impl_item_ref.kind,
+                        impl_item_ref.defaultness,
+                        impl_item_vis,
+                    );
                 }
             }
         }
index c05b69ab44f422ba98700e650befc143eb37ac2f..9b7b44025c13f73043590e2edca2d2dddbeea68a 100644 (file)
@@ -860,7 +860,7 @@ fn visit_fn(&mut self,
             FnKind::ItemFn(_, ref header, ..) =>
                 (FnItemRibKind, &header.asyncness.node),
             FnKind::Method(_, ref sig, _, _) =>
-                (TraitOrImplItemRibKind, &sig.header.asyncness.node),
+                (AssocItemRibKind, &sig.header.asyncness.node),
             FnKind::Closure(_) =>
                 // Async closures aren't resolved through `visit_fn`-- they're
                 // processed separately
@@ -1033,7 +1033,7 @@ enum RibKind<'a> {
     /// methods or associated types. Allow references to ty params that impl or trait
     /// binds. Disallow any other upvars (including other ty params that are
     /// upvars).
-    TraitOrImplItemRibKind,
+    AssocItemRibKind,
 
     /// We passed through a function definition. Disallow upvars.
     /// Permit only those const parameters that are specified in the function's generics.
@@ -2612,7 +2612,7 @@ fn resolve_item(&mut self, item: &Item) {
 
                         for trait_item in trait_items {
                             let generic_params = HasGenericParams(&trait_item.generics,
-                                                                    TraitOrImplItemRibKind);
+                                                                    AssocItemRibKind);
                             this.with_generic_param_rib(generic_params, |this| {
                                 match trait_item.node {
                                     TraitItemKind::Const(ref ty, ref default) => {
@@ -2899,7 +2899,7 @@ fn resolve_implementation(&mut self,
 
                                     // We also need a new scope for the impl item type parameters.
                                     let generic_params = HasGenericParams(&impl_item.generics,
-                                                                          TraitOrImplItemRibKind);
+                                                                          AssocItemRibKind);
                                     this.with_generic_param_rib(generic_params, |this| {
                                         use self::ResolutionError::*;
                                         match impl_item.node {
@@ -4074,7 +4074,7 @@ fn adjust_local_res(&mut self,
                                 seen.insert(node_id, depth);
                             }
                         }
-                        ItemRibKind | FnItemRibKind | TraitOrImplItemRibKind => {
+                        ItemRibKind | FnItemRibKind | AssocItemRibKind => {
                             // This was an attempt to access an upvar inside a
                             // named function item. This is not allowed, so we
                             // report an error.
@@ -4103,7 +4103,7 @@ fn adjust_local_res(&mut self,
             Res::Def(DefKind::TyParam, _) | Res::SelfTy(..) => {
                 for rib in ribs {
                     match rib.kind {
-                        NormalRibKind | TraitOrImplItemRibKind | ClosureRibKind(..) |
+                        NormalRibKind | AssocItemRibKind | ClosureRibKind(..) |
                         ModuleRibKind(..) | MacroDefinition(..) | ForwardTyParamBanRibKind |
                         ConstantItemRibKind | TyParamAsConstParamTy => {
                             // Nothing to do. Continue.
index 04cd632b29793461e345891970dcdec380bca172..96c647ca31e6fca339194abb83faba601471d514 100644 (file)
@@ -411,7 +411,7 @@ fn instantiate_binders_existentially(
     }
 
     fn debug_ex_clause(&mut self, value: &'v ChalkExClause<'tcx>) -> Box<dyn Debug + 'v> {
-        let string = format!("{:?}", self.infcx.resolve_type_vars_if_possible(value));
+        let string = format!("{:?}", self.infcx.resolve_vars_if_possible(value));
         Box::new(string)
     }
 
index 7ce450c7039a0c39640f0a1c75d98e37ae5656f2..c1f14cd3f8ed51e182382e2fc33ede2103625ca7 100644 (file)
@@ -57,7 +57,7 @@ pub(super) fn program_clauses_impl(
         use rustc::traits::WhereClause::*;
         use rustc::infer::canonical::OriginalQueryValues;
 
-        let goal = self.infcx.resolve_type_vars_if_possible(goal);
+        let goal = self.infcx.resolve_vars_if_possible(goal);
 
         debug!("program_clauses(goal = {:?})", goal);
 
index 9d234e93b837bc797aed624171a3dc41006503f5..f1b8588790b72a4fe3fbbdb3c2399b17c95e6594 100644 (file)
@@ -111,8 +111,8 @@ fn apply_answer_subst(
     ) -> Fallible<ChalkExClause<'tcx>> {
         debug!(
             "apply_answer_subst(ex_clause = {:?}, selected_goal = {:?})",
-            self.infcx.resolve_type_vars_if_possible(&ex_clause),
-            self.infcx.resolve_type_vars_if_possible(selected_goal)
+            self.infcx.resolve_vars_if_possible(&ex_clause),
+            self.infcx.resolve_vars_if_possible(selected_goal)
         );
 
         let (answer_subst, _) = self.infcx.instantiate_canonical_with_fresh_inference_vars(
index b1688a7fbbb728bdbfdec2e6e41eaf73bb842eae..73bb3fb5b9a2de6972ccf3e3b86f1a0d4091b250 100644 (file)
@@ -121,7 +121,7 @@ fn compute_implied_outlives_bounds<'tcx>(
                 ty::Predicate::TypeOutlives(ref data) => match data.no_bound_vars() {
                     None => vec![],
                     Some(ty::OutlivesPredicate(ty_a, r_b)) => {
-                        let ty_a = infcx.resolve_type_vars_if_possible(&ty_a);
+                        let ty_a = infcx.resolve_vars_if_possible(&ty_a);
                         let mut components = smallvec![];
                         tcx.push_outlives_components(ty_a, &mut components);
                         implied_bounds_from_components(r_b, components)
index 412d2ca6dfcff06384242238a22e0b35af2c38fa..24fa5e97752a67e84e526e67219402bdb473876f 100644 (file)
@@ -36,7 +36,7 @@ fn normalize_ty_after_erasing_regions<'tcx>(
                     None,
                 );
 
-                let normalized_value = infcx.resolve_type_vars_if_possible(&normalized_value);
+                let normalized_value = infcx.resolve_vars_if_possible(&normalized_value);
                 let normalized_value = infcx.tcx.erase_regions(&normalized_value);
                 tcx.lift_to_global(&normalized_value).unwrap()
             }
index a74a33b7448e2e3933cbce3de2996eb7f2f84b1b..5a84e0cb85a6ec0643c7153be6ee40daf9731ffc 100644 (file)
@@ -226,7 +226,7 @@ pub fn check_pat_walk(
 
                 // Now that we know the types can be unified we find the unified type and use
                 // it to type the entire expression.
-                let common_type = self.resolve_type_vars_if_possible(&lhs_ty);
+                let common_type = self.resolve_vars_if_possible(&lhs_ty);
 
                 // subtyping doesn't matter here, as the value is some kind of scalar
                 self.demand_eqtype_pat(pat.span, expected, lhs_ty, discrim_span);
index f863cfe1887db6f9c726b2652a1668a4ddae7b9e..38c3ee776369aa49c750803067fef773a4e08f46 100644 (file)
@@ -98,7 +98,7 @@ pub fn new(infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
             body_id,
             param_env,
             steps: vec![],
-            cur_ty: infcx.resolve_type_vars_if_possible(&base_ty),
+            cur_ty: infcx.resolve_vars_if_possible(&base_ty),
             obligations: vec![],
             at_start: true,
             include_raw_pointers: false,
@@ -152,7 +152,7 @@ fn overloaded_deref_ty(&mut self, ty: Ty<'tcx>) -> Option<Ty<'tcx>> {
                ty, normalized_ty, obligations);
         self.obligations.extend(obligations);
 
-        Some(self.infcx.resolve_type_vars_if_possible(&normalized_ty))
+        Some(self.infcx.resolve_vars_if_possible(&normalized_ty))
     }
 
     /// Returns the final type, generating an error if it is an
@@ -164,7 +164,7 @@ pub fn unambiguous_final_ty(&self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Ty<'tcx> {
     /// Returns the final type we ended up with, which may well be an
     /// inference variable (we will resolve it first, if possible).
     pub fn maybe_ambiguous_final_ty(&self) -> Ty<'tcx> {
-        self.infcx.resolve_type_vars_if_possible(&self.cur_ty)
+        self.infcx.resolve_vars_if_possible(&self.cur_ty)
     }
 
     pub fn step_count(&self) -> usize {
index 4689456d11fe21cff3aaafc3ea3f0cf36228c995..f8cad733ca1c87abcc292ab32d8998dc58d3f52f 100644 (file)
@@ -82,7 +82,7 @@ fn pointer_kind(&self, t: Ty<'tcx>, span: Span) ->
     {
         debug!("pointer_kind({:?}, {:?})", t, span);
 
-        let t = self.resolve_type_vars_if_possible(&t);
+        let t = self.resolve_vars_if_possible(&t);
 
         if t.references_error() {
             return Err(ErrorReported);
@@ -334,7 +334,7 @@ fn report_cast_to_unsized_type(&self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) {
         let tstr = fcx.ty_to_string(self.cast_ty);
         let mut err = type_error_struct!(fcx.tcx.sess, self.span, self.expr_ty, E0620,
                                          "cast to unsized type: `{}` as `{}`",
-                                         fcx.resolve_type_vars_if_possible(&self.expr_ty),
+                                         fcx.resolve_vars_if_possible(&self.expr_ty),
                                          tstr);
         match self.expr_ty.sty {
             ty::Ref(_, _, mt) => {
index 3fa192f16f32e2c431740c5735f747089f0d5773..419f61b0ee2c061444fcedd18eeb585f45eb9a7b 100644 (file)
@@ -282,7 +282,7 @@ fn deduce_sig_from_projection(
 
         let input_tys = if is_fn {
             let arg_param_ty = trait_ref.skip_binder().substs.type_at(1);
-            let arg_param_ty = self.resolve_type_vars_if_possible(&arg_param_ty);
+            let arg_param_ty = self.resolve_vars_if_possible(&arg_param_ty);
             debug!("deduce_sig_from_projection: arg_param_ty={:?}", arg_param_ty);
 
             match arg_param_ty.sty {
@@ -295,7 +295,7 @@ fn deduce_sig_from_projection(
         };
 
         let ret_param_ty = projection.skip_binder().ty;
-        let ret_param_ty = self.resolve_type_vars_if_possible(&ret_param_ty);
+        let ret_param_ty = self.resolve_vars_if_possible(&ret_param_ty);
         debug!("deduce_sig_from_projection: ret_param_ty={:?}", ret_param_ty);
 
         let sig = self.tcx.mk_fn_sig(
index 90b2643d165bea7f2ab6e23cfacbb56ae5a53a85..d64be24f7538f548fbb0eedc44b8110bf1a623bf 100644 (file)
@@ -575,7 +575,7 @@ fn coerce_unsized(&self, source: Ty<'tcx>, target: Ty<'tcx>) -> CoerceResult<'tc
                 // Uncertain or unimplemented.
                 Ok(None) => {
                     if trait_ref.def_id() == unsize_did {
-                        let trait_ref = self.resolve_type_vars_if_possible(&trait_ref);
+                        let trait_ref = self.resolve_vars_if_possible(&trait_ref);
                         let self_ty = trait_ref.skip_binder().self_ty();
                         let unsize_ty = trait_ref.skip_binder().input_types().nth(1).unwrap();
                         debug!("coerce_unsized: ambiguous unsize case for {:?}", trait_ref);
index 724f8d886e8a76da0d311f22c9999ddaa6a3156b..c3ea9ff40a84341b6dafd36ee91dd44a58b157a8 100644 (file)
@@ -270,7 +270,11 @@ fn can_use_as_ref(
         None
     }
 
-    fn is_hir_id_from_struct_pattern_shorthand_field(&self, hir_id: hir::HirId, sp: Span) -> bool {
+    crate fn is_hir_id_from_struct_pattern_shorthand_field(
+        &self,
+        hir_id: hir::HirId,
+        sp: Span,
+    ) -> bool {
         let cm = self.sess().source_map();
         let parent_id = self.tcx.hir().get_parent_node_by_hir_id(hir_id);
         if let Some(parent) = self.tcx.hir().find_by_hir_id(parent_id) {
index 08809917ba2be89655a4cc6a66f0b84d4a32cad3..3785c3c8684b4961ba835a0636c8e9fcb1e0cf8c 100644 (file)
@@ -48,7 +48,7 @@ fn record(&mut self,
         });
 
         if let Some(yield_span) = live_across_yield {
-            let ty = self.fcx.resolve_type_vars_if_possible(&ty);
+            let ty = self.fcx.resolve_vars_if_possible(&ty);
 
             debug!("type in expr = {:?}, scope = {:?}, type = {:?}, count = {}, yield_span = {:?}",
                    expr, scope, ty, self.expr_count, yield_span);
index f93d5449e8b7892e0895cf3a93a1cb57685b540d..493486321ac2fed0e8dacfb92024984370e0617a 100644 (file)
@@ -511,7 +511,7 @@ fn convert_place_op_to_mutable(&self,
 
         let base_ty = self.tables.borrow().expr_adjustments(base_expr).last()
             .map_or_else(|| self.node_ty(expr.hir_id), |adj| adj.target);
-        let base_ty = self.resolve_type_vars_if_possible(&base_ty);
+        let base_ty = self.resolve_vars_if_possible(&base_ty);
 
         // Need to deref because overloaded place ops take self by-reference.
         let base_ty = base_ty.builtin_deref(false)
index 65bc06b65e1fca18344c2a3e45b93635954fbe85..213d53cf48254a38ca10619e1c8d2e6a0f10cc13 100644 (file)
@@ -253,7 +253,7 @@ fn lookup_probe(&self,
                     scope: ProbeScope)
                     -> probe::PickResult<'tcx> {
         let mode = probe::Mode::MethodCall;
-        let self_ty = self.resolve_type_vars_if_possible(&self_ty);
+        let self_ty = self.resolve_vars_if_possible(&self_ty);
         self.probe_for_name(span, mode, method_name, IsSuggestion(false),
                             self_ty, call_expr.hir_id, scope)
     }
index 596ce008099a68162db9a7467f02a2dba296991f..d78e013708277f15f2a1260df49e8b3f28a2dce5 100644 (file)
@@ -1338,7 +1338,7 @@ fn consider_probe(&self,
                             // and point at it rather than reporting the entire
                             // trait-ref?
                             result = ProbeResult::NoMatch;
-                            let trait_ref = self.resolve_type_vars_if_possible(&trait_ref);
+                            let trait_ref = self.resolve_vars_if_possible(&trait_ref);
                             possibly_unsatisfied_predicates.push(trait_ref);
                         }
                     }
@@ -1351,7 +1351,7 @@ fn consider_probe(&self,
 
             // Evaluate those obligations to see if they might possibly hold.
             for o in candidate_obligations.into_iter().chain(sub_obligations) {
-                let o = self.resolve_type_vars_if_possible(&o);
+                let o = self.resolve_vars_if_possible(&o);
                 if !self.predicate_may_hold(&o) {
                     result = ProbeResult::NoMatch;
                     if let &ty::Predicate::Trait(ref pred) = &o.predicate {
@@ -1364,7 +1364,7 @@ fn consider_probe(&self,
                 if let (Some(return_ty), Some(xform_ret_ty)) =
                     (self.return_type, probe.xform_ret_ty)
                 {
-                    let xform_ret_ty = self.resolve_type_vars_if_possible(&xform_ret_ty);
+                    let xform_ret_ty = self.resolve_vars_if_possible(&xform_ret_ty);
                     debug!("comparing return_ty {:?} with xform ret ty {:?}",
                            return_ty,
                            probe.xform_ret_ty);
index dfe21edee41f3fb629f05580f2b477971f21a1c5..d2fcb987bc2d853958a187c9b1778a64bb4735d9 100644 (file)
@@ -196,7 +196,7 @@ pub fn report_method_error<'b>(
             }) => {
                 let tcx = self.tcx;
 
-                let actual = self.resolve_type_vars_if_possible(&rcvr_ty);
+                let actual = self.resolve_vars_if_possible(&rcvr_ty);
                 let ty_str = self.ty_to_string(actual);
                 let is_method = mode == Mode::MethodCall;
                 let item_kind = if is_method {
index f60ad5547a278caac464c1cce5700acef8057937..c5b85d52566d3ea2a767e468fcaef4c5cf2b6b0f 100644 (file)
@@ -330,13 +330,13 @@ fn resolve(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
         match self {
             NoExpectation => NoExpectation,
             ExpectCastableToType(t) => {
-                ExpectCastableToType(fcx.resolve_type_vars_if_possible(&t))
+                ExpectCastableToType(fcx.resolve_vars_if_possible(&t))
             }
             ExpectHasType(t) => {
-                ExpectHasType(fcx.resolve_type_vars_if_possible(&t))
+                ExpectHasType(fcx.resolve_vars_if_possible(&t))
             }
             ExpectRvalueLikeUnsized(t) => {
-                ExpectRvalueLikeUnsized(fcx.resolve_type_vars_if_possible(&t))
+                ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(&t))
             }
         }
     }
@@ -2067,7 +2067,7 @@ pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
     }
 
     /// Resolves type variables in `ty` if possible. Unlike the infcx
-    /// version (resolve_type_vars_if_possible), this version will
+    /// version (resolve_vars_if_possible), this version will
     /// also select obligations if it seems useful, in an effort
     /// to get more type information.
     fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
@@ -2080,7 +2080,7 @@ fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
         }
 
         // If `ty` is a type variable, see whether we already know what it is.
-        ty = self.resolve_type_vars_if_possible(&ty);
+        ty = self.resolve_vars_if_possible(&ty);
         if !ty.has_infer_types() {
             debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
             return ty;
@@ -2091,7 +2091,7 @@ fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
         // indirect dependencies that don't seem worth tracking
         // precisely.
         self.select_obligations_where_possible(false);
-        ty = self.resolve_type_vars_if_possible(&ty);
+        ty = self.resolve_vars_if_possible(&ty);
 
         debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
         ty
@@ -2127,7 +2127,7 @@ pub fn local_ty(&self, span: Span, nid: hir::HirId) -> LocalTy<'tcx> {
     #[inline]
     pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
         debug!("write_ty({:?}, {:?}) in fcx {}",
-               id, self.resolve_type_vars_if_possible(&ty), self.tag());
+               id, self.resolve_vars_if_possible(&ty), self.tag());
         self.tables.borrow_mut().node_types_mut().insert(id, ty);
 
         if ty.references_error() {
@@ -2950,9 +2950,9 @@ fn check_argument_types(&self,
         } else {
             // is the missing argument of type `()`?
             let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
-                self.resolve_type_vars_if_possible(&expected_arg_tys[0]).is_unit()
+                self.resolve_vars_if_possible(&expected_arg_tys[0]).is_unit()
             } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
-                self.resolve_type_vars_if_possible(&fn_inputs[0]).is_unit()
+                self.resolve_vars_if_possible(&fn_inputs[0]).is_unit()
             } else {
                 false
             };
@@ -3063,7 +3063,7 @@ fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
                     }
                     ty::FnDef(..) => {
                         let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
-                        let ptr_ty = self.resolve_type_vars_if_possible(&ptr_ty);
+                        let ptr_ty = self.resolve_vars_if_possible(&ptr_ty);
                         variadic_error(tcx.sess, arg.span, arg_ty, &ptr_ty.to_string());
                     }
                     _ => {}
@@ -3253,7 +3253,7 @@ fn expected_inputs_for_expected_output(&self,
             // Record all the argument types, with the substitutions
             // produced from the above subtyping unification.
             Ok(formal_args.iter().map(|ty| {
-                self.resolve_type_vars_if_possible(ty)
+                self.resolve_vars_if_possible(ty)
             }).collect())
         }).unwrap_or_default();
         debug!("expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
@@ -4333,9 +4333,9 @@ fn check_expr_kind(
                 // Find the type of `e`. Supply hints based on the type we are casting to,
                 // if appropriate.
                 let t_cast = self.to_ty_saving_user_provided_ty(t);
-                let t_cast = self.resolve_type_vars_if_possible(&t_cast);
+                let t_cast = self.resolve_vars_if_possible(&t_cast);
                 let t_expr = self.check_expr_with_expectation(e, ExpectCastableToType(t_cast));
-                let t_cast = self.resolve_type_vars_if_possible(&t_cast);
+                let t_cast = self.resolve_vars_if_possible(&t_cast);
 
                 // Eagerly check for some obvious errors.
                 if t_expr.references_error() || t_cast.references_error() {
@@ -5010,6 +5010,10 @@ pub fn suggest_ref_or_into(
                 Applicability::MachineApplicable,
             );
         } else if !self.check_for_cast(err, expr, found, expected) {
+            let is_struct_pat_shorthand_field = self.is_hir_id_from_struct_pattern_shorthand_field(
+                expr.hir_id,
+                expr.span,
+            );
             let methods = self.get_conversion_methods(expr.span, expected, found);
             if let Ok(expr_text) = self.sess().source_map().span_to_snippet(expr.span) {
                 let mut suggestions = iter::repeat(&expr_text).zip(methods.iter())
@@ -5019,14 +5023,18 @@ pub fn suggest_ref_or_into(
                             None  // do not suggest code that is already there (#53348)
                         } else {
                             let method_call_list = [".to_vec()", ".to_string()"];
-                            if receiver.ends_with(".clone()")
+                            let sugg = if receiver.ends_with(".clone()")
                                     && method_call_list.contains(&method_call.as_str()) {
                                 let max_len = receiver.rfind(".").unwrap();
-                                Some(format!("{}{}", &receiver[..max_len], method_call))
-                            }
-                            else {
-                                Some(format!("{}{}", receiver, method_call))
-                            }
+                                format!("{}{}", &receiver[..max_len], method_call)
+                            } else {
+                                format!("{}{}", receiver, method_call)
+                            };
+                            Some(if is_struct_pat_shorthand_field {
+                                format!("{}: {}", receiver, sugg)
+                            } else {
+                                sugg
+                            })
                         }
                     }).peekable();
                 if suggestions.peek().is_some() {
index cd207478f8f6f86e5c701df44e4257a01b2d7761..0bab63582aaa1830dad70f7819b96036a1192b79 100644 (file)
@@ -618,7 +618,7 @@ pub fn check_user_unop(&self,
                 method.sig.output()
             }
             Err(()) => {
-                let actual = self.resolve_type_vars_if_possible(&operand_ty);
+                let actual = self.resolve_vars_if_possible(&operand_ty);
                 if !actual.references_error() {
                     let mut err = struct_span_err!(self.tcx.sess, ex.span, E0600,
                                      "cannot apply unary operator `{}` to type `{}`",
index 353b9ac6cc30c53e5dbe2643b9f1506c3ec6e990..62c9c7c8b1c37d9446dd2c565d5f79e620a9a2e1 100644 (file)
@@ -270,7 +270,7 @@ fn set_repeating_scope(&mut self, scope: hir::HirId) -> hir::HirId {
     /// of b will be `&<R0>.i32` and then `*b` will require that `<R0>` be bigger than the let and
     /// the `*b` expression, so we will effectively resolve `<R0>` to be the block B.
     pub fn resolve_type(&self, unresolved_ty: Ty<'tcx>) -> Ty<'tcx> {
-        self.resolve_type_vars_if_possible(&unresolved_ty)
+        self.resolve_vars_if_possible(&unresolved_ty)
     }
 
     /// Try to resolve the type for the given node.
index 13baf667808f817293c72f6f13ed44dac147ae29..a856013b719fea3708e40c6f5d60454fadb7f950 100644 (file)
@@ -138,7 +138,7 @@ fn fix_scalar_builtin_expr(&mut self, e: &hir::Expr) {
             hir::ExprKind::Unary(hir::UnNeg, ref inner)
             | hir::ExprKind::Unary(hir::UnNot, ref inner) => {
                 let inner_ty = self.fcx.node_ty(inner.hir_id);
-                let inner_ty = self.fcx.resolve_type_vars_if_possible(&inner_ty);
+                let inner_ty = self.fcx.resolve_vars_if_possible(&inner_ty);
 
                 if inner_ty.is_scalar() {
                     let mut tables = self.fcx.tables.borrow_mut();
@@ -149,10 +149,10 @@ fn fix_scalar_builtin_expr(&mut self, e: &hir::Expr) {
             hir::ExprKind::Binary(ref op, ref lhs, ref rhs)
             | hir::ExprKind::AssignOp(ref op, ref lhs, ref rhs) => {
                 let lhs_ty = self.fcx.node_ty(lhs.hir_id);
-                let lhs_ty = self.fcx.resolve_type_vars_if_possible(&lhs_ty);
+                let lhs_ty = self.fcx.resolve_vars_if_possible(&lhs_ty);
 
                 let rhs_ty = self.fcx.node_ty(rhs.hir_id);
-                let rhs_ty = self.fcx.resolve_type_vars_if_possible(&rhs_ty);
+                let rhs_ty = self.fcx.resolve_vars_if_possible(&rhs_ty);
 
                 if lhs_ty.is_scalar() && rhs_ty.is_scalar() {
                     let mut tables = self.fcx.tables.borrow_mut();
@@ -192,7 +192,7 @@ fn fix_index_builtin_expr(&mut self, e: &hir::Expr) {
             // All valid indexing looks like this; might encounter non-valid indexes at this point
             if let ty::Ref(_, base_ty, _) = tables.expr_ty_adjusted(&base).sty {
                 let index_ty = tables.expr_ty_adjusted(&index);
-                let index_ty = self.fcx.resolve_type_vars_if_possible(&index_ty);
+                let index_ty = self.fcx.resolve_vars_if_possible(&index_ty);
 
                 if base_ty.builtin_index().is_some() && index_ty == self.fcx.tcx.types.usize {
                     // Remove the method call record
index 00990a5c5b579fee2bdddb82a13e4e793232d851..3806fd0998b5e8785c16f3b1c77d44a61d4c14f4 100644 (file)
@@ -27,7 +27,7 @@
 use rustc::ty::util::Discr;
 use rustc::ty::util::IntTypeExt;
 use rustc::ty::subst::UnpackedKind;
-use rustc::ty::{self, AdtKind, ToPolyTraitRef, Ty, TyCtxt};
+use rustc::ty::{self, AdtKind, DefIdTree, ToPolyTraitRef, Ty, TyCtxt};
 use rustc::ty::{ReprOptions, ToPredicate};
 use rustc::util::captures::Captures;
 use rustc::util::nodemap::FxHashMap;
@@ -1349,65 +1349,61 @@ pub fn checked_type_of<'a, 'tcx>(
 
                     match path {
                         QPath::Resolved(_, ref path) => {
-                            let mut arg_index = 0;
-                            let mut found_const = false;
-                            for seg in &path.segments {
-                                if let Some(generic_args) = &seg.args {
-                                    let args = &generic_args.args;
-                                    for arg in args {
-                                        if let GenericArg::Const(ct) = arg {
-                                            if ct.value.hir_id == hir_id {
-                                                found_const = true;
-                                                break;
-                                            }
-                                            arg_index += 1;
-                                        }
-                                    }
-                                }
-                            }
-                            // Sanity check to make sure everything is as expected.
-                            if !found_const {
-                                if !fail {
-                                    return None;
-                                }
-                                bug!("no arg matching AnonConst in path")
-                            }
-                            match path.res {
-                                // We've encountered an `AnonConst` in some path, so we need to
-                                // figure out which generic parameter it corresponds to and return
-                                // the relevant type.
-                                Res::Def(DefKind::Struct, def_id)
-                                | Res::Def(DefKind::Union, def_id)
-                                | Res::Def(DefKind::Enum, def_id)
-                                | Res::Def(DefKind::Fn, def_id) => {
-                                    let generics = tcx.generics_of(def_id);
-                                    let mut param_index = 0;
-                                    for param in &generics.params {
-                                        if let ty::GenericParamDefKind::Const = param.kind {
-                                            if param_index == arg_index {
-                                                return Some(tcx.type_of(param.def_id));
-                                            }
-                                            param_index += 1;
-                                        }
-                                    }
-                                    // This is no generic parameter associated with the arg. This is
-                                    // probably from an extra arg where one is not needed.
-                                    return Some(tcx.types.err);
-                                }
-                                Res::Err => tcx.types.err,
-                                x => {
+                            let arg_index = path.segments.iter()
+                                .filter_map(|seg| seg.args.as_ref())
+                                .map(|generic_args| generic_args.args.as_ref())
+                                .find_map(|args| {
+                                    args.iter()
+                                        .filter(|arg| arg.is_const())
+                                        .enumerate()
+                                        .filter(|(_, arg)| arg.id() == hir_id)
+                                        .map(|(index, _)| index)
+                                        .next()
+                                })
+                                .or_else(|| {
                                     if !fail {
-                                        return None;
+                                        None
+                                    } else {
+                                        bug!("no arg matching AnonConst in path")
                                     }
+                                })?;
+
+                            // We've encountered an `AnonConst` in some path, so we need to
+                            // figure out which generic parameter it corresponds to and return
+                            // the relevant type.
+                            let generics = match path.res {
+                                Res::Def(DefKind::Ctor(..), def_id) =>
+                                    tcx.generics_of(tcx.parent(def_id).unwrap()),
+                                Res::Def(_, def_id) =>
+                                    tcx.generics_of(def_id),
+                                Res::Err =>
+                                    return Some(tcx.types.err),
+                                _ if !fail =>
+                                    return None,
+                                x => {
                                     tcx.sess.delay_span_bug(
                                         DUMMY_SP,
                                         &format!(
                                             "unexpected const parent path def {:?}", x
                                         ),
                                     );
-                                    tcx.types.err
+                                    return Some(tcx.types.err);
                                 }
-                            }
+                            };
+
+                            generics.params.iter()
+                                .filter(|param| {
+                                    if let ty::GenericParamDefKind::Const = param.kind {
+                                        true
+                                    } else {
+                                        false
+                                    }
+                                })
+                                .nth(arg_index)
+                                .map(|param| tcx.type_of(param.def_id))
+                                // This is no generic parameter associated with the arg. This is
+                                // probably from an extra arg where one is not needed.
+                                .unwrap_or(tcx.types.err)
                         }
                         x => {
                             if !fail {
index 6cedab412df924ddcfcdf49e8a27005dcb6214cd..b75212d606fa5a63894b23c5d542dea00fe2e0c5 100644 (file)
@@ -9,7 +9,7 @@ name = "rustdoc"
 path = "lib.rs"
 
 [dependencies]
-pulldown-cmark = { version = "0.4.1", default-features = false }
+pulldown-cmark = { version = "0.5.2", default-features = false }
 minifier = "0.0.30"
 tempfile = "3"
 parking_lot = "0.7"
index 4ee63a4c9703b6c310491d0513193aee21b31ac9..e68ad6a7c3b4bc375c6e5a8f7db6c0298cd67aaa 100644 (file)
@@ -3145,10 +3145,7 @@ impl<'tcx> Clean<Constant> for ty::Const<'tcx> {
     fn clean(&self, cx: &DocContext<'_>) -> Constant {
         Constant {
             type_: self.ty.clean(cx),
-            expr: match self.val {
-                ConstValue::Param(ty::ParamConst { name, .. }) => format!("{}", name),
-                e => format!("{:?}", e), // FIXME generic consts with expressions
-            },
+            expr: format!("{}", self),
         }
     }
 }
index 12d10254c4d09ecf7574ca63ed0d75643dd7c393..334b83156507654dc638765b652ff1d942cb3a42 100644 (file)
@@ -351,9 +351,11 @@ fn next(&mut self) -> Option<Self::Item> {
         if let Some(Event::Start(Tag::Header(level))) = event {
             let mut id = String::new();
             for event in &mut self.inner {
-                match event {
+                match &event {
                     Event::End(Tag::Header(..)) => break,
-                    Event::Text(ref text) => id.extend(text.chars().filter_map(slugify)),
+                    Event::Text(text) | Event::Code(text) => {
+                        id.extend(text.chars().filter_map(slugify));
+                    }
                     _ => {},
                 }
                 self.buf.push_back(event);
@@ -402,7 +404,6 @@ fn check_if_allowed_tag(t: &Tag<'_>) -> bool {
         | Tag::Item
         | Tag::Emphasis
         | Tag::Strong
-        | Tag::Code
         | Tag::Link(..)
         | Tag::BlockQuote => true,
         _ => false,
@@ -790,9 +791,8 @@ fn next(&mut self) -> Option<String> {
             let next_event = next_event.unwrap();
             let (ret, is_in) = match next_event {
                 Event::Start(Tag::Paragraph) => (None, 1),
-                Event::Start(Tag::Code) => (Some("`".to_owned()), 1),
-                Event::End(Tag::Code) => (Some("`".to_owned()), -1),
                 Event::Start(Tag::Header(_)) => (None, 1),
+                Event::Code(code) => (Some(format!("`{}`", code)), 0),
                 Event::Text(ref s) if self.is_in > 0 => (Some(s.as_ref().to_owned()), 0),
                 Event::End(Tag::Paragraph) | Event::End(Tag::Header(_)) => (None, -1),
                 _ => (None, 0),
index 1b6460f52515419e8ec73753dd04b5dfaae0e415..5bce5d6ba5de1b264289dda9f60fa77cc50d22fb 100644 (file)
@@ -17,7 +17,7 @@
 use std::io;
 use std::panic::{self, AssertUnwindSafe};
 use std::path::PathBuf;
-use std::process::Command;
+use std::process::{self, Command};
 use std::str;
 use std::sync::{Arc, Mutex};
 use syntax::symbol::sym;
@@ -160,13 +160,45 @@ fn scrape_test_config(krate: &::rustc::hir::Crate) -> TestOptions {
     opts
 }
 
-fn run_test(test: &str, cratename: &str, filename: &FileName, line: usize,
-            cfgs: Vec<String>, libs: Vec<SearchPath>,
-            cg: CodegenOptions, externs: Externs,
-            should_panic: bool, no_run: bool, as_test_harness: bool,
-            compile_fail: bool, mut error_codes: Vec<String>, opts: &TestOptions,
-            maybe_sysroot: Option<PathBuf>, linker: Option<PathBuf>, edition: Edition,
-            persist_doctests: Option<PathBuf>) {
+/// Documentation test failure modes.
+enum TestFailure {
+    /// The test failed to compile.
+    CompileError,
+    /// The test is marked `compile_fail` but compiled successfully.
+    UnexpectedCompilePass,
+    /// The test failed to compile (as expected) but the compiler output did not contain all
+    /// expected error codes.
+    MissingErrorCodes(Vec<String>),
+    /// The test binary was unable to be executed.
+    ExecutionError(io::Error),
+    /// The test binary exited with a non-zero exit code.
+    ///
+    /// This typically means an assertion in the test failed or another form of panic occurred.
+    ExecutionFailure(process::Output),
+    /// The test is marked `should_panic` but the test binary executed successfully.
+    UnexpectedRunPass,
+}
+
+fn run_test(
+    test: &str,
+    cratename: &str,
+    filename: &FileName,
+    line: usize,
+    cfgs: Vec<String>,
+    libs: Vec<SearchPath>,
+    cg: CodegenOptions,
+    externs: Externs,
+    should_panic: bool,
+    no_run: bool,
+    as_test_harness: bool,
+    compile_fail: bool,
+    mut error_codes: Vec<String>,
+    opts: &TestOptions,
+    maybe_sysroot: Option<PathBuf>,
+    linker: Option<PathBuf>,
+    edition: Edition,
+    persist_doctests: Option<PathBuf>,
+) -> Result<(), TestFailure> {
     let (test, line_offset) = match panic::catch_unwind(|| {
         make_test(test, Some(cratename), as_test_harness, opts, edition)
     }) {
@@ -307,44 +339,43 @@ fn path(&self) -> &std::path::Path {
 
     match (compile_result, compile_fail) {
         (Ok(()), true) => {
-            panic!("test compiled while it wasn't supposed to")
+            return Err(TestFailure::UnexpectedCompilePass);
         }
         (Ok(()), false) => {}
         (Err(_), true) => {
-            if error_codes.len() > 0 {
+            if !error_codes.is_empty() {
                 let out = String::from_utf8(data.lock().unwrap().to_vec()).unwrap();
                 error_codes.retain(|err| !out.contains(err));
+
+                if !error_codes.is_empty() {
+                    return Err(TestFailure::MissingErrorCodes(error_codes));
+                }
             }
         }
         (Err(_), false) => {
-            panic!("couldn't compile the test")
+            return Err(TestFailure::CompileError);
         }
     }
 
-    if error_codes.len() > 0 {
-        panic!("Some expected error codes were not found: {:?}", error_codes);
+    if no_run {
+        return Ok(());
     }
 
-    if no_run { return }
-
     // Run the code!
     let mut cmd = Command::new(output_file);
 
     match cmd.output() {
-        Err(e) => panic!("couldn't run the test: {}{}", e,
-                        if e.kind() == io::ErrorKind::PermissionDenied {
-                            " - maybe your tempdir is mounted with noexec?"
-                        } else { "" }),
+        Err(e) => return Err(TestFailure::ExecutionError(e)),
         Ok(out) => {
             if should_panic && out.status.success() {
-                panic!("test executable succeeded when it should have failed");
+                return Err(TestFailure::UnexpectedRunPass);
             } else if !should_panic && !out.status.success() {
-                panic!("test executable failed:\n{}\n{}\n",
-                       str::from_utf8(&out.stdout).unwrap_or(""),
-                       str::from_utf8(&out.stderr).unwrap_or(""));
+                return Err(TestFailure::ExecutionFailure(out));
             }
         }
     }
+
+    Ok(())
 }
 
 /// Transforms a test into code that can be compiled into a Rust binary, and returns the number of
@@ -716,7 +747,7 @@ fn add_test(&mut self, test: String, config: LangString, line: usize) {
                 allow_fail: config.allow_fail,
             },
             testfn: testing::DynTestFn(box move || {
-                run_test(
+                let res = run_test(
                     &test,
                     &cratename,
                     &filename,
@@ -735,7 +766,65 @@ fn add_test(&mut self, test: String, config: LangString, line: usize) {
                     linker,
                     edition,
                     persist_doctests
-                )
+                );
+
+                if let Err(err) = res {
+                    match err {
+                        TestFailure::CompileError => {
+                            eprint!("Couldn't compile the test.");
+                        }
+                        TestFailure::UnexpectedCompilePass => {
+                            eprint!("Test compiled successfully, but it's marked `compile_fail`.");
+                        }
+                        TestFailure::UnexpectedRunPass => {
+                            eprint!("Test executable succeeded, but it's marked `should_panic`.");
+                        }
+                        TestFailure::MissingErrorCodes(codes) => {
+                            eprint!("Some expected error codes were not found: {:?}", codes);
+                        }
+                        TestFailure::ExecutionError(err) => {
+                            eprint!("Couldn't run the test: {}", err);
+                            if err.kind() == io::ErrorKind::PermissionDenied {
+                                eprint!(" - maybe your tempdir is mounted with noexec?");
+                            }
+                        }
+                        TestFailure::ExecutionFailure(out) => {
+                            let reason = if let Some(code) = out.status.code() {
+                                format!("exit code {}", code)
+                            } else {
+                                String::from("terminated by signal")
+                            };
+
+                            eprintln!("Test executable failed ({}).", reason);
+
+                            // FIXME(#12309): An unfortunate side-effect of capturing the test
+                            // executable's output is that the relative ordering between the test's
+                            // stdout and stderr is lost. However, this is better than the
+                            // alternative: if the test executable inherited the parent's I/O
+                            // handles the output wouldn't be captured at all, even on success.
+                            //
+                            // The ordering could be preserved if the test process' stderr was
+                            // redirected to stdout, but that functionality does not exist in the
+                            // standard library, so it may not be portable enough.
+                            let stdout = str::from_utf8(&out.stdout).unwrap_or_default();
+                            let stderr = str::from_utf8(&out.stderr).unwrap_or_default();
+
+                            if !stdout.is_empty() || !stderr.is_empty() {
+                                eprintln!();
+
+                                if !stdout.is_empty() {
+                                    eprintln!("stdout:\n{}", stdout);
+                                }
+
+                                if !stderr.is_empty() {
+                                    eprintln!("stderr:\n{}", stderr);
+                                }
+                            }
+                        }
+                    }
+
+                    panic::resume_unwind(box ());
+                }
             }),
         });
     }
index aeb822fa99e66a6fd1920de1c16aea4203ff4677..c8978a94fcda46507e007c3cdf58fc0bfaadc453 100644 (file)
@@ -94,7 +94,7 @@ fn description(&self) -> &str {
     ///         "I'm the superhero of errors"
     ///     }
     ///
-    ///     fn cause(&self) -> Option<&Error> {
+    ///     fn cause(&self) -> Option<&dyn Error> {
     ///         Some(&self.side)
     ///     }
     /// }
@@ -244,7 +244,7 @@ impl<'a, E: Error + 'a> From<E> for Box<dyn Error + 'a> {
     ///
     /// let an_error = AnError;
     /// assert!(0 == mem::size_of_val(&an_error));
-    /// let a_boxed_error = Box::<Error>::from(an_error);
+    /// let a_boxed_error = Box::<dyn Error>::from(an_error);
     /// assert!(mem::size_of::<Box<dyn Error>>() == mem::size_of_val(&a_boxed_error))
     /// ```
     fn from(err: E) -> Box<dyn Error + 'a> {
@@ -287,7 +287,7 @@ impl<'a, E: Error + Send + Sync + 'a> From<E> for Box<dyn Error + Send + Sync +
     ///
     /// let an_error = AnError;
     /// assert!(0 == mem::size_of_val(&an_error));
-    /// let a_boxed_error = Box::<Error + Send + Sync>::from(an_error);
+    /// let a_boxed_error = Box::<dyn Error + Send + Sync>::from(an_error);
     /// assert!(
     ///     mem::size_of::<Box<dyn Error + Send + Sync>>() == mem::size_of_val(&a_boxed_error))
     /// ```
@@ -309,7 +309,7 @@ impl From<String> for Box<dyn Error + Send + Sync> {
     /// use std::mem;
     ///
     /// let a_string_error = "a string error".to_string();
-    /// let a_boxed_error = Box::<Error + Send + Sync>::from(a_string_error);
+    /// let a_boxed_error = Box::<dyn Error + Send + Sync>::from(a_string_error);
     /// assert!(
     ///     mem::size_of::<Box<dyn Error + Send + Sync>>() == mem::size_of_val(&a_boxed_error))
     /// ```
@@ -344,7 +344,7 @@ impl From<String> for Box<dyn Error> {
     /// use std::mem;
     ///
     /// let a_string_error = "a string error".to_string();
-    /// let a_boxed_error = Box::<Error>::from(a_string_error);
+    /// let a_boxed_error = Box::<dyn Error>::from(a_string_error);
     /// assert!(mem::size_of::<Box<dyn Error>>() == mem::size_of_val(&a_boxed_error))
     /// ```
     fn from(str_err: String) -> Box<dyn Error> {
@@ -367,7 +367,7 @@ impl<'a> From<&str> for Box<dyn Error + Send + Sync + 'a> {
     /// use std::mem;
     ///
     /// let a_str_error = "a str error";
-    /// let a_boxed_error = Box::<Error + Send + Sync>::from(a_str_error);
+    /// let a_boxed_error = Box::<dyn Error + Send + Sync>::from(a_str_error);
     /// assert!(
     ///     mem::size_of::<Box<dyn Error + Send + Sync>>() == mem::size_of_val(&a_boxed_error))
     /// ```
@@ -389,7 +389,7 @@ impl From<&str> for Box<dyn Error> {
     /// use std::mem;
     ///
     /// let a_str_error = "a str error";
-    /// let a_boxed_error = Box::<Error>::from(a_str_error);
+    /// let a_boxed_error = Box::<dyn Error>::from(a_str_error);
     /// assert!(mem::size_of::<Box<dyn Error>>() == mem::size_of_val(&a_boxed_error))
     /// ```
     fn from(err: &str) -> Box<dyn Error> {
@@ -412,7 +412,7 @@ impl<'a, 'b> From<Cow<'b, str>> for Box<dyn Error + Send + Sync + 'a> {
     /// use std::borrow::Cow;
     ///
     /// let a_cow_str_error = Cow::from("a str error");
-    /// let a_boxed_error = Box::<Error + Send + Sync>::from(a_cow_str_error);
+    /// let a_boxed_error = Box::<dyn Error + Send + Sync>::from(a_cow_str_error);
     /// assert!(
     ///     mem::size_of::<Box<dyn Error + Send + Sync>>() == mem::size_of_val(&a_boxed_error))
     /// ```
@@ -436,7 +436,7 @@ impl<'a> From<Cow<'a, str>> for Box<dyn Error> {
     /// use std::borrow::Cow;
     ///
     /// let a_cow_str_error = Cow::from("a str error");
-    /// let a_boxed_error = Box::<Error>::from(a_cow_str_error);
+    /// let a_boxed_error = Box::<dyn Error>::from(a_cow_str_error);
     /// assert!(mem::size_of::<Box<dyn Error>>() == mem::size_of_val(&a_boxed_error))
     /// ```
     fn from(err: Cow<'a, str>) -> Box<dyn Error> {
index 616b5eb836ffd6c8c20163cd752790ade30ef170..d41b3a3a1233f563a097edf4775a1858f0ab43b8 100644 (file)
@@ -1976,7 +1976,7 @@ pub fn remove_dir_all<P: AsRef<Path>>(path: P) -> io::Result<()> {
 /// use std::path::Path;
 ///
 /// // one possible implementation of walking a directory only visiting files
-/// fn visit_dirs(dir: &Path, cb: &Fn(&DirEntry)) -> io::Result<()> {
+/// fn visit_dirs(dir: &Path, cb: &dyn Fn(&DirEntry)) -> io::Result<()> {
 ///     if dir.is_dir() {
 ///         for entry in fs::read_dir(dir)? {
 ///             let entry = entry?;
index e309f81192cf3ffb7322bd4540da7beb5c384461..aaf628e6c260fea2ec16fcbe7cc948d20fa00a2b 100644 (file)
@@ -158,7 +158,6 @@ pub fn get_mut(&mut self) -> &mut R { &mut self.inner }
     /// # Examples
     ///
     /// ```no_run
-    /// # #![feature(bufreader_buffer)]
     /// use std::io::{BufReader, BufRead};
     /// use std::fs::File;
     ///
@@ -173,7 +172,7 @@ pub fn get_mut(&mut self) -> &mut R { &mut self.inner }
     ///     Ok(())
     /// }
     /// ```
-    #[unstable(feature = "bufreader_buffer", issue = "45323")]
+    #[stable(feature = "bufreader_buffer", since = "1.37.0")]
     pub fn buffer(&self) -> &[u8] {
         &self.buf[self.pos..self.cap]
     }
@@ -552,7 +551,6 @@ pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() }
     /// # Examples
     ///
     /// ```no_run
-    /// # #![feature(bufreader_buffer)]
     /// use std::io::BufWriter;
     /// use std::net::TcpStream;
     ///
@@ -561,7 +559,7 @@ pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() }
     /// // See how many bytes are currently buffered
     /// let bytes_buffered = buf_writer.buffer().len();
     /// ```
-    #[unstable(feature = "bufreader_buffer", issue = "45323")]
+    #[stable(feature = "bufreader_buffer", since = "1.37.0")]
     pub fn buffer(&self) -> &[u8] {
         &self.buf
     }
@@ -1162,6 +1160,41 @@ fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> {
         assert_eq!(reader.get_ref().pos, expected);
     }
 
+    #[test]
+    fn test_buffered_reader_seek_underflow_discard_buffer_between_seeks() {
+        // gimmick reader that returns Err after first seek
+        struct ErrAfterFirstSeekReader {
+            first_seek: bool,
+        }
+        impl Read for ErrAfterFirstSeekReader {
+            fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
+                for x in &mut *buf {
+                    *x = 0;
+                }
+                Ok(buf.len())
+            }
+        }
+        impl Seek for ErrAfterFirstSeekReader {
+            fn seek(&mut self, _: SeekFrom) -> io::Result<u64> {
+                if self.first_seek {
+                    self.first_seek = false;
+                    Ok(0)
+                } else {
+                    Err(io::Error::new(io::ErrorKind::Other, "oh no!"))
+                }
+            }
+        }
+
+        let mut reader = BufReader::with_capacity(5, ErrAfterFirstSeekReader { first_seek: true });
+        assert_eq!(reader.fill_buf().ok(), Some(&[0, 0, 0, 0, 0][..]));
+
+        // The following seek will require two underlying seeks.  The first will
+        // succeed but the second will fail.  This should still invalidate the
+        // buffer.
+        assert!(reader.seek(SeekFrom::Current(i64::min_value())).is_err());
+        assert_eq!(reader.buffer().len(), 0);
+    }
+
     #[test]
     fn test_buffered_writer() {
         let inner = Vec::new();
index 53b9dd68f734f3053899718e1a5738c4a666e7cd..4ddc1f09a319bab3c02a2ce518a6e6b3e6d00d55 100644 (file)
@@ -27,7 +27,7 @@ pub trait PermissionsExt {
     ///     let metadata = f.metadata()?;
     ///     let permissions = metadata.permissions();
     ///
-    ///     println!("permissions: {}", permissions.mode());
+    ///     println!("permissions: {:o}", permissions.mode());
     ///     Ok(())
     /// }
     /// ```
index d9baac993c42c9419bef73c3d5d9dd54984cd908..c033c60cbe9e1b8ce15a370c8bb142b50c99131c 100644 (file)
@@ -238,7 +238,7 @@ pub trait PermissionsExt {
     ///     let metadata = f.metadata()?;
     ///     let permissions = metadata.permissions();
     ///
-    ///     println!("permissions: {}", permissions.mode());
+    ///     println!("permissions: {:o}", permissions.mode());
     ///     Ok(()) }
     /// ```
     #[stable(feature = "fs_ext", since = "1.1.0")]
index 8a210db91858ebb046da7023e668b6886d1478f8..e2171a84e23002b154160472fa8d3dd7ec6eb447 100644 (file)
@@ -727,6 +727,11 @@ fn find_width_of_character_at_span(&self, sp: Span, forwards: bool) -> u32 {
         debug!("find_width_of_character_at_span: local_begin=`{:?}`, local_end=`{:?}`",
                local_begin, local_end);
 
+        if local_begin.sf.start_pos != local_end.sf.start_pos {
+            debug!("find_width_of_character_at_span: begin and end are in different files");
+            return 1;
+        }
+
         let start_index = local_begin.pos.to_usize();
         let end_index = local_end.pos.to_usize();
         debug!("find_width_of_character_at_span: start_index=`{:?}`, end_index=`{:?}`",
index 8493ef565d888f32730c00c72f543ade5957bdf7..e94365058862a11b0e874fbc6da91bcf0008c32b 100644 (file)
@@ -1,20 +1,23 @@
 // Test that `-Zpgo-gen` creates expected instrumentation artifacts in LLVM IR.
+// Compiling with `-Cpanic=abort` because PGO+unwinding isn't supported on all platforms.
 
 // needs-profiler-support
-// compile-flags: -Z pgo-gen -Ccodegen-units=1
+// compile-flags: -Z pgo-gen -Ccodegen-units=1 -Cpanic=abort
 
 // CHECK: @__llvm_profile_raw_version =
 // CHECK: @__profc_{{.*}}pgo_instrumentation{{.*}}some_function{{.*}} = private global
 // CHECK: @__profd_{{.*}}pgo_instrumentation{{.*}}some_function{{.*}} = private global
-// CHECK: @__profc_{{.*}}pgo_instrumentation{{.*}}main{{.*}} = private global
-// CHECK: @__profd_{{.*}}pgo_instrumentation{{.*}}main{{.*}} = private global
+// CHECK: @__profc_{{.*}}pgo_instrumentation{{.*}}some_other_function{{.*}} = private global
+// CHECK: @__profd_{{.*}}pgo_instrumentation{{.*}}some_other_function{{.*}} = private global
 // CHECK: @__llvm_profile_filename = {{.*}}"default_%m.profraw\00"{{.*}}
 
+#![crate_type="lib"]
+
 #[inline(never)]
 fn some_function() {
 
 }
 
-fn main() {
+pub fn some_other_function() {
     some_function();
 }
index b8a0c4846abebb431e5cb232fef8f013e165f096..2912c4ead7a0a1cb0d0d10eb6ebe699281203289 100644 (file)
@@ -5,7 +5,7 @@
 trait Hierarchy {
     type Value;
     type ChildKey;
-    type Children = Index<Self::ChildKey, Output=Hierarchy>;
+    type Children = dyn Index<Self::ChildKey, Output=dyn Hierarchy>;
     //~^ ERROR: the value of the associated types `Value` (from the trait `Hierarchy`), `ChildKey`
 
     fn data(&self) -> Option<(Self::Value, Self::Children)>;
index 48181bcbdc6d363f636140483c79c2eafcd9b267..56f31434adee4a17845a53459e6d7fa1003abf75 100644 (file)
@@ -2,7 +2,17 @@
 
 -include ../tools.mk
 
+COMPILE_FLAGS=-Copt-level=3 -Clto=fat -Z pgo-gen="$(TMPDIR)"
+
+# LLVM doesn't yet support instrumenting binaries that use unwinding on MSVC:
+# https://github.com/rust-lang/rust/issues/61002
+#
+# Things work fine with -Cpanic=abort though.
+ifdef IS_MSVC
+COMPILE_FLAGS+= -Cpanic=abort
+endif
+
 all:
-       $(RUSTC) -Copt-level=3 -Clto=fat -Z pgo-gen="$(TMPDIR)" test.rs
+       $(RUSTC) $(COMPILE_FLAGS) test.rs
        $(call RUN,test) || exit 1
        [ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
index 20977edb88e87ad8b2467863c04bdff8a1cb4493..bb86160d2dfdf76c13081aa0de0c6e66208b29fa 100644 (file)
@@ -2,8 +2,18 @@
 
 -include ../tools.mk
 
+COMPILE_FLAGS=-O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)"
+
+# LLVM doesn't yet support instrumenting binaries that use unwinding on MSVC:
+# https://github.com/rust-lang/rust/issues/61002
+#
+# Things work fine with -Cpanic=abort though.
+ifdef IS_MSVC
+COMPILE_FLAGS+= -Cpanic=abort
+endif
+
 all:
-       $(RUSTC) -O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)" --emit=llvm-ir test.rs
+       $(RUSTC) $(COMPILE_FLAGS) --emit=llvm-ir test.rs
        # We expect symbols starting with "__llvm_profile_".
        $(CGREP) "__llvm_profile_" < $(TMPDIR)/test.ll
        # We do NOT expect the "__imp_" version of these symbols.
index ce44c10a7c2d2c5e8f50724fb7ba8db6dccb83a0..f0ab3b7d13d27444337c7d3ce385fa7828435533 100644 (file)
@@ -2,7 +2,17 @@
 
 -include ../tools.mk
 
+COMPILE_FLAGS=-g -Z pgo-gen="$(TMPDIR)"
+
+# LLVM doesn't yet support instrumenting binaries that use unwinding on MSVC:
+# https://github.com/rust-lang/rust/issues/61002
+#
+# Things work fine with -Cpanic=abort though.
+ifdef IS_MSVC
+COMPILE_FLAGS+= -Cpanic=abort
+endif
+
 all:
-       $(RUSTC) -g -Z pgo-gen="$(TMPDIR)" test.rs
+       $(RUSTC) $(COMPILE_FLAGS) test.rs
        $(call RUN,test) || exit 1
        [ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
index ababd45d33e2e9de7dca982ee204a384cfa87dc4..72c3c34ee3741675510c54f0c7cd0b611762e4f7 100644 (file)
@@ -16,7 +16,7 @@
 COMMON_FLAGS=-Copt-level=s -Ccodegen-units=1
 
 # LLVM doesn't support instrumenting binaries that use SEH:
-# https://bugs.llvm.org/show_bug.cgi?id=41279
+# https://github.com/rust-lang/rust/issues/61002
 #
 # Things work fine with -Cpanic=abort though.
 ifdef IS_MSVC
index 144c5ba10cccf14c316a0cc2649b984461938ea8..5f10f2aa3b0f419836efb67d7a4f23bbdc5c5def 100644 (file)
@@ -2,14 +2,7 @@
 
 # Checks that all the targets returned by `rustc --print target-list` are valid
 # target specifications
-# TODO remove the '*ios*' case when rust-lang/rust#29812 is fixed
 all:
        for target in $(shell $(BARE_RUSTC) --print target-list); do \
-               case $$target in \
-                       *ios*) \
-                               ;; \
-                       *) \
-                               $(BARE_RUSTC) --target $$target --print sysroot \
-                               ;; \
-                       esac \
+               $(BARE_RUSTC) --target $$target --print sysroot; \
        done
index 659de9cf6d51b616ba5597ff428dfd4c23b9a024..2e2a77b92ca5379c95d35bfa2bc2cff787c16b26 100644 (file)
@@ -62,7 +62,7 @@ fn make_x() -> P<Expr> {
 /// Iterate over exprs of depth up to `depth`. The goal is to explore all "interesting"
 /// combinations of expression nesting. For example, we explore combinations using `if`, but not
 /// `while` or `match`, since those should print and parse in much the same way as `if`.
-fn iter_exprs(depth: usize, f: &mut FnMut(P<Expr>)) {
+fn iter_exprs(depth: usize, f: &mut dyn FnMut(P<Expr>)) {
     if depth == 0 {
         f(make_x());
         return;
index badd095d0ae12884ea44682093507dd5372ba482..7e6ee60e5194cb93ee7450e9d5547ab0785fbf5f 100644 (file)
@@ -22,11 +22,11 @@ fn f(&self) -> (A, u16) {
     }
 }
 
-fn f<A:Clone + 'static>(a: A, b: u16) -> Box<Invokable<A>+'static> {
+fn f<A:Clone + 'static>(a: A, b: u16) -> Box<dyn Invokable<A>+'static> {
     box Invoker {
         a: a,
         b: b,
-    } as (Box<Invokable<A>+'static>)
+    } as (Box<dyn Invokable<A>+'static>)
 }
 
 pub fn main() {
index 5f86888aef02061d4033c97f7c6b339ad6ab059f..96ba2ee3b62b8c12ffd2875d792a988e67cfd271 100644 (file)
@@ -1,7 +1,7 @@
 // run-pass
 #![feature(box_syntax)]
 
-fn pairwise_sub(mut t: Box<DoubleEndedIterator<Item=isize>>) -> isize {
+fn pairwise_sub(mut t: Box<dyn DoubleEndedIterator<Item=isize>>) -> isize {
     let mut result = 0;
     loop {
         let front = t.next();
index 0f3dfe338a33c807aebed170e0079ed2d985868e..c202c376c5fe600e751a3ece74b110ea78b58517 100644 (file)
@@ -15,7 +15,7 @@ impl Foo for char {
     fn boo(&self) -> Bar { Bar }
 }
 
-fn baz(x: &Foo<A=Bar>) -> Bar {
+fn baz(x: &dyn Foo<A=Bar>) -> Bar {
     x.boo()
 }
 
index 0dc32f2fd94ec88b8fb0e92e07fc1cff7cc0c55f..eec95a141f5cf2e59a09712e582f2a2b1b4a7955 100644 (file)
@@ -19,7 +19,7 @@ fn dummy(&self) { }
 
 pub trait Publisher<'a> {
     type Output;
-    fn subscribe(&mut self, _: Box<Subscriber<Input=Self::Output> + 'a>);
+    fn subscribe(&mut self, _: Box<dyn Subscriber<Input=Self::Output> + 'a>);
 }
 
 pub trait Processor<'a> : Subscriber + Publisher<'a> { }
@@ -27,12 +27,12 @@ pub trait Processor<'a> : Subscriber + Publisher<'a> { }
 impl<'a, P> Processor<'a> for P where P : Subscriber + Publisher<'a> { }
 
 struct MyStruct<'a> {
-    sub: Box<Subscriber<Input=u64> + 'a>
+    sub: Box<dyn Subscriber<Input=u64> + 'a>
 }
 
 impl<'a> Publisher<'a> for MyStruct<'a> {
     type Output = u64;
-    fn subscribe(&mut self, t : Box<Subscriber<Input=u64> + 'a>) {
+    fn subscribe(&mut self, t : Box<dyn Subscriber<Input=u64> + 'a>) {
         self.sub = t;
     }
 }
index 0a54db7f5cd8a421ce083bf363d69037fdcaea22..fadb0784e75257eb35354fe9b7c7885ed67b710b 100644 (file)
@@ -11,6 +11,6 @@ fn double(self: Box<usize>) -> usize { *self * 2 }
 }
 
 pub fn main() {
-    let x: Box<_> = box (box 3usize as Box<double>);
+    let x: Box<_> = box (box 3usize as Box<dyn double>);
     assert_eq!(x.double(), 6);
 }
index 9721b08233e39db8db258979500b564892a527bd..8a6dfe76d6065c9c204c1dc3bfb18522a02d6b16 100644 (file)
@@ -12,7 +12,7 @@
 fn main() {
     trait T { fn foo(&self) {} }
 
-    fn f<'a, V: T>(v: &'a V) -> &'a T {
-        v as &'a T
+    fn f<'a, V: T>(v: &'a V) -> &'a dyn T {
+        v as &'a dyn T
     }
 }
index e53ab7919228b3de941321ceca7bdef87f0346be..a27dd9eef52ec31f351258d92418625ea7150fe5 100644 (file)
@@ -15,9 +15,9 @@ impl<T> Foo<T> for () {}
 impl Foo<u32> for u32 { fn foo(&self, _: u32) -> u32 { self+43 } }
 impl Bar for () {}
 
-unsafe fn round_trip_and_call<'a>(t: *const (Foo<u32>+'a)) -> u32 {
-    let foo_e : *const Foo<u16> = t as *const _;
-    let r_1 = foo_e as *mut Foo<u32>;
+unsafe fn round_trip_and_call<'a>(t: *const (dyn Foo<u32>+'a)) -> u32 {
+    let foo_e : *const dyn Foo<u16> = t as *const _;
+    let r_1 = foo_e as *mut dyn Foo<u32>;
 
     (&*r_1).foo(0)
 }
@@ -38,8 +38,8 @@ fn tuple_i32_to_u32<T:?Sized>(u: *const (i32, T)) -> *const (u32, T) {
 
 fn main() {
     let x = 4u32;
-    let y : &Foo<u32> = &x;
-    let fl = unsafe { round_trip_and_call(y as *const Foo<u32>) };
+    let y : &dyn Foo<u32> = &x;
+    let fl = unsafe { round_trip_and_call(y as *const dyn Foo<u32>) };
     assert_eq!(fl, (43+4));
 
     let s = FooS([0,1,2]);
index 324860e53e198f5809932e88113e0759a2685ac3..017b63c737493d5990e2756be7badd651346a3e3 100644 (file)
@@ -25,8 +25,8 @@ fn main()
     // coercion-cast
     let mut it = vec![137].into_iter();
     let itr: &mut vec::IntoIter<u32> = &mut it;
-    assert_eq!((itr as &mut Iterator<Item=u32>).next(), Some(137));
-    assert_eq!((itr as &mut Iterator<Item=u32>).next(), None);
+    assert_eq!((itr as &mut dyn Iterator<Item=u32>).next(), Some(137));
+    assert_eq!((itr as &mut dyn Iterator<Item=u32>).next(), None);
 
     assert_eq!(Some(4u32) as Option<u32>, Some(4u32));
     assert_eq!((1u32,2u32) as (u32,u32), (1,2));
index 2ae0b6c7d3de5b1210f9362ff960283638324d9d..0eead0194efa2999a4d5068844b1020dc52fd7f7 100644 (file)
@@ -24,11 +24,11 @@ fn f(&self) -> (A, u16) {
     }
 }
 
-fn f<A:Clone + 'static>(a: A, b: u16) -> Box<Invokable<A>+'static> {
+fn f<A:Clone + 'static>(a: A, b: u16) -> Box<dyn Invokable<A>+'static> {
     box Invoker {
         a: a,
         b: b,
-    } as (Box<Invokable<A>+'static>)
+    } as (Box<dyn Invokable<A>+'static>)
 }
 
 pub fn main() {
index 4e2d7ac60865374909a44090b6e9a1426eddfa02..26f53a9c18213b2f47894fc579632742d0fe956c 100644 (file)
@@ -1,4 +1,4 @@
 fn main() {
-    assert_eq!((ToString::to_string as fn(&(ToString+'static)) -> String)(&"foo"),
+    assert_eq!((ToString::to_string as fn(&(dyn ToString+'static)) -> String)(&"foo"),
         String::from("foo"));
 }
index a7e80afbf767ccb5fe72aaddf7cb36f142d8039e..b44aa6ab37760dfbd2c6ad529910624325b0c438 100644 (file)
@@ -12,16 +12,16 @@ pub fn main() {
     let _: Box<[isize]> = Box::new({ [1, 2, 3] });
     let _: Box<[isize]> = Box::new(if true { [1, 2, 3] } else { [1, 3, 4] });
     let _: Box<[isize]> = Box::new(match true { true => [1, 2, 3], false => [1, 3, 4] });
-    let _: Box<Fn(isize) -> _> = 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 _: Box<dyn Fn(isize) -> _> = Box::new({ |x| (x as u8) });
+    let _: Box<dyn Debug> = Box::new(if true { false } else { true });
+    let _: Box<dyn Debug> = Box::new(match true { true => 'a', false => 'b' });
 
     let _: &[isize] = &{ [1, 2, 3] };
     let _: &[isize] = &if true { [1, 2, 3] } else { [1, 3, 4] };
     let _: &[isize] = &match true { true => [1, 2, 3], false => [1, 3, 4] };
-    let _: &Fn(isize) -> _ = &{ |x| (x as u8) };
-    let _: &Debug = &if true { false } else { true };
-    let _: &Debug = &match true { true => 'a', false => 'b' };
+    let _: &dyn Fn(isize) -> _ = &{ |x| (x as u8) };
+    let _: &dyn Debug = &if true { false } else { true };
+    let _: &dyn Debug = &match true { true => 'a', false => 'b' };
 
     let _: &str = &{ String::new() };
     let _: &str = &if true { String::from("...") } else { 5.to_string() };
@@ -31,12 +31,12 @@ pub fn main() {
     };
 
     let _: Box<[isize]> = Box::new([1, 2, 3]);
-    let _: Box<Fn(isize) -> _> = Box::new(|x| (x as u8));
+    let _: Box<dyn Fn(isize) -> _> = Box::new(|x| (x as u8));
 
     let _: Rc<RefCell<[isize]>> = Rc::new(RefCell::new([1, 2, 3]));
-    let _: Rc<RefCell<FnMut(isize) -> _>> = Rc::new(RefCell::new(|x| (x as u8)));
+    let _: Rc<RefCell<dyn FnMut(isize) -> _>> = Rc::new(RefCell::new(|x| (x as u8)));
 
-    let _: Vec<Box<Fn(isize) -> _>> = vec![
+    let _: Vec<Box<dyn Fn(isize) -> _>> = vec![
         Box::new(|x| (x as u8)),
         Box::new(|x| (x as i16 as u8)),
     ];
index a324d73a3a9df09732e028c18fc7ba5d306482ea..12a2999d79d479ca00f93e9bcdcc3c0f1e93d8e3 100644 (file)
@@ -8,7 +8,7 @@ trait Trait {}
 impl Trait for Bar {}
 
 fn main() {
-    let x: &[&Trait] = &[{ &Bar }];
+    let x: &[&dyn Trait] = &[{ &Bar }];
 }
 
 // Issue #25748 - the cast causes an &Encoding -> &Encoding coercion:
@@ -16,9 +16,9 @@ fn main() {
 pub const UTF_8: &'static UTF8Encoding = &UTF8Encoding;
 pub trait Encoding {}
 impl Encoding for UTF8Encoding {}
-pub fn f() -> &'static Encoding { UTF_8 as &'static Encoding }
+pub fn f() -> &'static dyn Encoding { UTF_8 as &'static dyn Encoding }
 
 // Root of the problem: &Trait -> &Trait coercions:
-const FOO: &'static Trait = &Bar;
-const BAR: &'static Trait = FOO;
+const FOO: &'static dyn Trait = &Bar;
+const BAR: &'static dyn Trait = FOO;
 fn foo() { let _x = BAR; }
index 98c1f3ac0273e54a818140409713b463f1f51083..eb3a8948fc80d7acc70ebe72ce755c223a9dee04 100644 (file)
@@ -17,7 +17,7 @@ enum Enum {
 }
 
 #[derive(Debug)]
-struct Pointers(*const Send, *mut Sync);
+struct Pointers(*const dyn Send, *mut dyn Sync);
 
 macro_rules! t {
     ($x:expr, $expected:expr) => {
index 307b3f1d6dc2b9fc4f2a697400681174d71d27eb..1bc3b4c157ca8d596e9353cb905d427a5f165756 100644 (file)
@@ -30,7 +30,7 @@ fn drop(&mut self) {
 pub fn main() {
     {
         let x = box Cat {name: 22};
-        let nyan: Box<Dummy> = x as Box<Dummy>;
+        let nyan: Box<dyn Dummy> = x as Box<dyn Dummy>;
     }
     unsafe {
         assert_eq!(value, 22);
index 35927bde027a3b74053df0bfc6b724e5e7d252a1..24d83eb5343eccced01c8fafe13b8771b0030f2f 100644 (file)
@@ -36,7 +36,7 @@ fn main() {
 
     // Trait objects.
     let a: Bar<i32> = Bar { x: &42 };
-    let b: Bar<Baz> = a;
+    let b: Bar<dyn Baz> = a;
     unsafe {
         assert_eq!((*b.x).get(), 42);
     }
index bbd0b1f8be1f72e8320cdc9aa2d1813aff71b81a..683fa6850fd81075ab2ade11d200d1c18ddce41b 100644 (file)
@@ -26,17 +26,17 @@ fn main() {
     assert_eq!(b[2], 3);
 
     let a: Rc<i32> = Rc::new(42);
-    let b: Rc<Baz> = a.clone();
+    let b: Rc<dyn Baz> = a.clone();
     assert_eq!(b.get(), 42);
 
     let c: Weak<i32> = Rc::downgrade(&a);
-    let d: Weak<Baz> = c.clone();
+    let d: Weak<dyn Baz> = c.clone();
 
     let _c = b.clone();
 
     let a: Rc<RefCell<i32>> = Rc::new(RefCell::new(42));
-    let b: Rc<RefCell<Baz>> = a.clone();
+    let b: Rc<RefCell<dyn Baz>> = a.clone();
     assert_eq!(b.borrow().get(), 42);
     // FIXME
-    let c: Weak<RefCell<Baz>> = Rc::downgrade(&a) as Weak<_>;
+    let c: Weak<RefCell<dyn Baz>> = Rc::downgrade(&a) as Weak<_>;
 }
index 06c2892b69ea2b05bfd69d1a3c5492d18eadbe95..66688e93fb80d8d00eaa1cf716f159168e65563d 100644 (file)
@@ -9,20 +9,20 @@ trait T { fn dummy(&self) { } }
 impl T for S {}
 
 pub fn main() {
-    let x: &T = &S;
+    let x: &dyn T = &S;
     // Test we can convert from &-ptr to *-ptr of trait objects
-    let x: *const T = &S;
+    let x: *const dyn T = &S;
 
     // Test we can convert from &-ptr to *-ptr of struct pointer (not DST)
     let x: *const S = &S;
 
     // As above, but mut
-    let x: &mut T = &mut S;
-    let x: *mut T = &mut S;
+    let x: &mut dyn T = &mut S;
+    let x: *mut dyn T = &mut S;
 
     let x: *mut S = &mut S;
 
     // Test we can change the mutability from mut to const.
-    let x: &T = &mut S;
-    let x: *const T = &mut S;
+    let x: &dyn T = &mut S;
+    let x: *const dyn T = &mut S;
 }
index 9c81f5652d1ff1fe04d0699ee4af982615c416f0..6c338e99912ec2eec32edaa156f6d9fc7b9d8523 100644 (file)
@@ -26,7 +26,7 @@ fn main() {
     // Test that zero-offset works properly
     let b : Baz<usize> = Baz { a: 7 };
     assert_eq!(b.a.get(), 7);
-    let b : &Baz<Bar> = &b;
+    let b : &Baz<dyn Bar> = &b;
     assert_eq!(b.a.get(), 7);
 
     // Test that the field is aligned properly
@@ -34,7 +34,7 @@ fn main() {
     assert_eq!(f.b.get(), 11);
     let ptr1 : *const u8 = &f.b as *const _ as *const u8;
 
-    let f : &Foo<Bar> = &f;
+    let f : &Foo<dyn Bar> = &f;
     let ptr2 : *const u8 = &f.b as *const _ as *const u8;
     assert_eq!(f.b.get(), 11);
 
@@ -44,13 +44,13 @@ fn main() {
     // Test that nested DSTs work properly
     let f : Foo<Foo<usize>> = Foo { a: 0, b: Foo { a: 1, b: 17 }};
     assert_eq!(f.b.b.get(), 17);
-    let f : &Foo<Foo<Bar>> = &f;
+    let f : &Foo<Foo<dyn Bar>> = &f;
     assert_eq!(f.b.b.get(), 17);
 
     // Test that get the pointer via destructuring works
 
     let f : Foo<usize> = Foo { a: 0, b: 11 };
-    let f : &Foo<Bar> = &f;
+    let f : &Foo<dyn Bar> = &f;
     let &Foo { a: _, b: ref bar } = f;
     assert_eq!(bar.get(), 11);
 
index 0728599f3239e074a4c12f0f366ed647c3bd2e2d..980d99a6d6c11170b52e96ebe93845fc6a7bb17c 100644 (file)
@@ -19,11 +19,11 @@ fn index<'a>(&'a self, _: usize) -> &'a str {
 struct T;
 
 impl Index<usize> for T {
-    type Output = Debug + 'static;
+    type Output = dyn Debug + 'static;
 
-    fn index<'a>(&'a self, idx: usize) -> &'a (Debug + 'static) {
+    fn index<'a>(&'a self, idx: usize) -> &'a (dyn Debug + 'static) {
         static X: usize = 42;
-        &X as &(Debug + 'static)
+        &X as &(dyn Debug + 'static)
     }
 }
 
index 949adbbefcea7b07c8ac32f717e7cfee7aa9d1c3..0893b02e74e82e97c84710fe7aad6af23879ccf4 100644 (file)
@@ -24,7 +24,7 @@ struct Foo<T: ?Sized> {
 pub fn main() {
     // raw trait object
     let x = A { f: 42 };
-    let z: *const Trait = &x;
+    let z: *const dyn Trait = &x;
     let r = unsafe {
         (&*z).foo()
     };
@@ -32,7 +32,7 @@ pub fn main() {
 
     // raw DST struct
     let p = Foo {f: A { f: 42 }};
-    let o: *const Foo<Trait> = &p;
+    let o: *const Foo<dyn Trait> = &p;
     let r = unsafe {
         (&*o).f.foo()
     };
@@ -40,7 +40,7 @@ pub fn main() {
 
     // raw DST tuple
     let p = (A { f: 42 },);
-    let o: *const (Trait,) = &p;
+    let o: *const (dyn Trait,) = &p;
     let r = unsafe {
         (&*o).0.foo()
     };
@@ -84,21 +84,21 @@ pub fn main() {
 
     // all of the above with *mut
     let mut x = A { f: 42 };
-    let z: *mut Trait = &mut x;
+    let z: *mut dyn Trait = &mut x;
     let r = unsafe {
         (&*z).foo()
     };
     assert_eq!(r, 42);
 
     let mut p = Foo {f: A { f: 42 }};
-    let o: *mut Foo<Trait> = &mut p;
+    let o: *mut Foo<dyn Trait> = &mut p;
     let r = unsafe {
         (&*o).f.foo()
     };
     assert_eq!(r, 42);
 
     let mut p = (A { f: 42 },);
-    let o: *mut (Trait,) = &mut p;
+    let o: *mut (dyn Trait,) = &mut p;
     let r = unsafe {
         (&*o).0.foo()
     };
index ca88605ee3a8f69c7b23cdb9fac6c94bf927c4a2..70bcc3de07d29b279962e8d60e3f32d8b2c3288e 100644 (file)
@@ -38,7 +38,7 @@ fn to_val(&self) -> isize {
 }
 
 // x is a fat pointer
-fn foo(x: &Fat<ToBar>) {
+fn foo(x: &Fat<dyn ToBar>) {
     assert_eq!(x.0, 5);
     assert_eq!(x.1, "some str");
     assert_eq!(x.2.to_bar(), Bar);
@@ -49,12 +49,12 @@ fn foo(x: &Fat<ToBar>) {
     assert_eq!(y.to_val(), 42);
 }
 
-fn bar(x: &ToBar) {
+fn bar(x: &dyn ToBar) {
     assert_eq!(x.to_bar(), Bar);
     assert_eq!(x.to_val(), 42);
 }
 
-fn baz(x: &Fat<Fat<ToBar>>) {
+fn baz(x: &Fat<Fat<dyn ToBar>>) {
     assert_eq!(x.0, 5);
     assert_eq!(x.1, "some str");
     assert_eq!((x.2).0, 8);
@@ -73,20 +73,20 @@ pub fn main() {
     foo(&f1);
     let f2 = &f1;
     foo(f2);
-    let f3: &Fat<ToBar> = f2;
+    let f3: &Fat<dyn ToBar> = f2;
     foo(f3);
-    let f4: &Fat<ToBar> = &f1;
+    let f4: &Fat<dyn ToBar> = &f1;
     foo(f4);
-    let f5: &Fat<ToBar> = &(5, "some str", Bar1 {f :42});
+    let f5: &Fat<dyn ToBar> = &(5, "some str", Bar1 {f :42});
     foo(f5);
 
     // Zero size object.
-    let f6: &Fat<ToBar> = &(5, "some str", Bar);
+    let f6: &Fat<dyn ToBar> = &(5, "some str", Bar);
     assert_eq!(f6.2.to_bar(), Bar);
 
     // &*
     //
-    let f7: Box<ToBar> = Box::new(Bar1 {f :42});
+    let f7: Box<dyn ToBar> = Box::new(Bar1 {f :42});
     bar(&*f7);
 
     // Deep nesting
@@ -94,10 +94,10 @@ pub fn main() {
     baz(&f1);
     let f2 = &f1;
     baz(f2);
-    let f3: &Fat<Fat<ToBar>> = f2;
+    let f3: &Fat<Fat<dyn ToBar>> = f2;
     baz(f3);
-    let f4: &Fat<Fat<ToBar>> = &f1;
+    let f4: &Fat<Fat<dyn ToBar>> = &f1;
     baz(f4);
-    let f5: &Fat<Fat<ToBar>> = &(5, "some str", (8, "deep str", Bar1 {f :42}));
+    let f5: &Fat<Fat<dyn ToBar>> = &(5, "some str", (8, "deep str", Bar1 {f :42}));
     baz(f5);
 }
index 9a9bd12d50f4f95509ea1a4c672844217aaa9f81..ec6bc72192d4ffc0e1bb53fcdeba275da23ed433 100644 (file)
@@ -38,7 +38,7 @@ fn to_val(&self) -> isize {
 }
 
 // x is a fat pointer
-fn foo(x: &Fat<ToBar>) {
+fn foo(x: &Fat<dyn ToBar>) {
     assert_eq!(x.f1, 5);
     assert_eq!(x.f2, "some str");
     assert_eq!(x.ptr.to_bar(), Bar);
@@ -49,12 +49,12 @@ fn foo(x: &Fat<ToBar>) {
     assert_eq!(y.to_val(), 42);
 }
 
-fn bar(x: &ToBar) {
+fn bar(x: &dyn ToBar) {
     assert_eq!(x.to_bar(), Bar);
     assert_eq!(x.to_val(), 42);
 }
 
-fn baz(x: &Fat<Fat<ToBar>>) {
+fn baz(x: &Fat<Fat<dyn ToBar>>) {
     assert_eq!(x.f1, 5);
     assert_eq!(x.f2, "some str");
     assert_eq!(x.ptr.f1, 8);
@@ -73,20 +73,20 @@ pub fn main() {
     foo(&f1);
     let f2 = &f1;
     foo(f2);
-    let f3: &Fat<ToBar> = f2;
+    let f3: &Fat<dyn ToBar> = f2;
     foo(f3);
-    let f4: &Fat<ToBar> = &f1;
+    let f4: &Fat<dyn ToBar> = &f1;
     foo(f4);
-    let f5: &Fat<ToBar> = &Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
+    let f5: &Fat<dyn ToBar> = &Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
     foo(f5);
 
     // Zero size object.
-    let f6: &Fat<ToBar> = &Fat { f1: 5, f2: "some str", ptr: Bar };
+    let f6: &Fat<dyn ToBar> = &Fat { f1: 5, f2: "some str", ptr: Bar };
     assert_eq!(f6.ptr.to_bar(), Bar);
 
     // &*
     //
-    let f7: Box<ToBar> = Box::new(Bar1 {f :42});
+    let f7: Box<dyn ToBar> = Box::new(Bar1 {f :42});
     bar(&*f7);
 
     // Deep nesting
@@ -95,11 +95,11 @@ pub fn main() {
     baz(&f1);
     let f2 = &f1;
     baz(f2);
-    let f3: &Fat<Fat<ToBar>> = f2;
+    let f3: &Fat<Fat<dyn ToBar>> = f2;
     baz(f3);
-    let f4: &Fat<Fat<ToBar>> = &f1;
+    let f4: &Fat<Fat<dyn ToBar>> = &f1;
     baz(f4);
-    let f5: &Fat<Fat<ToBar>> =
+    let f5: &Fat<Fat<dyn ToBar>> =
         &Fat { f1: 5, f2: "some str", ptr: Fat { f1: 8, f2: "deep str", ptr: Bar1 {f :42}} };
     baz(f5);
 }
index ac4c70a71ce7683642d837206eebe7d32bd2203e..6cce6c723c5a2a4056b6912a8e1d33bca1890efc 100644 (file)
@@ -18,7 +18,7 @@ fn foo(&self) { }
 
 fn assert_foo<T: ?Sized + Foo>() { }
 
-fn use_foo<T: ?Sized + Foo>(x: &Foo) {
+fn use_foo<T: ?Sized + Foo>(x: &dyn Foo) {
     x.foo();
 }
 
index 367b57d5ea0a2ee8504bdb65468393c92c0c1a0c..1943abe9e14da596fc4a015bf327dcfdef7fd9e3 100644 (file)
@@ -25,7 +25,7 @@ fn main() {
     assert_eq!(a as usize, b as *const () as usize);
 
     // And conversion to a void pointer/address for trait objects too.
-    let a: *mut Foo = &mut Bar;
+    let a: *mut dyn Foo = &mut Bar;
     let b = a as *mut ();
     let c = a as *const () as usize;
     let d = unsafe {
index 96b7a66d075873d774d516f33570e7e86121e3df..e97785b5cacdfbc7ef8ee25378f47a7fc345828f 100644 (file)
@@ -5,7 +5,7 @@ struct UsizeRef<'a> {
     a: &'a usize
 }
 
-type RefTo = Box<for<'r> Fn(&'r Vec<usize>) -> UsizeRef<'r>>;
+type RefTo = Box<dyn for<'r> Fn(&'r Vec<usize>) -> UsizeRef<'r>>;
 
 fn ref_to<'a>(vec: &'a Vec<usize>) -> UsizeRef<'a> {
     UsizeRef{ a: &vec[0]}
index 054425989c318adc64c03418a2f6960c99e0e4b0..870ff980ec64d0ac897d9b475c6896a3816e6881 100644 (file)
@@ -17,6 +17,6 @@ fn get(&self) -> isize {
 
 pub fn main() {
     let x = box S { x: 1 };
-    let y = x as Box<Foo<isize>>;
+    let y = x as Box<dyn Foo<isize>>;
     assert_eq!(y.get(), 1);
 }
index 364661e565e2c99ae5f20524164d760a78e61121..987a3e414f5c0dfc2529aff1be1df6586157a204 100644 (file)
@@ -19,7 +19,7 @@ mod map_reduce {
     use std::str;
     use std::thread;
 
-    pub type putter<'a> = Box<FnMut(String, String) + 'a>;
+    pub type putter<'a> = Box<dyn FnMut(String, String) + 'a>;
 
     pub type mapper = extern fn(String, putter);
 
index 1591d616cac7813b6835933c29f1223d8b30aac7..cc766c0605c9f03e648a2299bba744b01bb6fb2b 100644 (file)
@@ -19,7 +19,7 @@ struct Tcx<'tcx> {
 impl<'tcx> Typer<'tcx> for Tcx<'tcx> {
 }
 
-fn g<'tcx>(typer: &Typer<'tcx>) {
+fn g<'tcx>(typer: &dyn Typer<'tcx>) {
 }
 
 fn check_static_type<'x>(tcx: &Tcx<'x>) {
index 09152970fdcd2787d0fc50ba74df87d3837137f1..8431226a3ece1205a9dad2c9c292db413bad4751 100644 (file)
@@ -7,7 +7,7 @@ fn method(&self, data: &'tcx isize) -> &'tcx isize { data }
     fn dummy(&self) { }
 }
 
-fn g<F>(_: F) where F: FnOnce(&Typer) {}
+fn g<F>(_: F) where F: FnOnce(&dyn Typer) {}
 
 fn h() {
     g(|typer| typer.dummy())
index 7ef8ea046b81a70f4150878f42da525e5b499f7d..ff84ad9d2988e4bb2c5507659b5e4c902469d939 100644 (file)
@@ -6,7 +6,7 @@ trait FnLike<A,R> {
     fn call(&self, arg: A) -> R;
 }
 
-type FnObject<'b> = for<'a> FnLike<&'a isize, &'a isize> + 'b;
+type FnObject<'b> = dyn for<'a> FnLike<&'a isize, &'a isize> + 'b;
 
 struct Identity;
 
index 3fb0b3290eb02f46b3c9f0902dd8e8ed4db436c8..1fab9758c5c83bd28adde3df8dee45f3d8a57d11 100644 (file)
@@ -24,8 +24,8 @@ fn foo01<T: for<'a> Get<&'a i32, &'a i32>>(t: T)
 
 // Parse HRTB with explicit `for` in various sorts of types:
 
-fn foo10(t: Box<for<'a> Get<i32, i32>>) { }
-fn foo11(t: Box<for<'a> Fn(i32) -> i32>) { }
+fn foo10(t: Box<dyn for<'a> Get<i32, i32>>) { }
+fn foo11(t: Box<dyn for<'a> Fn(i32) -> i32>) { }
 
 fn foo20(t: for<'a> fn(i32) -> i32) { }
 fn foo21(t: for<'a> unsafe fn(i32) -> i32) { }
index 5fda4b826e00c8c6b643922907d0380e24b6dbe2..6834c392d4e96634a8791cf071857fec2e9a3925 100644 (file)
@@ -6,7 +6,7 @@
 // 'static` and not `Fn(isize) -> (isize + 'static)`. The latter would
 // cause a compilation error. Issue #18772.
 
-fn adder(y: isize) -> Box<Fn(isize) -> isize + 'static> {
+fn adder(y: isize) -> Box<dyn Fn(isize) -> isize + 'static> {
     Box::new(move |x| y + x)
 }
 
index 917f6f9611844a09384913a8be2c32d3fa3c87b0..b97fdf4df508f2160a5e722d97741824190d9e24 100644 (file)
@@ -8,7 +8,7 @@ trait FnLike<A,R> {
     fn call(&self, arg: A) -> R;
 }
 
-type FnObject<'b> = for<'a> FnLike<&'a isize, &'a isize> + 'b;
+type FnObject<'b> = dyn for<'a> FnLike<&'a isize, &'a isize> + 'b;
 
 fn main() {
 }
index 0ed8f7ee52ae96124eb8cfaef3d67e8f8730c76b..d8c726cdd71e50b0bb94b6991fe72f11754194bc 100644 (file)
@@ -5,7 +5,7 @@ trait FnLike<A,R> {
     fn call(&self, arg: A) -> R;
 }
 
-type FnObject<'b> = for<'a> FnLike<(&'a i32,), &'a i32> + 'b;
+type FnObject<'b> = dyn for<'a> FnLike<(&'a i32,), &'a i32> + 'b;
 
 struct Identity;
 
index 4cb9242f0ed807e13f5a5c9ede9fd62ff12112ab..41ebb3f5a14ab1ee07b4cf085edf9cf6457198d5 100644 (file)
@@ -17,7 +17,7 @@ struct NoAnn<'ast> {
 impl<'ast> PrinterSupport<'ast> for NoAnn<'ast> {
 }
 
-fn foo<'ast, G>(f: Option<&'ast usize>, g: G) where G: FnOnce(&PrinterSupport) {
+fn foo<'ast, G>(f: Option<&'ast usize>, g: G) where G: FnOnce(&dyn PrinterSupport) {
     let annotation = NoAnn { f: f };
     g(&annotation)
 }
index 8c17b01e2bd899da9bff7fe79cac7594920ea96a..6660f393f7dac5f5b1990a43cd4203ace8aab1ec 100644 (file)
@@ -93,7 +93,7 @@ pub fn main() {
     t!(format!("{:#4}", C), "☃123");
     t!(format!("{:b}", D), "aa☃bb");
 
-    let a: &fmt::Debug = &1;
+    let a: &dyn fmt::Debug = &1;
     t!(format!("{:?}", a), "1");
 
 
index 968e9b7d34ab7606b1c2c18498d3e4aa88aca76e..f1b1656745e7c487b8ba1c75c69a3487e34a16db 100644 (file)
@@ -180,6 +180,10 @@ fn sub_one(&self) -> Self {
     fn add_usize(&self, _: usize) -> Option<Self> {
         unimplemented!()
     }
+
+    fn sub_usize(&self, _: usize) -> Option<Self> {
+        unimplemented!()
+    }
 }
 
 #[derive(Copy, Clone, Debug, Eq, Ord, PartialEq, PartialOrd)]
index 8872eae6f8bfbfa2f023fc0644e134f0b8729f2b..f1d6b37a6843f3fff6f98efdb8628b82aaba9f82 100644 (file)
@@ -24,9 +24,9 @@ trait MyTrait { fn dummy(&self) { } }
 impl MyTrait for Box<DroppableStruct> {}
 impl MyTrait for Box<DroppableEnum> {}
 
-struct Whatever { w: Box<MyTrait+'static> }
+struct Whatever { w: Box<dyn MyTrait+'static> }
 impl  Whatever {
-    fn new(w: Box<MyTrait+'static>) -> Whatever {
+    fn new(w: Box<dyn MyTrait+'static>) -> Whatever {
         Whatever { w: w }
     }
 }
@@ -34,13 +34,13 @@ fn new(w: Box<MyTrait+'static>) -> Whatever {
 fn main() {
     {
         let f: Box<_> = box DroppableStruct;
-        let _a = Whatever::new(box f as Box<MyTrait>);
+        let _a = Whatever::new(box f as Box<dyn MyTrait>);
     }
     assert!(unsafe { DROPPED });
     unsafe { DROPPED = false; }
     {
         let f: Box<_> = box DroppableEnum::DroppableVariant1;
-        let _a = Whatever::new(box f as Box<MyTrait>);
+        let _a = Whatever::new(box f as Box<dyn MyTrait>);
     }
     assert!(unsafe { DROPPED });
 }
index b628bf601968daba8b1bf0a7bd4e2280be227118..ce0951eafdd346d46d92c29b1cfb0c9f021821a8 100644 (file)
@@ -5,44 +5,44 @@
 
 trait Foo { fn dummy(&self) { } }
 impl Foo for isize {}
-fn foo(_: [&Foo; 2]) {}
-fn foos(_: &[&Foo]) {}
+fn foo(_: [&dyn Foo; 2]) {}
+fn foos(_: &[&dyn Foo]) {}
 fn foog<T>(_: &[T], _: &[T]) {}
 
-fn bar(_: [Box<Foo>; 2]) {}
-fn bars(_: &[Box<Foo+'static>]) {}
+fn bar(_: [Box<dyn Foo>; 2]) {}
+fn bars(_: &[Box<dyn Foo+'static>]) {}
 
 fn main() {
-    let x: [&Foo; 2] = [&1, &2];
+    let x: [&dyn Foo; 2] = [&1, &2];
     foo(x);
     foo([&1, &2]);
 
     let r = &1;
-    let x: [&Foo; 2] = [r; 2];
+    let x: [&dyn Foo; 2] = [r; 2];
     foo(x);
     foo([&1; 2]);
 
-    let x: &[&Foo] = &[&1, &2];
+    let x: &[&dyn Foo] = &[&1, &2];
     foos(x);
     foos(&[&1, &2]);
 
-    let x: &[&Foo] = &[&1, &2];
+    let x: &[&dyn Foo] = &[&1, &2];
     let r = &1;
     foog(x, &[r]);
 
-    let x: [Box<Foo>; 2] = [Box::new(1), Box::new(2)];
+    let x: [Box<dyn Foo>; 2] = [Box::new(1), Box::new(2)];
     bar(x);
     bar([Box::new(1), Box::new(2)]);
 
-    let x: &[Box<Foo+'static>] = &[Box::new(1), Box::new(2)];
+    let x: &[Box<dyn Foo+'static>] = &[Box::new(1), Box::new(2)];
     bars(x);
     bars(&[Box::new(1), Box::new(2)]);
 
-    let x: &[Box<Foo+'static>] = &[Box::new(1), Box::new(2)];
+    let x: &[Box<dyn Foo+'static>] = &[Box::new(1), Box::new(2)];
     foog(x, &[Box::new(1)]);
 
     struct T<'a> {
-        t: [&'a (Foo+'a); 2]
+        t: [&'a (dyn Foo+'a); 2]
     }
     let _n = T {
         t: [&1, &2]
@@ -51,34 +51,34 @@ struct T<'a> {
     let _n = T {
         t: [r; 2]
     };
-    let x: [&Foo; 2] = [&1, &2];
+    let x: [&dyn Foo; 2] = [&1, &2];
     let _n = T {
         t: x
     };
 
     struct F<'b> {
-        t: &'b [&'b (Foo+'b)]
+        t: &'b [&'b (dyn Foo+'b)]
     }
     let _n = F {
         t: &[&1, &2]
     };
     let r = &1;
-    let r: [&Foo; 2] = [r; 2];
+    let r: [&dyn Foo; 2] = [r; 2];
     let _n = F {
         t: &r
     };
-    let x: [&Foo; 2] = [&1, &2];
+    let x: [&dyn Foo; 2] = [&1, &2];
     let _n = F {
         t: &x
     };
 
     struct M<'a> {
-        t: &'a [Box<Foo+'static>]
+        t: &'a [Box<dyn Foo+'static>]
     }
     let _n = M {
         t: &[Box::new(1), Box::new(2)]
     };
-    let x: [Box<Foo>; 2] = [Box::new(1), Box::new(2)];
+    let x: [Box<dyn Foo>; 2] = [Box::new(1), Box::new(2)];
     let _n = M {
         t: &x
     };
index 1aaeaa62ad00539e194ee7acc3830b4a73b0ec7b..848ed6ac7a8ff12eb6d6ab113796f5f601dacc0c 100644 (file)
@@ -10,7 +10,7 @@ impl T<isize> for Empty {
     fn next(&mut self) -> Option<isize> { None }
 }
 
-fn do_something_with(a : &mut T<isize>) {
+fn do_something_with(a : &mut dyn T<isize>) {
     println!("{:?}", a.next())
 }
 
index 5dabecc48f9c1c72d85cbadcf2d38b93bf541962..be18c736f1483fe8ab141709523f2a8f41379ad8 100644 (file)
@@ -11,8 +11,8 @@ trait X<T> {
     fn dummy(&self) -> T { panic!() }
 }
 
-struct S<T> {f: Box<X<T>+'static>,
-             g: Box<X<T>+'static>}
+struct S<T> {f: Box<dyn X<T>+'static>,
+             g: Box<dyn X<T>+'static>}
 
 struct F;
 impl X<isize> for F {
index f191a203f03a83d17cfb0443cb94041d9fe5e18e..cb5e3dff3b31b395b5c36efeaffc26e9f5cb6aed 100644 (file)
@@ -9,7 +9,7 @@
 
 struct S {x:()}
 
-fn test(slot: &mut Option<Box<FnMut() -> Box<FnMut()>>>) -> () {
+fn test(slot: &mut Option<Box<dyn FnMut() -> Box<dyn FnMut()>>>) -> () {
   let a = slot.take();
   let _a = match a {
     // `{let .. a(); }` would break
index d02620ee1a471b1d74c4fe1c781094b7f67a877d..e2756ec970c39d7713956ef1b9971f94b83dc4ab 100644 (file)
@@ -1,5 +1,5 @@
 // run-pass
 fn main() {
-    fn test() -> Box<std::any::Any + 'static> { Box::new(1) }
+    fn test() -> Box<dyn std::any::Any + 'static> { Box::new(1) }
     println!("{:?}", test())
 }
index ce920a3ccab9df738fd8fc2fe4f055fc839c587f..63f3589c6cc635c8a7563c58d97fc445065988f9 100644 (file)
@@ -23,7 +23,7 @@ pub fn type_ids() -> Vec<TypeId> {
         TypeId::of::<FooFnPtr>(),
         TypeId::of::<FooNil>(),
         TypeId::of::<FooTuple>(),
-        TypeId::of::<FooTrait>(),
+        TypeId::of::<dyn FooTrait>(),
         TypeId::of::<FooStruct>(),
         TypeId::of::<FooEnum>()
     ]
index d1b94c71864620ffdae2d671957ad863268aa9d0..9f9db067bf4b5ea8924637d59e785094da61e554 100644 (file)
@@ -4,7 +4,7 @@
 // pretty-expanded FIXME #23616
 
 struct Foo<'a> {
-    listener: Box<FnMut() + 'a>,
+    listener: Box<dyn FnMut() + 'a>,
 }
 
 impl<'a> Foo<'a> {
index 1b57856e95566437e12556825b53ffeac7832b7a..6bf8a589959c57afa908a31f6f8f686e94880cc1 100644 (file)
@@ -16,5 +16,5 @@ impl A for B1 {}
 
 fn main() {
     let v: Box<_> = box B1;
-    let _c: Box<A> = v.clone();
+    let _c: Box<dyn A> = v.clone();
 }
index d495602dff7e7f86998b993784ac437827fa5adf..5d8aab2ce74ce532fde522ebda3a3989ff44c6cd 100644 (file)
@@ -5,9 +5,9 @@
 // pretty-expanded FIXME #23616
 
 fn main() {
-    send::<Box<Foo>>(Box::new(Output(0)));
-    Test::<Box<Foo>>::foo(Box::new(Output(0)));
-    Test::<Box<Foo>>::new().send(Box::new(Output(0)));
+    send::<Box<dyn Foo>>(Box::new(Output(0)));
+    Test::<Box<dyn Foo>>::foo(Box::new(Output(0)));
+    Test::<Box<dyn Foo>>::new().send(Box::new(Output(0)));
 }
 
 fn send<T>(_: T) {}
index 5ac0d0df0d7d419cfea4cc2faf0196a2b10d1409..00b2e3607fcba4f872eb9f01f5c18d553a57f17b 100644 (file)
@@ -6,16 +6,16 @@ trait SomeTrait {}
 impl SomeTrait for Meow {}
 
 struct Foo<'a> {
-    x: &'a SomeTrait,
-    y: &'a SomeTrait,
+    x: &'a dyn SomeTrait,
+    y: &'a dyn SomeTrait,
 }
 
 impl<'a> Foo<'a> {
-    pub fn new<'b>(x: &'b SomeTrait, y: &'b SomeTrait) -> Foo<'b> { Foo { x: x, y: y } }
+    pub fn new<'b>(x: &'b dyn SomeTrait, y: &'b dyn SomeTrait) -> Foo<'b> { Foo { x: x, y: y } }
 }
 
 fn main() {
     let r = Meow;
     let s = Meow;
-    let q = Foo::new(&r as &SomeTrait, &s as &SomeTrait);
+    let q = Foo::new(&r as &dyn SomeTrait, &s as &dyn SomeTrait);
 }
index c6ccb7575bb836f7946566d73d96ce1dfc118a40..943615433549e2e84e518e4ca494fc192f860536 100644 (file)
@@ -9,7 +9,7 @@ trait Matcher {
 
 struct CharPredMatcher<'a, 'b> {
     str: &'a str,
-    pred: Box<FnMut(char) -> bool + 'b>,
+    pred: Box<dyn FnMut(char) -> bool + 'b>,
 }
 
 impl<'a, 'b> Matcher for CharPredMatcher<'a, 'b> {
index 17f7f159fd2db6ff902f0846986abe91580639be..a12564ca9c0ee40a301c2bf91856a0ade73a5040 100644 (file)
@@ -7,17 +7,17 @@ trait Foo { fn dummy(&self) { }}
 
 struct Bar;
 
-impl<'a> std::ops::Fn<(&'a (Foo+'a),)> for Bar {
-    extern "rust-call" fn call(&self, _: (&'a Foo,)) {}
+impl<'a> std::ops::Fn<(&'a (dyn Foo+'a),)> for Bar {
+    extern "rust-call" fn call(&self, _: (&'a dyn Foo,)) {}
 }
 
-impl<'a> std::ops::FnMut<(&'a (Foo+'a),)> for Bar {
-    extern "rust-call" fn call_mut(&mut self, a: (&'a Foo,)) { self.call(a) }
+impl<'a> std::ops::FnMut<(&'a (dyn Foo+'a),)> for Bar {
+    extern "rust-call" fn call_mut(&mut self, a: (&'a dyn Foo,)) { self.call(a) }
 }
 
-impl<'a> std::ops::FnOnce<(&'a (Foo+'a),)> for Bar {
+impl<'a> std::ops::FnOnce<(&'a (dyn Foo+'a),)> for Bar {
     type Output = ();
-    extern "rust-call" fn call_once(self, a: (&'a Foo,)) { self.call(a) }
+    extern "rust-call" fn call_once(self, a: (&'a dyn Foo,)) { self.call(a) }
 }
 
 struct Baz;
index 3e513a3d5ecbe0345ebe61c4eadfac8a33aa3cb3..7b137b4af56a7d9745f7a9cd91aac7771d91b3db 100644 (file)
@@ -4,18 +4,18 @@ trait IndirectTraitWithSend: TraitWithSend {}
 
 // Check struct instantiation (Box<TraitWithSend> will only have Send if TraitWithSend has Send)
 #[allow(dead_code)]
-struct Blah { x: Box<TraitWithSend> }
+struct Blah { x: Box<dyn TraitWithSend> }
 impl TraitWithSend for Blah {}
 
 // Struct instantiation 2-levels deep
 #[allow(dead_code)]
-struct IndirectBlah { x: Box<IndirectTraitWithSend> }
+struct IndirectBlah { x: Box<dyn IndirectTraitWithSend> }
 impl TraitWithSend for IndirectBlah {}
 impl IndirectTraitWithSend for IndirectBlah {}
 
 fn test_trait<T: Send + ?Sized>() { println!("got here!") }
 
 fn main() {
-    test_trait::<TraitWithSend>();
-    test_trait::<IndirectTraitWithSend>();
+    test_trait::<dyn TraitWithSend>();
+    test_trait::<dyn IndirectTraitWithSend>();
 }
index 4438d1f2ceca3bc231db7c1b9cae4cdd6fb6b35a..9ceffff2e38066ac903cfe1b37ccdd83025fcb3a 100644 (file)
@@ -78,12 +78,12 @@ fn main() {
     assert_eq!(cc().unwrap(), 3);
     assert_eq!(dd().unwrap(), 3);
 
-    let i = box 32isize as Box<A>;
+    let i = box 32isize as Box<dyn A>;
     assert_eq!(i.aaa(), 3);
-    let i = box 32isize as Box<A>;
+    let i = box 32isize as Box<dyn A>;
     assert_eq!(i.bbb(), 3);
-    let i = box 32isize as Box<A>;
+    let i = box 32isize as Box<dyn A>;
     assert_eq!(i.ccc().unwrap(), 3);
-    let i = box 32isize as Box<A>;
+    let i = box 32isize as Box<dyn A>;
     assert_eq!(i.ddd().unwrap(), 3);
 }
index 6868eae6ea4f7204b055512e1745978c24b52dd6..54ad8fd076e4e871ccf601daa2671551b7018764 100644 (file)
@@ -39,12 +39,12 @@ extern "rust-call" fn call_once(mut self, args: (u32,u32)) -> u32 { self.call_mu
 }
 
 fn main() {
-    let mut f = box Foo { foo: 42 } as Box<FnMut() -> u32>;
+    let mut f = box Foo { foo: 42 } as Box<dyn FnMut() -> u32>;
     assert_eq!(f.call_mut(()), 42);
 
-    let mut f = box Foo { foo: 40 } as Box<FnMut(u32) -> u32>;
+    let mut f = box Foo { foo: 40 } as Box<dyn FnMut(u32) -> u32>;
     assert_eq!(f.call_mut((2,)), 42);
 
-    let mut f = box Foo { foo: 40 } as Box<FnMut(u32, u32) -> u32>;
+    let mut f = box Foo { foo: 40 } as Box<dyn FnMut(u32, u32) -> u32>;
     assert_eq!(f.call_mut((1, 1)), 42);
 }
index 82a3943e9efa51bae1fbfc25f430311e845c4d07..c3c6ff304888db8c6627a0608e9bb0ba0ad3b8c8 100644 (file)
@@ -7,5 +7,5 @@ fn foo(_: &u8) {
 }
 
 fn main() {
-    let _ = &foo as &Any;
+    let _ = &foo as &dyn Any;
 }
index 79b6a5ae5337c751d2915db8a42854acb3fe4d0c..20a8d136124695495b4dbe7e6e798497ffa4e4ff 100644 (file)
@@ -5,11 +5,11 @@
 
 use std::io::{self, Write};
 
-fn f(wr: &mut Write) {
+fn f(wr: &mut dyn Write) {
     wr.write_all(b"hello").ok().expect("failed");
 }
 
 fn main() {
-    let mut wr = box io::stdout() as Box<Write>;
+    let mut wr = box io::stdout() as Box<dyn Write>;
     f(&mut wr);
 }
index f51f0b3ca0171a5e78a8ce886f062d372b534dd6..62f6bcf15e3e74edd6b674d05a8af0a2ce416944 100644 (file)
@@ -6,5 +6,5 @@ impl Str for str {}
 impl<'a, S: ?Sized> Str for &'a S where S: Str {}
 
 fn main() {
-    let _: &Str = &"x";
+    let _: &dyn Str = &"x";
 }
index 7eea5ce6589b500dc613c499b478dda37ec75a16..2f6464668c2ceafd2dde15cccf7dc2318db278e6 100644 (file)
@@ -4,13 +4,13 @@
 
 trait Aaa { fn dummy(&self) { } }
 
-impl<'a> Aaa for &'a mut (Aaa + 'a) {}
+impl<'a> Aaa for &'a mut (dyn Aaa + 'a) {}
 
 struct Bar<'a> {
-    writer: &'a mut (Aaa + 'a),
+    writer: &'a mut (dyn Aaa + 'a),
 }
 
-fn baz(_: &mut Aaa) {
+fn baz(_: &mut dyn Aaa) {
 }
 
 fn foo<'a>(mut bar: Bar<'a>) {
index 291bd3f1718a2de4a92c8e2d2e3db6b8a0a376ef..6873c7ccb7f1c4a06857924633b41354c8db74e3 100644 (file)
@@ -1,5 +1,5 @@
 // run-pass
-fn action(mut cb: Box<FnMut(usize) -> usize>) -> usize {
+fn action(mut cb: Box<dyn FnMut(usize) -> usize>) -> usize {
     cb(1)
 }
 
index cb7b5a638fc2baf9ee5b8f76df5e4bd55491bf8f..772cd9d7eda822acd082934770668c63b7f37baf 100644 (file)
@@ -22,7 +22,7 @@ fn dummy(&self) { }
            box_4: fn () -> Box<[i8; 4]>,
             ) {
     println!("Hello World 1");
-    let _: Box<Boo> = match 3 {
+    let _: Box<dyn Boo> = match 3 {
         1 => box_1(),
         2 => box_2(),
         3 => box_3(),
index 95273edcf7e82994393cac9a85a30a3c5ebefad7..0ca67d9dc710e6c421ad4428f762c2b9341ad537 100644 (file)
@@ -4,7 +4,7 @@
 // pretty-expanded FIXME #23616
 
 fn main() {
-    let functions: [Box<Fn() -> Option<()>>; 1] = [Box::new(|| None)];
+    let functions: [Box<dyn Fn() -> Option<()>>; 1] = [Box::new(|| None)];
 
     let _: Option<Vec<()>> = functions.iter().map(|f| (*f)()).collect();
 }
index 27bbff09a00f2555e1aa1ac04abb10268b18f768..2bc5034960a1bfdaf9d862ec13878e96577043fd 100644 (file)
@@ -7,6 +7,6 @@
 use std::fmt;
 
 fn main() {
-    let a: &fmt::Debug = &1;
+    let a: &dyn fmt::Debug = &1;
     format!("{:?}", a);
 }
index f5c743d0d826274713012a6cfedfd5a3d6618b1d..4ec7e3195ebe05fb1ba39c98fcdbcdb1d8ecf616 100644 (file)
@@ -2,11 +2,11 @@
 #![allow(unused_mut)]
 #![allow(unused_variables)]
 fn main() {
-    let mut shrinker: Box<Iterator<Item=i32>> = Box::new(vec![1].into_iter());
+    let mut shrinker: Box<dyn Iterator<Item=i32>> = Box::new(vec![1].into_iter());
     println!("{:?}", shrinker.next());
     for v in shrinker { assert!(false); }
 
-    let mut shrinker: &mut Iterator<Item=i32> = &mut vec![1].into_iter();
+    let mut shrinker: &mut dyn Iterator<Item=i32> = &mut vec![1].into_iter();
     println!("{:?}", shrinker.next());
     for v in shrinker { assert!(false); }
 }
index e0cf26f7034cae090e0118808017eaa5af58ae4f..0483e62fd21213d300c92ce64930bab8c1b77c82 100644 (file)
@@ -13,7 +13,7 @@ fn main() {
         // str
         std::intrinsics::type_name::<str>(),
         // Trait
-        std::intrinsics::type_name::<Send>(),
+        std::intrinsics::type_name::<dyn Send>(),
         // Newtype
         std::intrinsics::type_name::<NT>(),
         // DST
index 5297a4a7b29e21e37659361d55bc31b07eac05f6..c970e77abb72b5b50fe7eb333a10d82b489e332a 100644 (file)
@@ -2,10 +2,10 @@
 
 fn main() {
     let v = vec![1, 2, 3];
-    let boxed: Box<Iterator<Item=i32>> = Box::new(v.into_iter());
+    let boxed: Box<dyn Iterator<Item=i32>> = Box::new(v.into_iter());
     assert_eq!(boxed.max(), Some(3));
 
     let v = vec![1, 2, 3];
-    let boxed: &mut Iterator<Item=i32> = &mut v.into_iter();
+    let boxed: &mut dyn Iterator<Item=i32> = &mut v.into_iter();
     assert_eq!(boxed.max(), Some(3));
 }
index cddd48349f9d0376dc86c0efc75007a8951b9dd4..d1cd4ec7b8a01995d1e76c34820e18c2abce14da 100644 (file)
@@ -1,6 +1,6 @@
 // run-pass
 
-fn test(it: &mut Iterator<Item=i32>) {
+fn test(it: &mut dyn Iterator<Item=i32>) {
     for x in it {
         assert_eq!(x, 1)
     }
index 34a80ab00516bcd69a6d79f43ec1790f5626cf39..e67a924b9eedc0ac0363ce725b8b2b891fe4755e 100644 (file)
@@ -9,11 +9,11 @@
 
 static generations: usize = 1024+256+128+49;
 
-fn spawn(mut f: Box<FnMut() + 'static + Send>) {
+fn spawn(mut f: Box<dyn FnMut() + 'static + Send>) {
     Builder::new().stack_size(32 * 1024).spawn(move|| f());
 }
 
-fn child_no(x: usize) -> Box<FnMut() + 'static + Send> {
+fn child_no(x: usize) -> Box<dyn FnMut() + 'static + Send> {
     Box::new(move|| {
         if x < generations {
             spawn(child_no(x+1));
index b728911e54170b453a3deddb3d5771b13277172b..5f6d9dcc9ae43d90ef0c770d721ce67f3d7b0066 100644 (file)
@@ -3,7 +3,7 @@
 // pretty-expanded FIXME #23616
 
 // This used to cause an ICE because the retslot for the "return" had the wrong type
-fn testcase<'a>() -> Box<Iterator<Item=usize> + 'a> {
+fn testcase<'a>() -> Box<dyn Iterator<Item=usize> + 'a> {
     return Box::new((0..3).map(|i| { return i; }));
 }
 
index 963e7e62c7f1115cffed79813e42e2bc49fe0c22..c74e53fca60fdfac8b07edf7c483277f39c491ff 100644 (file)
@@ -23,13 +23,13 @@ fn foo<A>(b: A) -> foo<A> {
     }
 }
 
-fn f<A>(x: Box<clam<A>>, a: A) {
+fn f<A>(x: Box<dyn clam<A>>, a: A) {
   x.chowder(a);
 }
 
 pub fn main() {
 
   let c = foo(42);
-  let d: Box<clam<isize>> = box c as Box<clam<isize>>;
+  let d: Box<dyn clam<isize>> = box c as Box<dyn clam<isize>>;
   f(d, c.x);
 }
index 0b34653a34535d09ae3b89cc025ff17b402813a3..e21f86351eeee130592500b7593953b33331c0e6 100644 (file)
@@ -41,7 +41,7 @@ fn check_both(val: &Foo<[u8]>) {
     }
 }
 
-fn check_trait_obj(val: &Foo<Get>) {
+fn check_trait_obj(val: &Foo<dyn Get>) {
     match *val {
         Foo { a, ref inner } => {
             assert_eq!(a, 32);
@@ -56,6 +56,6 @@ fn main() {
     check_dst_val(foo);
     check_both(foo);
 
-    let foo: &Foo<Get> = &Foo { a: 32, inner: 32 };
+    let foo: &Foo<dyn Get> = &Foo { a: 32, inner: 32 };
     check_trait_obj(foo);
 }
index a55846f40dfbdd7ebea0bfd90d565fb054ec0f33..1dd3d9293bcc6112b04cded5179522135edba6c5 100644 (file)
@@ -45,6 +45,6 @@ fn next(&mut self) -> Option<Token> {
 }
 
 fn main() {
-    let mut x: Box<Iterator<Item=Token>> = Box::new(Counter { value: 22 });
+    let mut x: Box<dyn Iterator<Item=Token>> = Box::new(Counter { value: 22 });
     assert_eq!(x.next().unwrap().value, 22);
 }
index 1f68d47d97b63b23d983f3d20537c347ae2c0c53..264e1ee22cdda8c70eddee0af9c0650e844a5672 100644 (file)
@@ -2,7 +2,7 @@ trait Foo: Fn(i32) -> i32 + Send {}
 
 impl<T: ?Sized + Fn(i32) -> i32 + Send> Foo for T {}
 
-fn wants_foo(f: Box<Foo>) -> i32 {
+fn wants_foo(f: Box<dyn Foo>) -> i32 {
     f(42)
 }
 
index 86fa5a6f3682e97c930e0b6bb2f37ed1c80ecd27..54622afbcfc1323daabb8d9e56c98ce1f5cb0ea9 100644 (file)
@@ -7,8 +7,8 @@ pub struct Registry<'a> {
 }
 
 pub struct Listener<'a> {
-    pub announce: Option<Box<FnMut(&mut Registry) + 'a>>,
-    pub remove: Option<Box<FnMut(&mut Registry) + 'a>>,
+    pub announce: Option<Box<dyn FnMut(&mut Registry) + 'a>>,
+    pub remove: Option<Box<dyn FnMut(&mut Registry) + 'a>>,
 }
 
 impl<'a> Drop for Registry<'a> {
index 602f458e4cf54e189159def5bbd3f45687df4d7b..6f8ec700951e25a4cec8c1584e29fea67aed6328 100644 (file)
@@ -12,7 +12,7 @@ pub trait Routing<I> {
 
 pub trait ToRouting {
     type Input;
-    type Routing : ?Sized = Routing<Self::Input, Output=()>;
+    type Routing : ?Sized = dyn Routing<Self::Input, Output=()>;
     fn to_routing(self) -> Self::Routing;
 }
 
index 75af16d8dda8e5419f3a413ed685f6f9118c025d..e7b9ea3acfc01e225263bdeffa68cc7f8de480d4 100644 (file)
@@ -13,7 +13,7 @@ fn main() {
     let mut drops = 0;
 
     {
-        let _: Rc<Send> = Rc::new(Foo(&mut drops));
+        let _: Rc<dyn Send> = Rc::new(Foo(&mut drops));
     }
 
     assert_eq!(1, drops);
index db9261f6ef48f66146a2b1d5c6f840f0c84e7bf9..25a2da707dc0f469d422d00e9a4edb725d192e65 100644 (file)
@@ -25,7 +25,7 @@ fn main() {
 
     drops = 0;
     {
-        let y = &Holder(Foo(&mut drops)) as &Holder<Trait>;
+        let y = &Holder(Foo(&mut drops)) as &Holder<dyn Trait>;
         // this used to cause an extra drop of the Foo instance
         let x = &y.0;
     }
index caade6defdd49ed5c3713e4997c72980fc39238e..ec1864d7deb589b883aab2fce42d19ed0f9b74fa 100644 (file)
@@ -9,7 +9,7 @@ fn x(&mut self) {
     }
 }
 
-const FUNC: &'static Fn(&mut Foo) -> () = &Foo::x;
+const FUNC: &'static dyn Fn(&mut Foo) -> () = &Foo::x;
 
 fn main() {
     let mut foo = Foo { a: 137 };
index 297b1d689a6b1f345e3585398806326ad32e70b7..4b6f2c2b3bc7d7d70dbcbef21a934368b6992ee1 100644 (file)
@@ -1,5 +1,5 @@
 // run-pass
-struct Parser<'a>(Box<FnMut(Parser) + 'a>);
+struct Parser<'a>(Box<dyn FnMut(Parser) + 'a>);
 
 fn main() {
     let _x = Parser(Box::new(|_|{}));
index 84cd21373672e24a69766ce4a2f65a0c973664c6..281ae13399dd2590dfc88d358c07f90ece659a41 100644 (file)
@@ -11,7 +11,7 @@ fn main() {
     let mut x = 0;
     {
         let wrapper = Box::new(Wrapper(&mut x, 123));
-        let _: Box<Wrapper<Send>> = wrapper;
+        let _: Box<Wrapper<dyn Send>> = wrapper;
     }
     assert_eq!(432, x)
 }
index c4aa70d50222d1aa42319547c98a340bbe035d25..307a67160980db8da67d82f2daa8d9cd6b6ffc6f 100644 (file)
@@ -5,7 +5,7 @@ fn bar<'b>(&self, x: &'b u8) -> u8 where 'a: 'b { *x+7 }
 
 pub struct FooBar;
 impl Foo<'static> for FooBar {}
-fn test(foobar: FooBar) -> Box<Foo<'static>> {
+fn test(foobar: FooBar) -> Box<dyn Foo<'static>> {
     Box::new(foobar)
 }
 
index 950d98315d049985d9d844271468da4d1f7584d6..bcf8a6731910fb006838b666be9b0846ce4a7d3a 100644 (file)
@@ -2,5 +2,5 @@
 struct NonOrd;
 
 fn main() {
-    let _: Box<Iterator<Item = _>> = Box::new(vec![NonOrd].into_iter());
+    let _: Box<dyn Iterator<Item = _>> = Box::new(vec![NonOrd].into_iter());
 }
index 2f500d1c0d1b7c360e55de7384f3d637d46d0fd7..2d5827f476b9e3c090ef95cd39758b2bf403cb27 100644 (file)
@@ -17,5 +17,5 @@ fn main() {
     let data = [1, 2, 3];
     let iter = data.iter();
     let x = MyRc { _ptr: &iter, _boo: PhantomData };
-    let _y: MyRc<Iterator<Item=&u32>> = x;
+    let _y: MyRc<dyn Iterator<Item=&u32>> = x;
 }
index fccea452fbcef7958031dc4bd219ccf3aaa02144..161e2d4d204eb22eaa893cc21c2aea4d3454659a 100644 (file)
@@ -1,4 +1,4 @@
 // run-pass
 fn main() {
-    const _C: &'static Fn() = &||{};
+    const _C: &'static dyn Fn() = &||{};
 }
index fcb224e2d043dd004ca65957111729af58b9515f..d449f6449aa091e3a0d42de258bbe4961fd34397 100644 (file)
@@ -11,8 +11,8 @@ fn dummy(&self) { }
 }
 impl<A> hax for A { }
 
-fn perform_hax<T: 'static>(x: Box<T>) -> Box<hax+'static> {
-    box x as Box<hax+'static>
+fn perform_hax<T: 'static>(x: Box<T>) -> Box<dyn hax+'static> {
+    box x as Box<dyn hax+'static>
 }
 
 fn deadcode() {
index c48bedf14f7b7d416a3840b620b98d1522067dfc..794c7d4edaa113f6e9d9089f7d820b0c988c48a5 100644 (file)
@@ -11,8 +11,8 @@ fn dummy(&self) { }
 }
 impl<A> hax for A { }
 
-fn perform_hax<T: 'static>(x: Box<T>) -> Box<hax+'static> {
-    box x as Box<hax+'static>
+fn perform_hax<T: 'static>(x: Box<T>) -> Box<dyn hax+'static> {
+    box x as Box<dyn hax+'static>
 }
 
 fn deadcode() {
index 0f6a932e4b886feb7d75e437af3dc7bf388b4354..9f85473380f828d0a6b400f9539ce4c673c75db8 100644 (file)
@@ -1,6 +1,6 @@
 // run-pass
-static PLUS_ONE: &'static (Fn(i32) -> i32 + Sync) = (&|x: i32| { x + 1 })
-    as &'static (Fn(i32) -> i32 + Sync);
+static PLUS_ONE: &'static (dyn Fn(i32) -> i32 + Sync) = (&|x: i32| { x + 1 })
+    as &'static (dyn Fn(i32) -> i32 + Sync);
 
 fn main() {
     assert_eq!(PLUS_ONE(2), 3);
index 58ade32b2502cd26cd35385b5a2ee31288ecf178..11641ca738018396765f77182fa3e1d0d70492be 100644 (file)
@@ -20,7 +20,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 (box true as Box<it>);
+    let z: Box<_> = box (box true as Box<dyn it>);
     //  x.f();
     // y.f();
     // (*z).f();
index 927102981e7f9ce72f0564fda24b4bd187cfe5dc..ee2456da3e2153f035b5df970177b8cf315f7a53 100644 (file)
@@ -2,7 +2,7 @@
 #![allow(dead_code)]
 // pretty-expanded FIXME #23616
 
-type Connection = Box<FnMut(Vec<u8>) + 'static>;
+type Connection = Box<dyn FnMut(Vec<u8>) + 'static>;
 
 fn f() -> Option<Connection> {
     let mock_connection: Connection = Box::new(|_| {});
index 0ae270200a6a2b5e8853263b33d45c8fd48d4f10..e837fc81721a807c7a5166632d0a9263c9243988 100644 (file)
@@ -8,7 +8,7 @@
 pub enum Handler {
     Default,
     #[allow(dead_code)]
-    Custom(*mut Box<Fn()>),
+    Custom(*mut Box<dyn Fn()>),
 }
 
 fn main() {
@@ -16,7 +16,7 @@ fn main() {
 }
 
 #[inline(never)]
-pub fn take(h: Handler, f: Box<Fn()>) -> Box<Fn()> {
+pub fn take(h: Handler, f: Box<dyn Fn()>) -> Box<dyn Fn()> {
     unsafe {
         match h {
             Handler::Custom(ptr) => *Box::from_raw(ptr),
index 236a181fc1d2501331944804a3882eee42cfb07a..c718449d84eed48676e61c6eee6cc1963b073a0d 100644 (file)
@@ -1,5 +1,5 @@
 // run-pass
 fn main() {
-    &0u8 as *const u8 as *const PartialEq<u8>;
+    &0u8 as *const u8 as *const dyn PartialEq<u8>;
     &[0u8] as *const [u8; 1] as *const [u8];
 }
index 6824c66cb3751e6c5be608313c19bc065f6cb3de..cc94cc819d6655d047576adf205fc812746e1284 100644 (file)
@@ -2,7 +2,7 @@
 fn foo<T>() -> T { loop {} }
 
 fn test() {
-    let ref mut a: &mut FnMut((i8,), i16) = foo();
+    let ref mut a: &mut dyn FnMut((i8,), i16) = foo();
     a((0,), 0);
 }
 
index 792ff95200a1dd3ebcb606529bd42c354e450fa8..499fa7c1f27ac7837432b4bdf3e8b8466dc932d8 100644 (file)
@@ -15,18 +15,18 @@ trait Foo {
 
 struct Bar<T: ?Sized>(T);
 
-fn unsize_fat_ptr<'a>(x: &'a Bar<Foo + Send + 'a>) -> &'a Bar<Foo + 'a> {
+fn unsize_fat_ptr<'a>(x: &'a Bar<dyn Foo + Send + 'a>) -> &'a Bar<dyn Foo + 'a> {
     x
 }
 
-fn unsize_nested_fat_ptr(x: Arc<Foo + Send>) -> Arc<Foo> {
+fn unsize_nested_fat_ptr(x: Arc<dyn Foo + Send>) -> Arc<dyn Foo> {
     x
 }
 
 fn main() {
-    let x: Box<Bar<Foo + Send>> = Box::new(Bar([1,2]));
+    let x: Box<Bar<dyn Foo + Send>> = Box::new(Bar([1,2]));
     assert_eq!(unsize_fat_ptr(&*x).0.get(), [1, 2]);
 
-    let x: Arc<Foo + Send> = Arc::new([3, 4]);
+    let x: Arc<dyn Foo + Send> = Arc::new([3, 4]);
     assert_eq!(unsize_nested_fat_ptr(x).get(), [3, 4]);
 }
index 9c6c5bfe78c733a4e5d51aac4795f3d06c02ac54..4e01d4d3061f93409c5d0df304965424120cd703 100644 (file)
@@ -24,5 +24,5 @@ impl<P: TheTrait> Shape<P> for TheType<P::TheAssociatedType> {
 
 fn main() {
     let ball = TheType { t: PhantomData };
-    let handle: &Shape<()> = &ball;
+    let handle: &dyn Shape<()> = &ball;
 }
index 1fb4b8759bd58ffd91a9bfe013e8f5477ec36457..26e7358408f484c10ed78651361b17d10f381b55 100644 (file)
@@ -7,5 +7,5 @@ fn bar(&self, x: &Option<T>) -> bool
         where Option<T>: Ord { *x < *x }
     }
     impl Foo<X> for () {}
-    let _ = &() as &Foo<X>;
+    let _ = &() as &dyn Foo<X>;
 }
index 70e0ed9f7ce0167990e4926d00b180b8337346dd..05fd1b15d43d08179fa395a38ac27a97b72dbc08 100644 (file)
@@ -10,6 +10,6 @@ struct Foo<T: ?Sized> {
 
 fn main() {
     let foo: &Foo<i32> = &Foo { a: 1, b: false, c: 2i32 };
-    let foo_unsized: &Foo<Send> = foo;
+    let foo_unsized: &Foo<dyn Send> = foo;
     assert_eq!(mem::size_of_val(foo), mem::size_of_val(foo_unsized));
 }
index 728dd5ec8d0d6f40f44990d5254e0f01e7cae9cf..d96dc80ea719ceec61eda10b76e34164ac7afcc1 100644 (file)
@@ -2,7 +2,7 @@
 // Make sure this compiles without getting a linker error because of missing
 // drop-glue because the collector missed adding drop-glue for the closure:
 
-fn create_fn() -> Box<Fn()> {
+fn create_fn() -> Box<dyn Fn()> {
     let text = String::new();
 
     Box::new(move || { let _ = &text; })
index 38461db544ffb7806d4deeeff457caf4cea1a121..e5341ba7dbedde67dc232e703f869b51fe744511 100644 (file)
@@ -3,6 +3,6 @@
 // correctly
 
 fn main() {
-    let x : Vec<Box<Fn()>> = vec![Box::new(|| ())];
+    let x : Vec<Box<dyn Fn()>> = vec![Box::new(|| ())];
     x[0]()
 }
index 1420dff063cfab7caf357cfeaf734f15d41417d6..f48d549b3eb2cc2a386da36c71a7be430d93a7ce 100644 (file)
@@ -6,7 +6,7 @@ trait Text {
     fn to_string(&self) -> String;
   }
 
-  fn to_string(t: Box<Text>) {
+  fn to_string(t: Box<dyn Text>) {
     println!("{}", (*t).to_string());
   }
 
index d6af65f787d700384ff2cfca07271b01a2239f2f..408d8d866d862efdfb7989f471d0be0e00aa6dfb 100644 (file)
@@ -16,7 +16,7 @@ fn print(&self) {
     }
 }
 
-fn print_t(t: &T) {
+fn print_t(t: &dyn T) {
     t.print();
 }
 
@@ -27,6 +27,6 @@ fn print_s(s: &S) {
 pub fn main() {
     let s: Box<S> = box S { s: 5 };
     print_s(&*s);
-    let t: Box<T> = s as Box<T>;
+    let t: Box<dyn T> = s as Box<dyn T>;
     print_t(&*t);
 }
index 0b8139dd795146eb73ef5cb07959fa7677c6b996..968cf08916fd6dd2bfd840e605fb7c0c715d4df7 100644 (file)
@@ -13,5 +13,5 @@ trait Bar: for<'a> Foo<&'a ()> { }
 impl Bar for () {}
 
 fn main() {
-    (&() as &Bar).print(); // Segfault
+    (&() as &dyn Bar).print(); // Segfault
 }
index 0dfa8a75c4f00917e1881a616ee3b83edd982532..148cf527e7cb7799dd2b5de6b6827bb113048130 100644 (file)
 struct LocalG<T>(T);
 
 fn main() {
-    let virtual_localc : &Fn(_) -> LocalC = &LocalC;
+    let virtual_localc : &dyn Fn(_) -> LocalC = &LocalC;
     assert_eq!(virtual_localc(1), LocalC(1));
 
-    let virtual_localg : &Fn(_) -> LocalG<u32> = &LocalG;
+    let virtual_localg : &dyn Fn(_) -> LocalG<u32> = &LocalG;
     assert_eq!(virtual_localg(1), LocalG(1));
 
-    let virtual_remotec : &Fn(_) -> RemoteC = &RemoteC;
+    let virtual_remotec : &dyn Fn(_) -> RemoteC = &RemoteC;
     assert_eq!(virtual_remotec(1), RemoteC(1));
 
-    let virtual_remoteg : &Fn(_) -> RemoteG<u32> = &RemoteG;
+    let virtual_remoteg : &dyn Fn(_) -> RemoteG<u32> = &RemoteG;
     assert_eq!(virtual_remoteg(1), RemoteG(1));
 }
index cd7a0a22623a88191b4369bab9a29e16a22fde7c..967edfd44157688aa25659d824525b626b019fc5 100644 (file)
@@ -6,8 +6,8 @@ pub trait Trait { fn foo(&self) {} }
 pub struct Foo;
 
 impl Iterator for Foo {
-    type Item = Box<Trait>;
-    fn next(&mut self) -> Option<Box<Trait>> {
+    type Item = Box<dyn Trait>;
+    fn next(&mut self) -> Option<Box<dyn Trait>> {
         extern crate issue_41053;
         impl ::Trait for issue_41053::Test {
             fn foo(&self) {}
index edc4354b25336009599d4b2762c5ba01dfc72980..dcdd1c21ee527b664f591de9564f7bb63473c741 100644 (file)
@@ -3,5 +3,5 @@ trait Tc {}
 impl Tc for bool {}
 
 fn main() {
-    let _: &[&Tc] = &[&true];
+    let _: &[&dyn Tc] = &[&true];
 }
index cf4a698f516f373803f741d8dab6fb30e6b3b766..318e3099f98ba4139df86f2dbaf881881d5ed754 100644 (file)
@@ -12,9 +12,9 @@ fn foo() { }
 trait Baz {
 }
 
-impl Foo for (Bar, Baz) { }
+impl Foo for (Bar, dyn Baz) { }
 
 
 fn main() {
-    <(Bar, Baz) as Foo>::foo()
+    <(Bar, dyn Baz) as Foo>::foo()
 }
index 726a86142f6a5473033feeb39b5c20dbf486da04..c886f4b0a2d6bdadd801bc16f3396a4a8717422b 100644 (file)
@@ -6,7 +6,7 @@ fn main() {
 
 fn foo() {
     let b = mk::<
-        Forward<(Box<Future<Error = u32>>,)>,
+        Forward<(Box<dyn Future<Error = u32>>,)>,
     >();
     b.map_err(|_| ()).join();
 }
index ae9f4c8bdb523e83d1188272f2c0fbf287337ee5..3df319b683f47d03ebbc104087c474cecaedad44 100644 (file)
@@ -5,6 +5,6 @@
 use std::io;
 
 pub fn main() {
-    let stdout = &mut io::stdout() as &mut io::Write;
+    let stdout = &mut io::stdout() as &mut dyn io::Write;
     stdout.write(b"Hello!");
 }
index 357364ee6127384b3a27b97047e57593c2b837c9..a1ed3c36544010f9a176bfe8ba95a888da3c8d53 100644 (file)
@@ -1,10 +1,10 @@
 // run-pass
 #![allow(unused_variables)]
-fn id<'c, 'b>(f: &'c &'b Fn(&i32)) -> &'c &'b Fn(&'static i32) {
+fn id<'c, 'b>(f: &'c &'b dyn Fn(&i32)) -> &'c &'b dyn Fn(&'static i32) {
     f
 }
 
 fn main() {
-    let f: &Fn(&i32) = &|x| {};
+    let f: &dyn Fn(&i32) = &|x| {};
     id(&f);
 }
index 457fca3fedf0628b00800390103d4985e962e81a..fc869ae4fec261fd93cd721a40f456ca12f35f2e 100644 (file)
@@ -23,12 +23,12 @@ impl Debuggable for Thing {
     fn debug_name(&self) -> String { self.name.clone() }
 }
 
-fn print_name(x: &Debuggable)
+fn print_name(x: &dyn Debuggable)
 {
     println!("debug_name = {}", x.debug_name());
 }
 
 pub fn main() {
     let thing = Thing::new();
-    print_name(&thing as &Debuggable);
+    print_name(&thing as &dyn Debuggable);
 }
index 74d8d861a7d05cc86e50cba7aa247958455397c1..5a83d1c2ff9fd1b10fb3b989849611e0906374be 100644 (file)
@@ -24,12 +24,12 @@ impl EventLoop for UvEventLoop {
 }
 
 pub struct Scheduler {
-    event_loop: Box<EventLoop+'static>,
+    event_loop: Box<dyn EventLoop+'static>,
 }
 
 impl Scheduler {
 
-    pub fn new(event_loop: Box<EventLoop+'static>) -> Scheduler {
+    pub fn new(event_loop: Box<dyn EventLoop+'static>) -> Scheduler {
         Scheduler {
             event_loop: event_loop,
         }
@@ -37,5 +37,5 @@ pub fn new(event_loop: Box<EventLoop+'static>) -> Scheduler {
 }
 
 pub fn main() {
-    let _sched = Scheduler::new(box UvEventLoop::new() as Box<EventLoop>);
+    let _sched = Scheduler::new(box UvEventLoop::new() as Box<dyn EventLoop>);
 }
index bf919ed5b1073469f05338e8dbc817876de5e360..aa513277830128d70f11828117d92aa69fba4ea3 100644 (file)
@@ -19,7 +19,7 @@ fn bark(&self) -> String {
 pub fn main() {
     let snoopy = box Dog{name: "snoopy".to_string()};
     let bubbles = box Dog{name: "bubbles".to_string()};
-    let barker = [snoopy as Box<Barks>, bubbles as Box<Barks>];
+    let barker = [snoopy as Box<dyn Barks>, bubbles as Box<dyn Barks>];
 
     for pup in &barker {
         println!("{}", pup.bark());
index d3a2858873caf68f32c8490aac8829e68ab8787c..6fe9943d3689f7eee49cc37446eb3ef80b61bbd2 100644 (file)
@@ -21,11 +21,11 @@ impl Inner for isize {
 }
 
 struct Outer<'a> {
-    inner: &'a (Inner+'a)
+    inner: &'a (dyn Inner+'a)
 }
 
 impl<'a> Outer<'a> {
-    fn new(inner: &Inner) -> Outer {
+    fn new(inner: &dyn Inner) -> Outer {
         Outer {
             inner: inner
         }
@@ -34,7 +34,7 @@ fn new(inner: &Inner) -> Outer {
 
 pub fn main() {
     let inner: isize = 5;
-    let outer = Outer::new(&inner as &Inner);
+    let outer = Outer::new(&inner as &dyn Inner);
     outer.inner.print();
 }
 
@@ -45,11 +45,11 @@ fn dummy(&self, t: T) -> T { panic!() }
 }
 
 pub struct MyContainer<'a, T:'a> {
-    foos: Vec<&'a (MyTrait<T>+'a)> ,
+    foos: Vec<&'a (dyn MyTrait<T>+'a)> ,
 }
 
 impl<'a, T> MyContainer<'a, T> {
-    pub fn add (&mut self, foo: &'a MyTrait<T>) {
+    pub fn add (&mut self, foo: &'a dyn MyTrait<T>) {
         self.foos.push(foo);
     }
 }
index db77ca4375fc38c06047e216b06819e0d7875e15..303fb4fbc94165f64d2d33f60d0b4986fb820435 100644 (file)
@@ -19,6 +19,6 @@ impl T for A {
 
 fn main() {
     let a = A;
-    let br = &a as &B;
+    let br = &a as &dyn B;
     br.f();
 }
index f23a317c6ba6a234ea3c9f396e6206bd3c1cefd6..8859fbe6afb7b4ef01c5a3595d30828d8fe61866 100644 (file)
@@ -20,5 +20,5 @@ fn g(&self, _e: isize) {
 
 pub fn main() {
     let g : Box<HashMap<isize,isize>> = box HashMap::new();
-    let _g2 : Box<Graph<isize,isize>> = g as Box<Graph<isize,isize>>;
+    let _g2 : Box<dyn Graph<isize,isize>> = g as Box<dyn Graph<isize,isize>>;
 }
index 354797cb2a78474e46340be0afea6d7633266d87..b7a44ed86239584cca3d8013e72b8024c67a07c3 100644 (file)
@@ -9,7 +9,7 @@ fn call(&mut self, a:isize, b:isize) -> isize {
     }
 }
 
-fn squarei<'a>(x: isize, op: &'a mut OpInt) -> isize { op.call(x, x) }
+fn squarei<'a>(x: isize, op: &'a mut dyn OpInt) -> isize { op.call(x, x) }
 
 fn muli(x:isize, y:isize) -> isize { x * y }
 
@@ -17,7 +17,7 @@ pub fn main() {
     let mut f = |x, y| muli(x, y);
     {
         let g = &mut f;
-        let h = g as &mut OpInt;
+        let h = g as &mut dyn OpInt;
         squarei(3, h);
     }
 }
index d416048265fa51eb3f5114c86e61da86753c9ef1..d8bd83f0dc6adfba71918c8eec3f61cf60db59dd 100644 (file)
@@ -4,7 +4,7 @@
 #![feature(box_syntax)]
 
 pub enum Thing {
-    A(Box<Foo+'static>)
+    A(Box<dyn Foo+'static>)
 }
 
 pub trait Foo {
@@ -16,7 +16,7 @@ fn dummy(&self) { }
 impl Foo for Struct {}
 
 pub fn main() {
-    match Thing::A(box Struct as Box<Foo+'static>) {
+    match Thing::A(box Struct as Box<dyn Foo + 'static>) {
         Thing::A(_a) => 0,
     };
 }
index 820fffd1056a901213d4fbbd9151ea389017e317..c62405554b4d1d390b7b385f49a698e3edc0325b 100644 (file)
@@ -16,7 +16,7 @@ fn do_nothing(&self) {
     }
 
 impl<'a> B<'a> {
-    fn get_pa(&self) -> &'a IDummy { self.pa as &'a IDummy }
+    fn get_pa(&self) -> &'a dyn IDummy { self.pa as &'a dyn IDummy }
 }
 
 pub fn main() {
index cb7e009d074e51362af17ca1ec92c7d680d97b41..de833324bd20f4be22b8356ff04c47ca45fc3d71 100644 (file)
@@ -12,18 +12,18 @@ struct Foo { bar: Bar }
 impl FooBar for Bar {}
 
 trait Test {
-    fn get_immut(&self) -> &FooBar;
-    fn get_mut(&mut self) -> &mut FooBar;
+    fn get_immut(&self) -> &dyn FooBar;
+    fn get_mut(&mut self) -> &mut dyn FooBar;
 }
 
 macro_rules! generate_test { ($type_:path, $slf:ident, $field:expr) => (
     impl Test for $type_ {
-        fn get_immut(&$slf) -> &FooBar {
-            &$field as &FooBar
+        fn get_immut(&$slf) -> &dyn FooBar {
+            &$field as &dyn FooBar
         }
 
-        fn get_mut(&mut $slf) -> &mut FooBar {
-            &mut $field as &mut FooBar
+        fn get_mut(&mut $slf) -> &mut dyn FooBar {
+            &mut $field as &mut dyn FooBar
         }
     }
 )}
index 239c432e457bff89084a4b613dd4cfeba47a712e..31a305c31bee241058c1a4be6a88f759e858b29a 100644 (file)
@@ -7,9 +7,9 @@ fn dummy(&self) { }
 struct B;
 impl A for B {}
 
-fn foo(_: &mut A) {}
+fn foo(_: &mut dyn A) {}
 
 pub fn main() {
     let mut b = B;
-    foo(&mut b as &mut A);
+    foo(&mut b as &mut dyn A);
 }
index db49f354a3929e2e15e013b363ad239c574cfa88..d09dff3a6970905b972a571a3f53fc809627493c 100644 (file)
@@ -9,10 +9,10 @@ fn dummy(&self) { }
 impl A for B {}
 
 struct C<'a> {
-    foo: &'a mut (A+'a),
+    foo: &'a mut (dyn A+'a),
 }
 
-fn foo(a: &mut A) {
+fn foo(a: &mut dyn A) {
     C{ foo: a };
 }
 
index c81b9b1a10d0d8a7e9dd4ee2093abdefa3f88a01..3d87e1c203783b1b65787f9526da7900fc6416b5 100644 (file)
@@ -20,7 +20,7 @@ fn Ident_new() -> Ident {
     Ident {name: 0x6789ABCD }
 }
 
-pub fn light_fuse(fld: Box<bomb>) {
+pub fn light_fuse(fld: Box<dyn bomb>) {
     int3!();
     let f = || {
         int3!();
@@ -30,6 +30,6 @@ pub fn light_fuse(fld: Box<bomb>) {
 }
 
 pub fn main() {
-    let b = box S as Box<bomb>;
+    let b = box S as Box<dyn bomb>;
     light_fuse(b);
 }
index c4c95aa1aaed15b23439fe747c4a3af4d45e2c9f..cc0dd4fc14a0dc73ca7ff2425e8d250cc3f309ac 100644 (file)
@@ -52,7 +52,7 @@ fn bar(&self) -> String{
 
 pub fn main() {
     let n = X;
-    let s = &n as &Super;
+    let s = &n as &dyn Super;
     assert_eq!(s.bar(),"super bar".to_string());
     assert_eq!(s.foo(),"base foo".to_string());
     assert_eq!(s.foo1(),"base foo1".to_string());
index 4e14bdbd7342974db2431da7acb76e87fab59cfc..2698a3b17c6c25d4d444f26dc8005c0770a64380 100644 (file)
@@ -11,11 +11,11 @@ fn noop(&self) {}
 }
 
 fn main() {
-    let (a, b) = (&5u8 as &Bar, &9u8 as &Bar);
-    let (c, d): (&Bar, &Bar) = (a, b);
+    let (a, b) = (&5u8 as &dyn Bar, &9u8 as &dyn Bar);
+    let (c, d): (&dyn Bar, &dyn Bar) = (a, b);
 
-    let (a, b) = (Box::new(5u8) as Box<Bar>, Box::new(9u8) as Box<Bar>);
-    let (c, d): (&Bar, &Bar) = (&*a, &*b);
+    let (a, b) = (Box::new(5u8) as Box<dyn Bar>, Box::new(9u8) as Box<dyn Bar>);
+    let (c, d): (&dyn Bar, &dyn Bar) = (&*a, &*b);
 
-    let (c, d): (&Bar, &Bar) = (&5, &9);
+    let (c, d): (&dyn Bar, &dyn Bar) = (&5, &9);
 }
index b77f7b5d7822c1dff983d448e788f9e71bc51d85..42dc6a4b06e1dc30dee6534894fd3e4a7ca45def 100644 (file)
@@ -3,7 +3,7 @@
 
 struct A { a: Box<isize> }
 
-fn foo() -> Box<FnMut() -> isize + 'static> {
+fn foo() -> Box<dyn FnMut() -> isize + 'static> {
     let k: Box<_> = Box::new(22);
     let _u = A {a: k.clone()};
     let result  = || 22;
index aba4383c7344112ade0e632c6389de8bcb7dd05a..eb1872cc7f094f72705ee0bbf4442fc906accdb9 100644 (file)
@@ -4,7 +4,7 @@
 use std::fmt;
 
 struct Foo<'a> {
-    writer: &'a mut (Write+'a),
+    writer: &'a mut (dyn Write+'a),
     other: &'a str,
 }
 
@@ -22,7 +22,7 @@ fn borrowing_writer_from_struct_and_formatting_struct_field(foo: Foo) {
 
 fn main() {
     let mut w = Vec::new();
-    write!(&mut w as &mut Write, "").unwrap();
+    write!(&mut w as &mut dyn Write, "").unwrap();
     write!(&mut w, "").unwrap(); // should coerce
     println!("ok");
 
index 579b485a2a56e8fad97f1676d09cad178dc288f4..dd3ad2ef0ac0fd90655e7af2228748c0220aa556 100644 (file)
@@ -16,7 +16,7 @@ macro_rules! m { () => { i32 } }
 
     let x: m!() = m!();
     std::cell::Cell::<m!()>::new(m!());
-    impl<T> std::ops::Index<m!()> for Trait<(m!(), T)>
+    impl<T> std::ops::Index<m!()> for dyn Trait<(m!(), T)>
         where T: Trait<m!()>
     {
         type Output = m!();
index b5ba1f9455697a192798998abfc738b04f64dc80..acd4a8465b0757dcec4aa982b4b90d93fb11f6ed 100644 (file)
@@ -10,13 +10,13 @@ pub trait Service {
 pub struct S<T>(T);
 
 impl Service for ClientMap {
-    type Request = S<Box<Fn(i32)>>;
+    type Request = S<Box<dyn Fn(i32)>>;
     fn call(&self, _req: Self::Request) {}
 }
 
 
 impl Service for ClientMap2 {
-    type Request = (Box<Fn(i32)>,);
+    type Request = (Box<dyn Fn(i32)>,);
     fn call(&self, _req: Self::Request) {}
 }
 
index 075d266d34d740a5dc611dcb1fa6e3fb73c402c3..fc0db03e3a96894350a9611f398c150de1afebe3 100644 (file)
@@ -42,7 +42,7 @@ fn test4(x: &Foo, a: isize) -> isize {
     x.extension_method(a)
 }
 
-fn test5(x: &Bar, a: isize) -> isize {
+fn test5(x: &dyn Bar, a: isize) -> isize {
     // Test calling method on trait object
     x.extension_method(a)
 }
@@ -88,11 +88,11 @@ fn test_closure<F>(f: &F, x: i32, y: i32) -> i32
     f(x, y)
 }
 
-fn test_fn_object(f: &Fn(i32, i32) -> i32, x: i32, y: i32) -> i32 {
+fn test_fn_object(f: &dyn Fn(i32, i32) -> i32, x: i32, y: i32) -> i32 {
     f(x, y)
 }
 
-fn test_fn_impl(f: &&Fn(i32, i32) -> i32, x: i32, y: i32) -> i32 {
+fn test_fn_impl(f: &&dyn Fn(i32, i32) -> i32, x: i32, y: i32) -> i32 {
     // This call goes through the Fn implementation for &Fn provided in
     // core::ops::impls. It expands to a static Fn::call() that calls the
     // Fn::call() implementation of the object shim underneath.
@@ -174,7 +174,7 @@ fn main() {
     let closure = |x: i32, y: i32| { r*(x + (y*2)) };
     assert_eq!(test_fn_const_call(&closure), 294);
     assert_eq!(test_closure(&closure, 100, 1), 306);
-    let function_object = &closure as &Fn(i32, i32) -> i32;
+    let function_object = &closure as &dyn Fn(i32, i32) -> i32;
     assert_eq!(test_fn_object(function_object, 100, 2), 312);
     assert_eq!(test_fn_impl(&function_object, 100, 3), 318);
     assert_eq!(test_fn_direct_call(&closure, 100, 4), 324);
index 03b111e93dd2529961699c8d1f742b4032aee4d1..5c1f1c3b70135ce17f461780fb7ba32ea74ad958 100644 (file)
@@ -37,7 +37,7 @@ fn next(&mut self) -> Option<A::Item> {
 }
 
 // Make sure we actually codegen a version of the function
-pub fn do_stuff(mut f: Foo<Box<Iterator<Item=u32>>, Box<Iterator<Item=u32>>>) {
+pub fn do_stuff(mut f: Foo<Box<dyn Iterator<Item=u32>>, Box<dyn Iterator<Item=u32>>>) {
     let _x = f.next();
 }
 
index b673345db7045efa6b759e6c30a899801cf6059c..f3dcc6b85fd98a537443a103812d17392b83e7c4 100644 (file)
@@ -4,12 +4,12 @@
 use std::ops::CoerceUnsized;
 use std::marker::Unsize;
 
-fn identity_coercion(x: &(Fn(u32)->u32 + Send)) -> &Fn(u32)->u32 {
+fn identity_coercion(x: &(dyn Fn(u32)->u32 + Send)) -> &dyn Fn(u32)->u32 {
     x
 }
 fn fn_coercions(f: &fn(u32) -> u32) ->
     (unsafe fn(u32) -> u32,
-     &(Fn(u32) -> u32+Send))
+     &(dyn Fn(u32) -> u32+Send))
 {
     (*f, f)
 }
@@ -35,8 +35,8 @@ impl<'a, T: ?Sized+Unsize<U>, U: ?Sized>
     p
 }
 
-fn coerce_fat_ptr_wrapper(p: PtrWrapper<Fn(u32) -> u32+Send>)
-                          -> PtrWrapper<Fn(u32) -> u32> {
+fn coerce_fat_ptr_wrapper(p: PtrWrapper<dyn Fn(u32) -> u32+Send>)
+                          -> PtrWrapper<dyn Fn(u32) -> u32> {
     p
 }
 
@@ -65,7 +65,7 @@ fn main() {
     let z = coerce_fat_ptr_wrapper(PtrWrapper(2,3,(),&square_local));
     assert_eq!((z.3)(6), 36);
 
-    let z: PtrWrapper<Fn(u32) -> u32> =
+    let z: PtrWrapper<dyn Fn(u32) -> u32> =
         coerce_ptr_wrapper_poly(PtrWrapper(2,3,(),&square_local));
     assert_eq!((z.3)(6), 36);
 }
index 328c8c502cbc9ea344a0d53158ccb7fc9871441b..6583852aa9bb64b1c475e7b1df5c4c182d1246f1 100644 (file)
@@ -63,7 +63,7 @@ fn compare_au8(a: *const [u8], b: *const [u8]) -> ComparisonResults {
     }
 }
 
-fn compare_foo<'a>(a: *const (Foo+'a), b: *const (Foo+'a)) -> ComparisonResults {
+fn compare_foo<'a>(a: *const (dyn Foo+'a), b: *const (dyn Foo+'a)) -> ComparisonResults {
     ComparisonResults {
         lt: a < b,
         le: a <= b,
@@ -74,7 +74,7 @@ fn compare_foo<'a>(a: *const (Foo+'a), b: *const (Foo+'a)) -> ComparisonResults
     }
 }
 
-fn simple_eq<'a>(a: *const (Foo+'a), b: *const (Foo+'a)) -> bool {
+fn simple_eq<'a>(a: *const (dyn Foo+'a), b: *const (dyn Foo+'a)) -> bool {
     let result = a == b;
     result
 }
@@ -128,7 +128,7 @@ fn main() {
     let u32_ = (4u32, 5u32);
 
     // check ordering for ptrs
-    let buf: &mut [*const Foo] = &mut [
+    let buf: &mut [*const dyn Foo] = &mut [
         &u8_, &u8_.0,
         &u32_, &u32_.0,
     ];
index b35c5445a440577d0aacf346e6d9af6dee32aad2..5539518c37072d26bd8c1c5cb021d887598ff3eb 100644 (file)
@@ -18,13 +18,13 @@ fn printme(&self) {
     }
 }
 
-fn g(x: Box<Trait>) {
+fn g(x: Box<dyn Trait>) {
     x.printme();
-    let y: &Trait = &*x;
+    let y: &dyn Trait = &*x;
     y.printme();
 }
 
 fn main() {
     f(box 1234);
-    g(box Struct as Box<Trait>);
+    g(box Struct as Box<dyn Trait>);
 }
index 969868486e6eb31e51a24dbe5338db79b06f78ed..79c9f7dc01103cc38f2560622cfbdf15cfbfd256 100644 (file)
@@ -4,7 +4,7 @@
 
 // pretty-expanded FIXME #23616
 
-fn unique() -> Box<FnMut()+'static> { return Box::new(|| ()); }
+fn unique() -> Box<dyn FnMut()+'static> { return Box::new(|| ()); }
 
 pub fn main() {
 }
index 676b3507c57409eabfd3976ddf623123e6163412..104f5be7767d35fc9febece36c1e7770bfc35799 100644 (file)
@@ -4,7 +4,7 @@
 
 // pretty-expanded FIXME #23616
 
-fn unique() -> Box<FnMut()+'static> { Box::new(|| ()) }
+fn unique() -> Box<dyn FnMut()+'static> { Box::new(|| ()) }
 
 pub fn main() {
 }
index cf836c1a7deda00ede11c742f78701ff5ea4f1b8..cd61dea03788fa9ab3ae6c2c5db18bf0b7f6ebb1 100644 (file)
@@ -10,23 +10,23 @@ fn foo(&self) { }
 }
 
 struct SomeStruct {
-    t: Box<Test>,
-    u: Box<Test+'static>,
+    t: Box<dyn Test>,
+    u: Box<dyn Test+'static>,
 }
 
-fn a(t: Box<Test>, mut ss: SomeStruct) {
+fn a(t: Box<dyn Test>, mut ss: SomeStruct) {
     ss.t = t;
 }
 
-fn b(t: Box<Test+'static>, mut ss: SomeStruct) {
+fn b(t: Box<dyn Test+'static>, mut ss: SomeStruct) {
     ss.t = t;
 }
 
-fn c(t: Box<Test>, mut ss: SomeStruct) {
+fn c(t: Box<dyn Test>, mut ss: SomeStruct) {
     ss.u = t;
 }
 
-fn d(t: Box<Test+'static>, mut ss: SomeStruct) {
+fn d(t: Box<dyn Test+'static>, mut ss: SomeStruct) {
     ss.u = t;
 }
 
index 3f69c9274889ceb586406db02b0a049fcb9a08c8..9212f2802c0180572f34ae6d25bacfe1b54c93c4 100644 (file)
@@ -10,21 +10,21 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a Box<Test>,
-    u: &'a Box<Test+'a>,
+    t: &'a Box<dyn Test>,
+    u: &'a Box<dyn Test+'a>,
 }
 
-fn a<'a>(t: &'a Box<Test>, mut ss: SomeStruct<'a>) {
+fn a<'a>(t: &'a Box<dyn Test>, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn b<'a>(t: &'a Box<Test>, mut ss: SomeStruct<'a>) {
+fn b<'a>(t: &'a Box<dyn Test>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
 // see also compile-fail/object-lifetime-default-from-rptr-box-error.rs
 
-fn d<'a>(t: &'a Box<Test+'a>, mut ss: SomeStruct<'a>) {
+fn d<'a>(t: &'a Box<dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
index dc9e292f0de388e4a6ac69b0672f7c5bea78e6e3..061f3a116fcbb9dee6c993488cfdec6569a81fa9 100644 (file)
@@ -10,23 +10,23 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a mut Test,
-    u: &'a mut (Test+'a),
+    t: &'a mut dyn Test,
+    u: &'a mut (dyn Test+'a),
 }
 
-fn a<'a>(t: &'a mut Test, mut ss: SomeStruct<'a>) {
+fn a<'a>(t: &'a mut dyn Test, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn b<'a>(t: &'a mut Test, mut ss: SomeStruct<'a>) {
+fn b<'a>(t: &'a mut dyn Test, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
-fn c<'a>(t: &'a mut (Test+'a), mut ss: SomeStruct<'a>) {
+fn c<'a>(t: &'a mut (dyn Test+'a), mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn d<'a>(t: &'a mut (Test+'a), mut ss: SomeStruct<'a>) {
+fn d<'a>(t: &'a mut (dyn Test+'a), mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
index 061f71b9ae6bfc50e33df9a126aa65169c675d3b..cfa4af0d7a53fb5b0102783e7f34a04e94e4cfb4 100644 (file)
@@ -12,30 +12,30 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a Test,
-    u: &'a (Test+'a),
+    t: &'a dyn Test,
+    u: &'a (dyn Test+'a),
 }
 
-fn a<'a>(t: &'a Test, mut ss: SomeStruct<'a>) {
+fn a<'a>(t: &'a dyn Test, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn b<'a>(t: &'a Test, mut ss: SomeStruct<'a>) {
+fn b<'a>(t: &'a dyn Test, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
-fn c<'a>(t: &'a (Test+'a), mut ss: SomeStruct<'a>) {
+fn c<'a>(t: &'a (dyn Test+'a), mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn d<'a>(t: &'a (Test+'a), mut ss: SomeStruct<'a>) {
+fn d<'a>(t: &'a (dyn Test+'a), mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
-fn e<'a>(_: &'a (Display+'static)) {}
+fn e<'a>(_: &'a (dyn Display+'static)) {}
 
 fn main() {
     // Inside a function body, we can just infer both
     // lifetimes, to allow &'tmp (Display+'static).
-    e(&0 as &Display);
+    e(&0 as &dyn Display);
 }
index 455af78c7a08e0cd4eb246e1503b679f3b44dc85..7f24ab2cbb5ff7559129449b25d70aef142584de 100644 (file)
@@ -21,7 +21,7 @@ fn get(&self) -> i32 {
 
 fn main() {
     let x = 22;
-    let x1: &SomeTrait<SomeType=i32> = &x;
+    let x1: &dyn SomeTrait<SomeType=i32> = &x;
     let y = get_int(x1);
     assert_eq!(x, y);
 }
index 872b9d3e9160b680fa6bb28c6efbb5b1b170773b..47196f108c02c6831f10205fa64593770aea5ff2 100644 (file)
@@ -17,7 +17,7 @@ fn bar(&mut self) -> usize {
     }
 }
 
-fn do_it_mut(obj: &mut Foo) {
+fn do_it_mut(obj: &mut dyn Foo) {
     let x = obj.bar();
     let y = obj.foo();
     assert_eq!(x, y);
@@ -25,14 +25,14 @@ fn do_it_mut(obj: &mut Foo) {
     do_it_imm(obj, y);
 }
 
-fn do_it_imm(obj: &Foo, v: usize) {
+fn do_it_imm(obj: &dyn Foo, v: usize) {
     let y = obj.foo();
     assert_eq!(v, y);
 }
 
 pub fn main() {
     let mut x: usize = 22;
-    let obj = &mut x as &mut Foo;
+    let obj = &mut x as &mut dyn Foo;
     do_it_mut(obj);
     do_it_imm(obj, 23);
     do_it_mut(obj);
index a96772bfb63122185ee9a9614d498d19e724baf7..58327237494edba475e68bc9a1d2a728c03e5324 100644 (file)
@@ -20,10 +20,10 @@ fn foo(&self) -> usize {
 }
 
 pub fn main() {
-    let foos: Vec<Box<FooTrait>> = vec![
-        box BarStruct{ x: 0 } as Box<FooTrait>,
-        box BarStruct{ x: 1 } as Box<FooTrait>,
-        box BarStruct{ x: 2 } as Box<FooTrait>
+    let foos: Vec<Box<dyn FooTrait>> = vec![
+        box BarStruct{ x: 0 } as Box<dyn FooTrait>,
+        box BarStruct{ x: 1 } as Box<dyn FooTrait>,
+        box BarStruct{ x: 2 } as Box<dyn FooTrait>
     ];
 
     for i in 0..foos.len() {
index 6ca5233b198e0f8f8e6f5c84eda183f89b6b7cd4..69984fbb62f1467bbcc8309bcbb34890db1e3995 100644 (file)
@@ -19,6 +19,6 @@ fn foo(self: Box<BarStruct>) -> usize {
 }
 
 pub fn main() {
-    let foo = box BarStruct{ x: 22 } as Box<FooTrait>;
+    let foo = box BarStruct{ x: 22 } as Box<dyn FooTrait>;
     assert_eq!(22, foo.foo());
 }
index ff484418c1dbe14212aeb8411019820fe002c3cd..1afab9a1ffbe7890625230c7ecc32397bbbae58d 100644 (file)
@@ -3,7 +3,7 @@
 // This is a bit tricky due to rust-call ABI.
 
 
-fn foo(f: &mut FnMut(isize) -> isize) -> isize {
+fn foo(f: &mut dyn FnMut(isize) -> isize) -> isize {
     f(22)
 }
 
index 0d0136bc29ac7cf08b49347d4c9a10286b638844..38087bc8710fcf4cc63316cdeaac583894ce1734 100644 (file)
@@ -3,7 +3,7 @@
 // This is a bit tricky due to rust-call ABI.
 
 
-fn foo(f: &mut FnMut(isize, isize) -> isize) -> isize {
+fn foo(f: &mut dyn FnMut(isize, isize) -> isize) -> isize {
     f(1, 2)
 }
 
index bbea6a909c880c155ccc20fa365e06fe019126a6..9a7bfaa9bf4f019ea8fa7c920ec3af8e64d2745a 100644 (file)
@@ -3,7 +3,7 @@
 // This is a bit tricky due to rust-call ABI.
 
 
-fn foo(f: &mut FnMut() -> isize) -> isize {
+fn foo(f: &mut dyn FnMut() -> isize) -> isize {
     f()
 }
 
index 3798a4fc5cba1167993e082ce868f5f8418cb111..9867cc56406ef109dd2c4a2fed8c7c9b1c831783 100644 (file)
@@ -33,7 +33,7 @@ fn main() {
     assert::<Box<[u8]>>();
 
     trait Trait: UnwindSafe {}
-    assert::<Box<Trait>>();
+    assert::<Box<dyn Trait>>();
 
     fn bar<T>() {
         assert::<Mutex<T>>();
index b1b03eae5db5f139f1151de4a55eb8dddacd3359..c32e3f17880db13d02562e2fdff72150d0d096de 100644 (file)
@@ -28,19 +28,19 @@ fn test_unused1() {
 fn test_single1() {
     use foo1::Bar;
 
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 fn test_list1() {
     use foo1::{Bar,Baz};
 
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 fn test_glob1() {
     use foo1::*;
 
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 // private type, public value
@@ -93,21 +93,21 @@ fn test_single3() {
     use foo3::Bar;
 
     Bar();
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 fn test_list3() {
     use foo3::{Bar,Baz};
 
     Bar();
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 fn test_glob3() {
     use foo3::*;
 
     Bar();
-    let _x: Box<Bar>;
+    let _x: Box<dyn Bar>;
 }
 
 fn main() {
index df69db1cc9a25745108f2681925dd996e0990cf5..511a35b25a3e8fc766ad2e3e8ec362ef788f6ec5 100644 (file)
@@ -78,7 +78,7 @@ fn main() {
     let mut u32_ = (4u32, 5u32);
 
     // check ordering for ptrs
-    let buf: &mut [*const Foo] = &mut [
+    let buf: &mut [*const dyn Foo] = &mut [
         &u8_, &u8_.0,
         &u32_, &u32_.0,
     ];
@@ -90,7 +90,7 @@ fn main() {
     assert_inorder(buf);
 
     // check ordering for mut ptrs
-    let buf: &mut [*mut Foo] = &mut [
+    let buf: &mut [*mut dyn Foo] = &mut [
         &mut u8_, &mut u8_.0,
         &mut u32_, &mut u32_.0,
     ];
index 204f4f8130dea722137843a8d144e902c7283d80..3815498f86fbb8ee8f227f3cf513f51cefaf3dad 100644 (file)
@@ -9,7 +9,7 @@ trait Foo {
     fn dummy(&self) { }
 }
 
-fn foo<'a>(x: Box<Foo + 'a>) {
+fn foo<'a>(x: Box<dyn Foo + 'a>) {
 }
 
 fn bar<'a, T: 'a>() {
index 85c9c64c64386065a1e3b193e02010a007519147..4b47ed8c6aeb7120ed4c56888112208bafa0d365 100644 (file)
@@ -12,8 +12,8 @@ fn get(&self) -> isize {
     }
 }
 
-fn make_object<'a,A:SomeTrait+'a>(v: A) -> Box<SomeTrait+'a> {
-    box v as Box<SomeTrait+'a>
+fn make_object<'a,A:SomeTrait+'a>(v: A) -> Box<dyn SomeTrait+'a> {
+    box v as Box<dyn SomeTrait+'a>
 }
 
 fn main() {
index 6545ddf72c76a00bfa82521cf52fb0fcb383cd49..43640079777a343cf5b81f86b64d3e0c96e6cec1 100644 (file)
@@ -2,10 +2,10 @@
 #![allow(non_camel_case_types)]
 
 struct closure_box<'a> {
-    cl: Box<FnMut() + 'a>,
+    cl: Box<dyn FnMut() + 'a>,
 }
 
-fn box_it<'a>(x: Box<FnMut() + 'a>) -> closure_box<'a> {
+fn box_it<'a>(x: Box<dyn FnMut() + 'a>) -> closure_box<'a> {
     closure_box {cl: x}
 }
 
index 24c0cf53317e090d76df14cc55136cddd30251f5..0b5510489fb45a9b4b7beedab337e80cc4abc170 100644 (file)
@@ -13,9 +13,9 @@ trait AstConv<'tcx> {
     fn tcx<'a>(&'a self) -> &'a ctxt<'tcx>;
 }
 
-fn foo(conv: &AstConv) { }
+fn foo(conv: &dyn AstConv) { }
 
-fn bar<'tcx>(conv: &AstConv<'tcx>) {
+fn bar<'tcx>(conv: &dyn AstConv<'tcx>) {
     foo(conv)
 }
 
index c71e47db22d4155220d2ed192173105b466853bf..cc2bde78d8594b3a6d488a9b75acd9d603455398 100644 (file)
@@ -15,14 +15,14 @@ fn poly_invoke<'c, T: Trait<'c>>(x: &'c T) -> (isize, isize) {
     (l,s)
 }
 
-fn object_invoke1<'d>(x: &'d Trait<'d>) -> (isize, isize) {
+fn object_invoke1<'d>(x: &'d dyn Trait<'d>) -> (isize, isize) {
     let l = x.long();
     let s = x.short();
     (l,s)
 }
 
 struct Struct1<'e> {
-    f: &'e (Trait<'e>+'e)
+    f: &'e (dyn Trait<'e>+'e)
 }
 
 fn field_invoke1<'f, 'g>(x: &'g Struct1<'f>) -> (isize,isize) {
@@ -32,10 +32,10 @@ fn field_invoke1<'f, 'g>(x: &'g Struct1<'f>) -> (isize,isize) {
 }
 
 struct Struct2<'h, 'i:'h> {
-    f: &'h (Trait<'i>+'h)
+    f: &'h (dyn Trait<'i>+'h)
 }
 
-fn object_invoke2<'j, 'k>(x: &'k Trait<'j>) -> isize {
+fn object_invoke2<'j, 'k>(x: &'k dyn Trait<'j>) -> isize {
     x.short()
 }
 
@@ -70,10 +70,10 @@ fn short<'b>(&'b self) -> isize {
     }
 }
 
-impl<'t> MakerTrait for Box<Trait<'t>+'static> {
-    fn mk() -> Box<Trait<'t>+'static> {
+impl<'t> MakerTrait for Box<dyn Trait<'t>+'static> {
+    fn mk() -> Box<dyn Trait<'t>+'static> {
         let tup: Box<(isize, isize)> = box (4,5);
-        tup as Box<Trait>
+        tup as Box<dyn Trait>
     }
 }
 
@@ -105,7 +105,7 @@ fn mk(l:List<'t>) -> &'t List<'t> {
 
 pub fn main() {
     let t = (2,3);
-    let o = &t as &Trait;
+    let o = &t as &dyn Trait;
     let s1 = Struct1 { f: o };
     let s2 = Struct2 { f: o };
     assert_eq!(poly_invoke(&t), (2,3));
@@ -114,7 +114,7 @@ pub fn main() {
     assert_eq!(object_invoke2(&t), 3);
     assert_eq!(field_invoke2(&s2), 3);
 
-    let m : Box<Trait> = make_val();
+    let m : Box<dyn Trait> = make_val();
     // assert_eq!(object_invoke1(&*m), (4,5));
     //            ~~~~~~~~~~~~~~~~~~~
     // this call yields a compilation error; see compile-fail/dropck-object-cycle.rs
index cbd88ebde0d1e3a90057144743875b1d03e4c781..83949ddba3d1ee96126c4a983ba1eeb4d216ca8e 100644 (file)
@@ -7,13 +7,13 @@
 // that `x` is in.
 // pretty-expanded FIXME #23616
 
-fn has_same_region(f: Box<for<'a> FnMut(&'a isize, Box<FnMut(&'a isize)>)>) {
+fn has_same_region(f: Box<dyn for<'a> FnMut(&'a isize, Box<dyn FnMut(&'a isize)>)>) {
     // `f` should be the type that `wants_same_region` wants, but
     // right now the compiler complains that it isn't.
     wants_same_region(f);
 }
 
-fn wants_same_region(_f: Box<for<'b> FnMut(&'b isize, Box<FnMut(&'b isize)>)>) {
+fn wants_same_region(_f: Box<dyn for<'b> FnMut(&'b isize, Box<dyn FnMut(&'b isize)>)>) {
 }
 
 pub fn main() {
index a1da966659a2160a1ac2061e006196bff79725ca..9570359c69e315a89a230da74692588e044f4d18 100644 (file)
@@ -8,21 +8,21 @@
 #![allow(unused_variables)]
 
 // Should pass region checking.
-fn ok(f: Box<FnMut(&usize)>) {
+fn ok(f: Box<dyn FnMut(&usize)>) {
     // Here, g is a function that can accept a usize pointer with
     // lifetime r, and f is a function that can accept a usize pointer
     // with any lifetime.  The assignment g = f should be OK (i.e.,
     // 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 usize)> = Box::new(|x| { });
+    let mut g: Box<dyn for<'r> FnMut(&'r usize)> = 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(&usize)>) {
-    let mut g: Box<for<'r> FnMut(&'r usize)> = Box::new(|_| {});
+fn ok_inferred(f: Box<dyn FnMut(&usize)>) {
+    let mut g: Box<dyn for<'r> FnMut(&'r usize)> = Box::new(|_| {});
     g = f;
 }
 
index dff36e6d183b918ab18355f25710ab8fa85631c3..6aa5d8217a466b496fc82f813e1751f558b9005d 100644 (file)
@@ -8,7 +8,7 @@
 // contains region pointers
 // pretty-expanded FIXME #23616
 
-struct foo(Box<FnMut(&isize)+'static>);
+struct foo(Box<dyn FnMut(&isize)+'static>);
 
 fn take_foo<T:'static>(x: T) {}
 
index 189f6172029688b33872beb9de460416fa694b3a..c8106f32c65c257f68071d359c1484d6276d83b4 100644 (file)
 
 pub fn main() {
     fn explicit() {
-        fn test<F>(_x: Option<Box<F>>) where F: FnMut(Box<for<'a> FnMut(&'a isize)>) {}
-        test(Some(box |_f: Box<for<'a> FnMut(&'a isize)>| {}));
+        fn test<F>(_x: Option<Box<F>>) where F: FnMut(Box<dyn for<'a> FnMut(&'a isize)>) {}
+        test(Some(box |_f: Box<dyn for<'a> FnMut(&'a isize)>| {}));
     }
 
     // The code below is shorthand for the code above (and more likely
     // to represent what one encounters in practice).
     fn implicit() {
-        fn test<F>(_x: Option<Box<F>>) where F: FnMut(Box<        FnMut(&   isize)>) {}
-        test(Some(box |_f: Box<        FnMut(&   isize)>| {}));
+        fn test<F>(_x: Option<Box<F>>) where F: FnMut(Box<dyn        FnMut(&   isize)>) {}
+        test(Some(box |_f: Box<dyn        FnMut(&   isize)>| {}));
     }
 
     explicit();
index cd095f6f3a4a3613aafacc411cc2d8008615d1cb..96c71b084b13e941688d9a7f99738fddcbaf7cbf 100644 (file)
 use std::rc::Rc;
 
 #[derive(Clone)]
-enum CachedMir<'mir> {
+enum Cached<'mir> {
     Ref(&'mir String),
     Owned(Rc<String>),
 }
 
-impl<'mir> CachedMir<'mir> {
+impl<'mir> Cached<'mir> {
     fn get_ref<'a>(&'a self) -> &'a String {
         match *self {
-            CachedMir::Ref(r) => r,
-            CachedMir::Owned(ref rc) => &rc,
+            Cached::Ref(r) => r,
+            Cached::Owned(ref rc) => &rc,
         }
     }
 }
index f26ef85ef72347d930aa98c494230ad6a2a6f137..aec05161c1afbca2d57e7fdf7c7836db6136b889 100644 (file)
@@ -44,7 +44,7 @@ fn foo(&mut self) -> isize {
 
     fn elaborate_bounds(
         &mut self,
-        mut mk_cand: Box<for<'b> FnMut(&mut Foo<'b, 'tcx>) -> isize>)
+        mut mk_cand: Box<dyn for<'b> FnMut(&mut Foo<'b, 'tcx>) -> isize>)
         -> isize
     {
         mk_cand(self)
index 6d00f7501ca9f2e18135f8749763330c4747f796..09cd56220323d84a00756534297b9ff1a7d51c78 100644 (file)
@@ -2,10 +2,10 @@
 #![allow(non_camel_case_types)]
 
 struct closure_box<'a> {
-    cl: Box<FnMut() + 'a>,
+    cl: Box<dyn FnMut() + 'a>,
 }
 
-fn box_it<'a>(x: Box<FnMut() + 'a>) -> closure_box<'a> {
+fn box_it<'a>(x: Box<dyn FnMut() + 'a>) -> closure_box<'a> {
     closure_box {cl: x}
 }
 
index 242142588eafe7fafa8673ab116211d4d5069bef..679bf4dd8117c5506b01d43e9873e1e80c0f09b2 100644 (file)
@@ -21,10 +21,10 @@ impl<'d> M for P<'d> {
     fn n(&self) -> u8 { *self.g }
 }
 
-fn extension<'e>(x: &'e E<'e>) -> Box<M+'e> {
+fn extension<'e>(x: &'e E<'e>) -> Box<dyn M+'e> {
     loop {
         let p = P { g: x.m() };
-        return Box::new(p) as Box<M+'e>;
+        return Box::new(p) as Box<dyn M+'e>;
     }
 }
 
index debbe665a89f9389a1cf7f499087f11b95da24e1..944157d0b20094cda0d4a2379a465ef3708822a3 100644 (file)
@@ -4,8 +4,8 @@
 use std::error::Error;
 
 fn main() {
-    let _err1: Box<Error + Send + Sync> = From::from("test".to_string());
-    let _err2: Box<Error> = From::from("test".to_string());
-    let _err3: Box<Error + Send + Sync + 'static> = From::from("test");
-    let _err4: Box<Error> = From::from("test");
+    let _err1: Box<dyn Error + Send + Sync> = From::from("test".to_string());
+    let _err2: Box<dyn Error> = From::from("test".to_string());
+    let _err3: Box<dyn Error + Send + Sync + 'static> = From::from("test");
+    let _err4: Box<dyn Error> = From::from("test");
 }
index cb4a67f609d958a3f05da85ae97242381dad63b1..bf1ba8a643fea8f89950724a933b5d34598552da 100644 (file)
@@ -8,13 +8,13 @@
 use std::string::ToString;
 use cci_class_cast::kitty::cat;
 
-fn print_out(thing: Box<ToString>, expected: String) {
+fn print_out(thing: Box<dyn ToString>, expected: String) {
   let actual = (*thing).to_string();
   println!("{}", actual);
   assert_eq!(actual.to_string(), expected);
 }
 
 pub fn main() {
-  let nyan: Box<ToString> = box cat(0, 2, "nyan".to_string()) as Box<ToString>;
+  let nyan: Box<dyn ToString> = box cat(0, 2, "nyan".to_string()) as Box<dyn ToString>;
   print_out(nyan, "nyan".to_string());
 }
index 5ce6538fcb3617f6f9522f10151ee0930fed51a7..55975cbdb5342ee491a78f37fe9d95017b9985f7 100644 (file)
@@ -79,7 +79,7 @@ fn cat(in_x: usize, in_y: isize, in_name: String) -> cat {
 }
 
 
-fn annoy_neighbors(critter: &mut noisy) {
+fn annoy_neighbors(critter: &mut dyn noisy) {
     for _i in 0_usize..10 { critter.speak(); }
 }
 
index 7fa60da6e57625bfd3f55ae1647de0e5709273f1..1019bb30015a94302ee12798a005296d1748b1e1 100644 (file)
@@ -55,6 +55,6 @@ fn cat(in_x : usize, in_y : isize, in_name: String) -> cat {
 
 pub fn main() {
     let mut nyan = cat(0, 2, "nyan".to_string());
-    let mut nyan: &mut noisy = &mut nyan;
+    let mut nyan: &mut dyn noisy = &mut nyan;
     nyan.speak();
 }
index 2b10a46e8e25dd2c3b253b52e6fe06ec047bd36a..947690b51f422ab70ec1bfb46dd4eb83adbb1321 100644 (file)
@@ -53,13 +53,13 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
-fn print_out(thing: Box<ToString>, expected: String) {
+fn print_out(thing: Box<dyn ToString>, expected: String) {
   let actual = (*thing).to_string();
   println!("{}", actual);
   assert_eq!(actual.to_string(), expected);
 }
 
 pub fn main() {
-  let nyan: Box<ToString> = box cat(0, 2, "nyan".to_string()) as Box<ToString>;
+  let nyan: Box<dyn ToString> = box cat(0, 2, "nyan".to_string()) as Box<dyn ToString>;
   print_out(nyan, "nyan".to_string());
 }
index 5e3b5942a8209b402a2b125ff5ff3f05f7dac0ce..87629665bc2bd6dc015fb558f3b0eb8599c9dd31 100644 (file)
@@ -22,9 +22,9 @@ fn main() {
     assert_eq!(size_of::<&mut [isize]>(), size_of::<Option<&mut [isize]>>());
 
     // Traits - Box<Trait> / &Trait / &mut Trait
-    assert_eq!(size_of::<Box<Trait>>(), size_of::<Option<Box<Trait>>>());
-    assert_eq!(size_of::<&Trait>(), size_of::<Option<&Trait>>());
-    assert_eq!(size_of::<&mut Trait>(), size_of::<Option<&mut Trait>>());
+    assert_eq!(size_of::<Box<dyn Trait>>(), size_of::<Option<Box<dyn Trait>>>());
+    assert_eq!(size_of::<&dyn Trait>(), size_of::<Option<&dyn Trait>>());
+    assert_eq!(size_of::<&mut dyn Trait>(), size_of::<Option<&mut dyn Trait>>());
 
     // Pointers - Box<T>
     assert_eq!(size_of::<Box<isize>>(), size_of::<Option<Box<isize>>>());
index 0a48725cbe44ae6a5facb93fe424597be573f53d..e1a865fa5039967666dbd3ccd7f08429dbbf2776 100644 (file)
@@ -22,37 +22,37 @@ struct Ref2<'a,'b,T:'a+'b+?Sized> {
 }
 
 struct SomeStruct<'a> {
-    t: Ref<'a,Test>,
-    u: Ref<'a,Test+'a>,
+    t: Ref<'a, dyn Test>,
+    u: Ref<'a, dyn Test+'a>,
 }
 
-fn a<'a>(t: Ref<'a,Test>, mut ss: SomeStruct<'a>) {
+fn a<'a>(t: Ref<'a, dyn Test>, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn b<'a>(t: Ref<'a,Test>, mut ss: SomeStruct<'a>) {
+fn b<'a>(t: Ref<'a, dyn Test>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
-fn c<'a>(t: Ref<'a,Test+'a>, mut ss: SomeStruct<'a>) {
+fn c<'a>(t: Ref<'a, dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn d<'a>(t: Ref<'a,Test+'a>, mut ss: SomeStruct<'a>) {
+fn d<'a>(t: Ref<'a, dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
-fn e<'a>(_: Ref<'a, Display+'static>) {}
-fn g<'a, 'b>(_: Ref2<'a, 'b, Display+'static>) {}
+fn e<'a>(_: Ref<'a, dyn Display+'static>) {}
+fn g<'a, 'b>(_: Ref2<'a, 'b, dyn Display+'static>) {}
 
 
 fn main() {
     // Inside a function body, we can just infer all
     // lifetimes, to allow Ref<'tmp, Display+'static>
     // and Ref2<'tmp, 'tmp, Display+'static>.
-    let x = &0 as &(Display+'static);
-    let r: Ref<Display> = Ref { r: x };
-    let r2: Ref2<Display> = Ref2 { a: x, b: x };
+    let x = &0 as &(dyn Display+'static);
+    let r: Ref<dyn Display> = Ref { r: x };
+    let r2: Ref2<dyn Display> = Ref2 { a: x, b: x };
     e(r);
     g(r2);
 }
index 48ee5a2ed545034764c499c2b0eb1ad9cd5669b6..1fc52ead48e0e54d421210e9283e444d859c3a37 100644 (file)
@@ -11,25 +11,25 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a MyBox<Test>,
-    u: &'a MyBox<Test+'a>,
+    t: &'a MyBox<dyn Test>,
+    u: &'a MyBox<dyn Test+'a>,
 }
 
 struct MyBox<T:?Sized> {
     b: Box<T>
 }
 
-fn a<'a>(t: &'a MyBox<Test>, mut ss: SomeStruct<'a>) {
+fn a<'a>(t: &'a MyBox<dyn Test>, mut ss: SomeStruct<'a>) {
     ss.t = t;
 }
 
-fn b<'a>(t: &'a MyBox<Test>, mut ss: SomeStruct<'a>) {
+fn b<'a>(t: &'a MyBox<dyn Test>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
 // see also compile-fail/object-lifetime-default-from-rptr-box-error.rs
 
-fn d<'a>(t: &'a MyBox<Test+'a>, mut ss: SomeStruct<'a>) {
+fn d<'a>(t: &'a MyBox<dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.u = t;
 }
 
index 7702725e640cda38da39cf56850bda29c2954de0..c495b97b25bfee31a4b659434aea376d1c0f61c5 100644 (file)
@@ -27,5 +27,5 @@ fn main() {
     take_auto_unsafe(AutoBool(true));
 
     /// Auto traits are allowed in trait object bounds.
-    let _: &(Send + Auto) = &0;
+    let _: &(dyn Send + Auto) = &0;
 }
index 140dcaf6a27b66a8bfb865348709b7dde2405cfd..82760788897a5878a322eeb555c7c2b316f166ad 100644 (file)
@@ -11,7 +11,7 @@ impl Foo {
     fn bar(&self) {}
 }
 
-impl Trait {
+impl dyn Trait {
     fn baz(_: &Foo) {}
 }
 
@@ -26,5 +26,5 @@ fn main() {
 
     // Should work even if Trait::baz doesn't exist.
     // N.B: `<Trait>::bar` would be ambiguous.
-    <Trait>::baz(&Foo);
+    <dyn Trait>::baz(&Foo);
 }
index 1deb17e00da613199fbb3fa577722a4bad0c880c..ed258dbb24c3f7fcdeb798069ee0e6c9f3475eac 100644 (file)
@@ -14,7 +14,7 @@
 
 struct Type<A> { a: PhantomData<A> }
 
-fn as_trait<A>(t: &Type<A>) -> &Trait<A> { loop {  } }
+fn as_trait<A>(t: &Type<A>) -> &dyn Trait<A> { loop {  } }
 
 fn want<A,T:Trait<A>+?Sized>(t: &T) { }
 
index f7a58c6f926713cdbd46958b2130049cf90659c5..23b91f924b553055f6562153a2904bdd66224b63 100644 (file)
@@ -12,8 +12,8 @@ fn get(&self) -> A {
     }
 }
 
-fn repeater<A:Clone + 'static>(v: Box<A>) -> Box<repeat<A>+'static> {
-    box v as Box<repeat<A>+'static> // No
+fn repeater<A:Clone + 'static>(v: Box<A>) -> Box<dyn repeat<A>+'static> {
+    box v as Box<dyn repeat<A>+'static> // No
 }
 
 pub fn main() {
index 12e4a34a233e07b42fcb019c794dd9eaac9e192e..b92a2ab7b4bc2414ab9aaab2517088df6652b372 100644 (file)
 
 trait Wrap {
     fn get(&self) -> isize;
-    fn wrap(self: Box<Self>) -> Box<Any+'static>;
+    fn wrap(self: Box<Self>) -> Box<dyn Any+'static>;
 }
 
 impl Wrap for isize {
     fn get(&self) -> isize {
         *self
     }
-    fn wrap(self: Box<isize>) -> Box<Any+'static> {
-        self as Box<Any+'static>
+    fn wrap(self: Box<isize>) -> Box<dyn Any+'static> {
+        self as Box<dyn Any+'static>
     }
 }
 
-fn is<T:Any>(x: &Any) -> bool {
+fn is<T:Any>(x: &dyn Any) -> bool {
     x.is::<T>()
 }
 
 fn main() {
-    let x = box 22isize as Box<Wrap>;
+    let x = box 22isize as Box<dyn Wrap>;
     println!("x={}", x.get());
     let y = x.wrap();
 }
index b1339b207ebae54fd806fd1132f074a442d37f1b..832d4f6c89f09c321199554abbef7c5ceb3a738c 100644 (file)
@@ -12,10 +12,10 @@ mod foo {
     pub trait D<'a, T> { fn get(self) -> &'a T; }
 }
 
-fn foo1<T>(_: &(A<T> + Send)) {}
-fn foo2<T>(_: Box<A<T> + Send + Sync>) {}
-fn foo3<T>(_: Box<B<isize, usize> + 'static>) {}
-fn foo4<'a, T>(_: Box<C<'a, T> + 'static + Send>) {}
-fn foo5<'a, T>(_: Box<foo::D<'a, T> + 'static + Send>) {}
+fn foo1<T>(_: &(dyn A<T> + Send)) {}
+fn foo2<T>(_: Box<dyn A<T> + Send + Sync>) {}
+fn foo3<T>(_: Box<dyn B<isize, usize> + 'static>) {}
+fn foo4<'a, T>(_: Box<dyn C<'a, T> + 'static + Send>) {}
+fn foo5<'a, T>(_: Box<dyn foo::D<'a, T> + 'static + Send>) {}
 
 pub fn main() {}
index af6392e565859a9d1d2b0b1a2306a2d5d3deec67..8c8a7eb7d9da1c679ccd107b9e3f27f739896592 100644 (file)
@@ -7,18 +7,18 @@
 trait Foo {
 }
 
-fn b(_x: Box<Foo+Send>) {
+fn b(_x: Box<dyn Foo+Send>) {
 }
 
-fn c(x: Box<Foo+Sync+Send>) {
+fn c(x: Box<dyn Foo+Sync+Send>) {
     e(x);
 }
 
-fn d(x: Box<Foo+Send>) {
+fn d(x: Box<dyn Foo+Send>) {
     e(x);
 }
 
-fn e(x: Box<Foo>) {
+fn e(x: Box<dyn Foo>) {
     e(x);
 }
 
index 82bdcdcf7c50bb1cd782edb472ae48c8221cf801..a45d834297eedc0e9325af7611f48b1eacff01ca 100644 (file)
@@ -12,7 +12,7 @@
 use std::thread;
 
 trait Pet {
-    fn name(&self, blk: Box<FnMut(&str)>);
+    fn name(&self, blk: Box<dyn FnMut(&str)>);
     fn num_legs(&self) -> usize;
     fn of_good_pedigree(&self) -> bool;
 }
@@ -34,19 +34,19 @@ struct Goldfyshe {
 }
 
 impl Pet for Catte {
-    fn name(&self, mut blk: Box<FnMut(&str)>) { blk(&self.name) }
+    fn name(&self, mut blk: Box<dyn FnMut(&str)>) { blk(&self.name) }
     fn num_legs(&self) -> usize { 4 }
     fn of_good_pedigree(&self) -> bool { self.num_whiskers >= 4 }
 }
 impl Pet for Dogge {
-    fn name(&self, mut blk: Box<FnMut(&str)>) { blk(&self.name) }
+    fn name(&self, mut blk: Box<dyn FnMut(&str)>) { blk(&self.name) }
     fn num_legs(&self) -> usize { 4 }
     fn of_good_pedigree(&self) -> bool {
         self.bark_decibels < 70 || self.tricks_known > 20
     }
 }
 impl Pet for Goldfyshe {
-    fn name(&self, mut blk: Box<FnMut(&str)>) { blk(&self.name) }
+    fn name(&self, mut blk: Box<dyn FnMut(&str)>) { blk(&self.name) }
     fn num_legs(&self) -> usize { 0 }
     fn of_good_pedigree(&self) -> bool { self.swim_speed >= 500 }
 }
@@ -67,10 +67,10 @@ pub fn main() {
         swim_speed: 998,
         name: "alec_guinness".to_string(),
     };
-    let arc = Arc::new(vec![box catte  as Box<Pet+Sync+Send>,
-                            box dogge1 as Box<Pet+Sync+Send>,
-                            box fishe  as Box<Pet+Sync+Send>,
-                            box dogge2 as Box<Pet+Sync+Send>]);
+    let arc = Arc::new(vec![box catte  as Box<dyn Pet+Sync+Send>,
+                            box dogge1 as Box<dyn Pet+Sync+Send>,
+                            box fishe  as Box<dyn Pet+Sync+Send>,
+                            box dogge2 as Box<dyn Pet+Sync+Send>]);
     let (tx1, rx1) = channel();
     let arc1 = arc.clone();
     let t1 = thread::spawn(move|| { check_legs(arc1); tx1.send(()); });
@@ -88,21 +88,21 @@ pub fn main() {
     t3.join();
 }
 
-fn check_legs(arc: Arc<Vec<Box<Pet+Sync+Send>>>) {
+fn check_legs(arc: Arc<Vec<Box<dyn Pet+Sync+Send>>>) {
     let mut legs = 0;
     for pet in arc.iter() {
         legs += pet.num_legs();
     }
     assert!(legs == 12);
 }
-fn check_names(arc: Arc<Vec<Box<Pet+Sync+Send>>>) {
+fn check_names(arc: Arc<Vec<Box<dyn Pet+Sync+Send>>>) {
     for pet in arc.iter() {
         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>>>) {
+fn check_pedigree(arc: Arc<Vec<Box<dyn Pet+Sync+Send>>>) {
     for pet in arc.iter() {
         assert!(pet.of_good_pedigree());
     }
index 18b25b852d17357ad205129dad60ef808c997096..4dc4fecc91fcfc36da7c098a8e737296bfc54959 100644 (file)
@@ -7,11 +7,11 @@ trait U {}
 trait T<X: U> { fn get(self) -> X; }
 
 trait S2<Y: U> {
-    fn m(x: Box<T<Y>+'static>) {}
+    fn m(x: Box<dyn T<Y>+'static>) {}
 }
 
 struct St<X: U> {
-    f: Box<T<X>+'static>,
+    f: Box<dyn T<X>+'static>,
 }
 
 impl<X: U> St<X> {
index 5d1b442afcc7070e053965266776bf6ba2f566d9..bf4dda49519107cef0b14585479d001d6b9d3f64 100644 (file)
@@ -18,8 +18,8 @@ fn f(&self, x: &'static str) {
 
 pub fn main() {
     let a = Struct { x: 1, y: 2 };
-    let b: Box<Trait<&'static str>> = Box::new(a);
+    let b: Box<dyn Trait<&'static str>> = Box::new(a);
     b.f("Mary");
-    let c: &Trait<&'static str> = &a;
+    let c: &dyn Trait<&'static str> = &a;
     c.f("Joe");
 }
index 1a40b81c89fe9233b3c6c063272b1421ca5114cb..cba33af1f1aca1f9b8221b5bdd8c912c630c8ce6 100644 (file)
@@ -22,13 +22,13 @@ fn f(&self) {
     }
 }
 
-fn foo(mut a: Box<Write>) {}
+fn foo(mut a: Box<dyn Write>) {}
 
 pub fn main() {
     let a = Struct { x: 1, y: 2 };
-    let b: Box<Trait> = Box::new(a);
+    let b: Box<dyn Trait> = Box::new(a);
     b.f();
-    let c: &Trait = &a;
+    let c: &dyn Trait = &a;
     c.f();
 
     let out = io::stdout();
index b28d74a7b35b1ddd5763ea7f7f11172993d540d9..804ffec12c2bfd61d909f9ca4968abf83f518620 100644 (file)
@@ -11,7 +11,7 @@ pub trait Trait {
 }
 
 mod Bar {
-    impl<'a> ::Foo::Trait+'a {
+    impl<'a> dyn (::Foo::Trait) + 'a {
         fn bar(&self) { self.foo() }
     }
 }
index 6b22ac08bb8a6e0f55d5c2084d1fe52ef44eda13..14796ce19c88ed08b62d726b53e1f674e13405d3 100644 (file)
@@ -12,7 +12,7 @@ trait T {
     fn t(&self) {}
 }
 
-impl<'a> T+'a {
+impl<'a> dyn T+'a {
     fn foo(&self) {
         unsafe { COUNT *= 2; }
     }
@@ -27,7 +27,7 @@ impl T for isize {}
 impl<'a> Bar<'a> for Foo {}
 
 fn main() {
-    let x: &T = &42;
+    let x: &dyn T = &42;
 
     x.foo();
     T::foo(x);
@@ -36,6 +36,6 @@ fn main() {
     unsafe { assert_eq!(COUNT, 12); }
 
     // Cross-crait case
-    let x: &Bar = &Foo;
+    let x: &dyn Bar = &Foo;
     x.bar();
 }
index c0b5db63bd4523b752e40a65acec528f482a03b5..25159c1adb6f6febdb0316660140be18e04e9e8a 100644 (file)
@@ -26,8 +26,8 @@ fn g(&self) -> isize { 20 }
 
 pub fn main() {
     let a = &A { x: 3 };
-    let afoo = a as &Foo;
-    let abar = a as &Bar;
+    let afoo = a as &dyn Foo;
+    let abar = a as &dyn Bar;
     assert_eq!(afoo.f(), 10);
     assert_eq!(abar.g(), 20);
 }
index 38e5c79e9e033ecd92ca2805039cd53498607b68..9070b9d1f5606991efceaece5ef1d96ea9870aee 100644 (file)
@@ -25,8 +25,8 @@ fn g(&self) -> isize { 20 }
 
 pub fn main() {
     let a = &A { x: 3 };
-    let afoo = a as &Foo;
-    let abar = a as &Bar;
+    let afoo = a as &dyn Foo;
+    let abar = a as &dyn Bar;
     assert_eq!(afoo.f(), 10);
     assert_eq!(abar.g(), 20);
     assert_eq!(abar.f(), 10);
index 248804d144a25f4f37db71654c445086b03c0849..0b8b0e2f5ef4d48e24c52495b6269f629f62b908 100644 (file)
@@ -4,7 +4,7 @@ trait Future: 'static {
     // Future::forget in vtables, otherwise there's an infinite type
     // recursion through <Map<...> as Future>::forget.
     fn forget(self) where Self: Sized {
-        Box::new(Map(self)) as Box<Future>;
+        Box::new(Map(self)) as Box<dyn Future>;
     }
 }
 
index 168bffa0e481486e4242ed8764a793bbb3946e5d..c18754302b75b279af7165e3398a87cfdb5ac3ea 100644 (file)
@@ -16,7 +16,7 @@ pub struct Impl<A1, A2, A3> {
      * task <unnamed> failed at 'index out of bounds: the len is 1 but the index is 1',
      * src/librustc/middle/subst.rs:58
      */
-    t: Box<Trait2<A2>+'static>
+    t: Box<dyn Trait2<A2>+'static>
 }
 
 impl<A1, A2, A3> Impl<A1, A2, A3> {
@@ -38,6 +38,6 @@ fn method(&self, _x: Type<(u8,V)>) -> isize { 0 }
 }
 
 pub fn main() {
-    let a = box () as Box<Trait<u8, u8>>;
+    let a = box () as Box<dyn Trait<u8, u8>>;
     assert_eq!(a.method(Type::Constant((1, 2))), 0);
 }
index e95a652057d5c3aa93e731a0c068d1c75c030239..33757cb7c0ab1da7efa9d1e5458efb1ce606a8c9 100644 (file)
@@ -4,8 +4,8 @@
 static BYTE: u8 = 33;
 
 fn main() {
-    let x: &('static + Display) = &BYTE;
-    let y: Box<'static + Display> = Box::new(BYTE);
+    let x: &(dyn 'static + Display) = &BYTE;
+    let y: Box<dyn 'static + Display> = Box::new(BYTE);
     let xstr = format!("{}", x);
     let ystr = format!("{}", y);
     assert_eq!(xstr, "33");
index 9060380db17e28a16fa777e11db7154513cee314..05aab5e3b085c0965907a9791d38557056c9c09f 100644 (file)
@@ -20,10 +20,10 @@ impl<'d> M for P<'d> {
     fn n(&self) -> u8 { *self.g }
 }
 
-fn extension<'e>(x: &'e E<'e>) -> Box<M+'e> {
+fn extension<'e>(x: &'e E<'e>) -> Box<dyn M+'e> {
     loop {
         let p = P { g: x.m() };
-        return Box::new(p) as Box<M+'e>;
+        return Box::new(p) as Box<dyn M+'e>;
     }
 }
 
index 6584182d38a4b4ae78fa41f140e9c5b7c69ba9c1..0456ca931156ec5b833c02a69a06c0d63c92504f 100644 (file)
@@ -16,6 +16,6 @@ fn f(&self) -> isize {
 
 pub fn main() {
     let a = A { x: 3 };
-    let b = (&a) as &Foo;
+    let b = (&a) as &dyn Foo;
     assert_eq!(b.f(), 3);
 }
index c9745e06d8fb438c8d8efdf52f2566788ebcd209..e490967b690475107a6fed637edd0e574061eab2 100644 (file)
@@ -14,5 +14,5 @@ impl<T:?Sized> Foo for T { }
 fn want_foo<B:?Sized+Foo>() { }
 
 fn main() {
-    want_foo::<Bar>();
+    want_foo::<dyn Bar>();
 }
index 0f831be24850019b4479ad48070ec65d41335ffc..bedd87cc4cc7977eb031e75d75dff1d806c2ee35 100644 (file)
@@ -25,7 +25,7 @@ fn eq(&self, _rhs: &Bar) -> bool {
 impl A for Aimpl { }
 
 fn main() {
-    let a = &Aimpl as &A;
+    let a = &Aimpl as &dyn A;
 
     assert!(*a == Foo);
 }
index c8318bdf15476fac9a31c68a2e17845bbbb0eda1..391d19c4385586c7277447c8d32eea66e6cfd036 100644 (file)
@@ -22,7 +22,7 @@ fn same_as(&self, t: u64) -> bool { *self == (t as i64) }
 
 impl CompareToInts for i64 { }
 
-fn with_obj(c: &CompareToInts) -> bool {
+fn with_obj(c: &dyn CompareToInts) -> bool {
     c.same_as(22_i64) && c.same_as(22_u64)
 }
 
index abe164a5720bd0fa33ba25d3bbefcbc34fd010d2..700488c22d6780606207df0103fcb415ce676d30 100644 (file)
@@ -12,6 +12,6 @@ fn test(&self) -> i32 { *self }
 }
 
 fn main() {
-    let a: &Foo = &22;
+    let a: &dyn Foo = &22;
     assert_eq!(Foo::test(a), 22);
 }
index bc56d0158d4df0bdf39b878120458582a7bc0396..f06b0708290bc909063e751e10985a3c35ce10e1 100644 (file)
@@ -36,21 +36,21 @@ pub fn main() {
 
     // unsize trait
     let x: &Bar = &Bar;
-    let _ = x as &Foo;
-    let _ = x as *const Foo;
+    let _ = x as &dyn Foo;
+    let _ = x as *const dyn Foo;
 
     let x: &mut Bar = &mut Bar;
-    let _ = x as &mut Foo;
-    let _ = x as *mut Foo;
+    let _ = x as &mut dyn Foo;
+    let _ = x as *mut dyn Foo;
 
     let x: Box<Bar> = Box::new(Bar);
-    let _ = x as Box<Foo>;
+    let _ = x as Box<dyn Foo>;
 
     // functions
     fn baz(_x: i32) {}
-    let _ = &baz as &Fn(i32);
+    let _ = &baz as &dyn Fn(i32);
     let x = |_x: i32| {};
-    let _ = &x as &Fn(i32);
+    let _ = &x as &dyn Fn(i32);
 }
 
 // subtyping
index d9280cf97f92078e5ff0c799a82927c302175a55..469bc8ed7e15309d551ce058f53665337a2ad819 100644 (file)
@@ -7,7 +7,7 @@
 fn good(s: &String) -> Foo { Foo(s) }
 
 fn bad1(s: String) -> Option<&'static str> {
-    let a: Box<Any> = Box::new(good as fn(&String) -> Foo);
+    let a: Box<dyn Any> = Box::new(good as fn(&String) -> Foo);
     a.downcast_ref::<fn(&String) -> Foo<'static>>().map(|f| f(&s).0)
 }
 
@@ -20,8 +20,8 @@ fn get(&'a self) -> &'a str { self }
 }
 
 fn bad2(s: String) -> Option<&'static str> {
-    let a: Box<Any> = Box::new(Box::new(s) as Box<for<'a> AsStr<'a, 'a>>);
-    a.downcast_ref::<Box<for<'a> AsStr<'a, 'static>>>().map(|x| x.get())
+    let a: Box<dyn Any> = Box::new(Box::new(s) as Box<dyn for<'a> AsStr<'a, 'a>>);
+    a.downcast_ref::<Box<dyn for<'a> AsStr<'a, 'static>>>().map(|x| x.get())
 }
 
 fn main() {
index 55d70e31b164174f4201a7a8b5064f03d58ba552..b98dff0d72b8d5752de9ee1f7722148dfd85affc 100644 (file)
@@ -26,9 +26,9 @@ fn main() {
         assert!(e != f);
 
         // Make sure lifetime parameters of items are not ignored.
-        let g = TypeId::of::<for<'a> fn(&'a Trait<'a>) -> Struct<'a>>();
-        let h = TypeId::of::<for<'a> fn(&'a Trait<'a>) -> Struct<'static>>();
-        let i = TypeId::of::<for<'a, 'b> fn(&'a Trait<'b>) -> Struct<'b>>();
+        let g = TypeId::of::<for<'a> fn(&'a dyn Trait<'a>) -> Struct<'a>>();
+        let h = TypeId::of::<for<'a> fn(&'a dyn Trait<'a>) -> Struct<'static>>();
+        let i = TypeId::of::<for<'a, 'b> fn(&'a dyn Trait<'b>) -> Struct<'b>>();
         assert!(g != h);
         assert!(g != i);
         assert!(h != i);
@@ -40,10 +40,10 @@ fn main() {
     }
     // Boxed unboxed closures
     {
-        let a = TypeId::of::<Box<Fn(&'static isize, &'static isize)>>();
-        let b = TypeId::of::<Box<for<'a> Fn(&'static isize, &'a isize)>>();
-        let c = TypeId::of::<Box<for<'a, 'b> Fn(&'a isize, &'b isize)>>();
-        let d = TypeId::of::<Box<for<'a, 'b> Fn(&'b isize, &'a isize)>>();
+        let a = TypeId::of::<Box<dyn Fn(&'static isize, &'static isize)>>();
+        let b = TypeId::of::<Box<dyn for<'a> Fn(&'static isize, &'a isize)>>();
+        let c = TypeId::of::<Box<dyn for<'a, 'b> Fn(&'a isize, &'b isize)>>();
+        let d = TypeId::of::<Box<dyn for<'a, 'b> Fn(&'b isize, &'a isize)>>();
         assert!(a != b);
         assert!(a != c);
         assert!(a != d);
@@ -52,8 +52,8 @@ fn main() {
         assert_eq!(c, d);
 
         // Make sure De Bruijn indices are handled correctly
-        let e = TypeId::of::<Box<for<'a> Fn(Box<Fn(&'a isize) -> &'a isize>)>>();
-        let f = TypeId::of::<Box<Fn(Box<for<'a> Fn(&'a isize) -> &'a isize>)>>();
+        let e = TypeId::of::<Box<dyn for<'a> Fn(Box<dyn Fn(&'a isize) -> &'a isize>)>>();
+        let f = TypeId::of::<Box<dyn Fn(Box<dyn for<'a> Fn(&'a isize) -> &'a isize>)>>();
         assert!(e != f);
     }
     // Raw unboxed closures
index 244a72c80fa23d1c4b5861035bbb2f49cca642bc..6298156452e49b080054bddc8c458d6bd96c1605 100644 (file)
@@ -23,8 +23,8 @@ trait Get<T: ?Sized> {
     fn get(&self) -> &T;
 }
 
-impl Get<MyShow + 'static> for Wrap<T> {
-    fn get(&self) -> &(MyShow + 'static) {
+impl Get<dyn MyShow + 'static> for Wrap<T> {
+    fn get(&self) -> &(dyn MyShow + 'static) {
         static x: usize = 42;
         &x
     }
@@ -38,9 +38,9 @@ fn get(&self) -> &usize {
 }
 
 trait MyShow { fn dummy(&self) { } }
-impl<'a> MyShow for &'a (MyShow + 'a) { }
+impl<'a> MyShow for &'a (dyn MyShow + 'a) { }
 impl MyShow for usize { }
-fn constrain<'a>(rc: RefCell<&'a (MyShow + 'a)>) { }
+fn constrain<'a>(rc: RefCell<&'a (dyn MyShow + 'a)>) { }
 
 fn main() {
     let mut collection: Wrap<_> = WrapNone;
index 08a9796ea29c5af940066249b8b25998b738de25..a1001673506f0660c7991ce3b3f6ab4dc32c22f5 100644 (file)
@@ -8,7 +8,7 @@ fn a<F:FnMut() -> i32>(mut f: F) -> i32 {
     f()
 }
 
-fn b(f: &mut FnMut() -> i32) -> i32 {
+fn b(f: &mut dyn FnMut() -> i32) -> i32 {
     a(f)
 }
 
index 76ad40b8f3d634c4eab3b53c9b1101a86d517b34..ca1d31ca54470a0193667e12451c24f92237d677 100644 (file)
@@ -8,7 +8,7 @@ fn a<F:Fn() -> i32>(f: F) -> i32 {
     f()
 }
 
-fn b(f: &Fn() -> i32) -> i32 {
+fn b(f: &dyn Fn() -> i32) -> i32 {
     a(f)
 }
 
index 6d55fe997b092ca8cc07d95293ade4bea22c5d38..b2596e49aa78eecc8ea2e91f8a93e3e6d8a12aab 100644 (file)
@@ -3,9 +3,9 @@
 
 use std::ops::FnMut;
 
- fn make_adder(x: i32) -> Box<FnMut(i32)->i32+'static> {
+ fn make_adder(x: i32) -> Box<dyn FnMut(i32)->i32+'static> {
     (box move |y: i32| -> i32 { x + y }) as
-        Box<FnMut(i32)->i32+'static>
+        Box<dyn FnMut(i32)->i32+'static>
 }
 
 pub fn main() {
index 22fc148c3522abc0a368208795e787f3ef9e06e3..d47ceea0f4f4d9ca2122d17baa7aee32e75c8a42 100644 (file)
@@ -3,7 +3,7 @@
 
 use std::ops::FnMut;
 
-fn make_adder(x: isize) -> Box<FnMut(isize)->isize + 'static> {
+fn make_adder(x: isize) -> Box<dyn FnMut(isize)->isize + 'static> {
     Box::new(move |y| { x + y })
 }
 
index 91311fba2e80f6767acbfcb75e7efb2b333bd812..f77733d106d4f4d6f0e1603140dcb45659f75431 100644 (file)
@@ -1,7 +1,7 @@
 // run-pass
 use std::ops::FnMut;
 
-fn make_adder(x: isize) -> Box<FnMut(isize)->isize + 'static> {
+fn make_adder(x: isize) -> Box<dyn FnMut(isize)->isize + 'static> {
     Box::new(move |y| { x + y })
 }
 
index 0fd23a2d79646538f43c858f76e07a62127cef30..3ee1aeb109b18b5ebd953a91a7e51c1e4b684d08 100644 (file)
@@ -7,7 +7,7 @@ fn call_it<F:Fn(&isize)->isize>(f: &F, x: isize) -> isize {
     (*f)(&x)
 }
 
-fn call_it_boxed(f: &Fn(&isize) -> isize, x: isize) -> isize {
+fn call_it_boxed(f: &dyn Fn(&isize) -> isize, x: isize) -> isize {
     f(&x)
 }
 
index 4f23f85b649e46a711f1c7dea14e2e12bfad1afc..d2eaee304104ae7d230f131e918c709062f722aa 100644 (file)
@@ -12,7 +12,7 @@ impl ToPrimitive for isize {}
 impl ToPrimitive for i32 {}
 impl ToPrimitive for usize {}
 
-fn doit<T>(val: T, f: &Fn(T)) { f(val) }
+fn doit<T>(val: T, f: &dyn Fn(T)) { f(val) }
 
 pub fn main() {
     doit(0, &|x /*: isize*/ | { x.to_int(); });
index 72d658f393bd904527b7b00ffae500a2b24b0491..86834f49407fc74ad8f1d5ce1b76a8ee5a485a22 100644 (file)
@@ -20,23 +20,23 @@ fn new(f: F) -> YCombinator<F,A,R> {
     }
 }
 
-impl<A,R,F : Fn(&Fn(A) -> R, A) -> R> Fn<(A,)> for YCombinator<F,A,R> {
+impl<A,R,F : Fn(&dyn Fn(A) -> R, A) -> R> Fn<(A,)> for YCombinator<F,A,R> {
     extern "rust-call" fn call(&self, (arg,): (A,)) -> R {
         (self.func)(self, arg)
     }
 }
 
-impl<A,R,F : Fn(&Fn(A) -> R, A) -> R> FnMut<(A,)> for YCombinator<F,A,R> {
+impl<A,R,F : Fn(&dyn Fn(A) -> R, A) -> R> FnMut<(A,)> for YCombinator<F,A,R> {
     extern "rust-call" fn call_mut(&mut self, args: (A,)) -> R { self.call(args) }
 }
 
-impl<A,R,F : Fn(&Fn(A) -> R, A) -> R> FnOnce<(A,)> for YCombinator<F,A,R> {
+impl<A,R,F : Fn(&dyn Fn(A) -> R, A) -> R> FnOnce<(A,)> for YCombinator<F,A,R> {
     type Output = R;
     extern "rust-call" fn call_once(self, args: (A,)) -> R { self.call(args) }
 }
 
 fn main() {
-    let factorial = |recur: &Fn(u32) -> u32, arg: u32| -> u32 {
+    let factorial = |recur: &dyn Fn(u32) -> u32, arg: u32| -> u32 {
         if arg == 0 {1} else {arg * recur(arg-1)}
     };
     let factorial: YCombinator<_,u32,u32> = YCombinator::new(factorial);
index 5c7aafdc5736122d3d03f5ec544fc44a332f72ec..df60b42ab126a550d9215df3b27ef924f62e605b 100644 (file)
@@ -19,7 +19,7 @@ fn call_it<F:FnMut(i32)->i32>(mut f: F, x: i32) -> i32 {
     f(x) + 3
 }
 
-fn call_box(f: &mut FnMut(i32) -> i32, x: i32) -> i32 {
+fn call_box(f: &mut dyn FnMut(i32) -> i32, x: i32) -> i32 {
     f(x) + 3
 }
 
index 092224b793457650858a648e9ba0320fdeee1af8..2df360d4a30a4bcbcad40609e9cd4f161e81dd6f 100644 (file)
@@ -3,7 +3,7 @@
 // monomorphize correctly (issue #16791)
 
 fn main(){
-    fn bar<'a, T:Clone+'a> (t: T) -> Box<FnMut()->T + 'a> {
+    fn bar<'a, T:Clone+'a> (t: T) -> Box<dyn FnMut()->T + 'a> {
         Box::new(move || t.clone())
     }
 
index 7e53c4d9eb613f82f8db4130be42d17bd4b649de..89a273b7a43ff26e57c09af4559a1320081b13cf 100644 (file)
@@ -4,10 +4,10 @@
 // pretty-expanded FIXME #23616
 
 fn main() {
-    let task: Box<Fn(isize) -> isize> = Box::new(|x| x);
+    let task: Box<dyn Fn(isize) -> isize> = Box::new(|x| x);
     task(0);
 
-    let mut task: Box<FnMut(isize) -> isize> = Box::new(|x| x);
+    let mut task: Box<dyn FnMut(isize) -> isize> = Box::new(|x| x);
     task(0);
 
     call(|x| x, 22);
index 45ab5df94b22c30844a26a9fad35a57b7d543d9e..1ca25517c3c5fc9e2fff8b8a5a6d4008e8ad646d 100644 (file)
@@ -19,7 +19,7 @@ fn get(&self, arg: X) -> X {
 }
 
 fn main() {
-    let x: &Getter<(i32,), (i32,)> = &Identity;
+    let x: &dyn Getter<(i32,), (i32,)> = &Identity;
     let (y,) = x.get((22,));
     assert_eq!(y, 22);
 }
index 4bd3764fa15a7e747cf6ce90e1fbe29b8e1cd7c1..84e8cdb32b84e588a03ed474451900fa53f1acb3 100644 (file)
@@ -15,6 +15,6 @@ pub struct UvEventLoop {
 impl EventLoop for UvEventLoop { }
 
 pub fn main() {
-    let loop_: Box<EventLoop> = box UvEventLoop { uvio: 0 } as Box<EventLoop>;
+    let loop_: Box<dyn EventLoop> = box UvEventLoop { uvio: 0 } as Box<dyn EventLoop>;
     let _loop2_ = loop_;
 }
index c3eae299b86c8fbb0de5d807a124912b581f2050..c9a8b2e7c664b6e80784f4a753d731beb6010cbe 100644 (file)
@@ -60,26 +60,26 @@ fn f7<X: ?Sized+T3>(x: &X) {
 
 trait T4<X> {
     fn dummy(&self) { }
-    fn m1(&self, x: &T4<X>, y: X);
-    fn m2(&self, x: &T5<X>, y: X);
+    fn m1(&self, x: &dyn T4<X>, y: X);
+    fn m2(&self, x: &dyn T5<X>, y: X);
 }
 trait T5<X: ?Sized> {
     fn dummy(&self) { }
     // not an error (for now)
-    fn m1(&self, x: &T4<X>);
-    fn m2(&self, x: &T5<X>);
+    fn m1(&self, x: &dyn T4<X>);
+    fn m2(&self, x: &dyn T5<X>);
 }
 
 trait T6<X: T> {
     fn dummy(&self) { }
-    fn m1(&self, x: &T4<X>);
-    fn m2(&self, x: &T5<X>);
+    fn m1(&self, x: &dyn T4<X>);
+    fn m2(&self, x: &dyn T5<X>);
 }
 trait T7<X: ?Sized+T> {
     fn dummy(&self) { }
     // not an error (for now)
-    fn m1(&self, x: &T4<X>);
-    fn m2(&self, x: &T5<X>);
+    fn m1(&self, x: &dyn T4<X>);
+    fn m2(&self, x: &dyn T5<X>);
 }
 
 // The last field in a struct may be unsized
index d81059ca6a844ef0461c0c4bd911ed2e54ce7926..6814e2baab59730eb6f79ec65c4fdb9be363af1d 100644 (file)
@@ -12,7 +12,7 @@ pub struct Context<'tcx> {
 pub type Cmd<'a> = &'a isize;
 
 pub type DecodeInlinedItem<'a> =
-    Box<for<'tcx> FnMut(Cmd, &Context<'tcx>) -> Result<&'tcx isize, ()> + 'a>;
+    Box<dyn for<'tcx> FnMut(Cmd, &Context<'tcx>) -> Result<&'tcx isize, ()> + 'a>;
 
 fn foo(d: DecodeInlinedItem) {
 }
diff --git a/src/test/rustdoc-ui/failed-doctest-compile-fail.rs b/src/test/rustdoc-ui/failed-doctest-compile-fail.rs
new file mode 100644 (file)
index 0000000..297d6ef
--- /dev/null
@@ -0,0 +1,11 @@
+// FIXME: if/when the output of the test harness can be tested on its own, this test should be
+// adapted to use that, and that normalize line can go away
+
+// compile-flags:--test
+// normalize-stdout-test: "src/test/rustdoc-ui" -> "$$DIR"
+// failure-status: 101
+
+/// ```compile_fail
+/// println!("Hello");
+/// ```
+pub struct Foo;
diff --git a/src/test/rustdoc-ui/failed-doctest-compile-fail.stdout b/src/test/rustdoc-ui/failed-doctest-compile-fail.stdout
new file mode 100644 (file)
index 0000000..74e33d7
--- /dev/null
@@ -0,0 +1,14 @@
+
+running 1 test
+test $DIR/failed-doctest-compile-fail.rs - Foo (line 8) ... FAILED
+
+failures:
+
+---- $DIR/failed-doctest-compile-fail.rs - Foo (line 8) stdout ----
+Test compiled successfully, but it's marked `compile_fail`.
+
+failures:
+    $DIR/failed-doctest-compile-fail.rs - Foo (line 8)
+
+test result: FAILED. 0 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out
+
diff --git a/src/test/rustdoc-ui/failed-doctest-missing-codes.rs b/src/test/rustdoc-ui/failed-doctest-missing-codes.rs
new file mode 100644 (file)
index 0000000..6210206
--- /dev/null
@@ -0,0 +1,11 @@
+// FIXME: if/when the output of the test harness can be tested on its own, this test should be
+// adapted to use that, and that normalize line can go away
+
+// compile-flags:--test
+// normalize-stdout-test: "src/test/rustdoc-ui" -> "$$DIR"
+// failure-status: 101
+
+/// ```compile_fail,E0004
+/// let x: () = 5i32;
+/// ```
+pub struct Foo;
diff --git a/src/test/rustdoc-ui/failed-doctest-missing-codes.stdout b/src/test/rustdoc-ui/failed-doctest-missing-codes.stdout
new file mode 100644 (file)
index 0000000..d206b72
--- /dev/null
@@ -0,0 +1,26 @@
+
+running 1 test
+test $DIR/failed-doctest-missing-codes.rs - Foo (line 8) ... FAILED
+
+failures:
+
+---- $DIR/failed-doctest-missing-codes.rs - Foo (line 8) stdout ----
+error[E0308]: mismatched types
+ --> $DIR/failed-doctest-missing-codes.rs:9:13
+  |
+3 | let x: () = 5i32;
+  |             ^^^^ expected (), found i32
+  |
+  = note: expected type `()`
+             found type `i32`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0308`.
+Some expected error codes were not found: ["E0004"]
+
+failures:
+    $DIR/failed-doctest-missing-codes.rs - Foo (line 8)
+
+test result: FAILED. 0 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out
+
index 48f1424e6b23d6cfdbe271732484094b066f4a30..d2cdeb8f8f50e8d110b884464e8b15611830bf0e 100644 (file)
@@ -5,10 +5,13 @@
 // compile-flags:--test
 // normalize-stdout-test: "src/test/rustdoc-ui" -> "$$DIR"
 // failure-status: 101
-// rustc-env:RUST_BACKTRACE=0
 
 // doctest fails at runtime
 /// ```
+/// println!("stdout 1");
+/// eprintln!("stderr 1");
+/// println!("stdout 2");
+/// eprintln!("stderr 2");
 /// panic!("oh no");
 /// ```
 pub struct SomeStruct;
index 45efa30d9919c5b51977350700233a44d5fe6b90..0c42c652d786c724b1e23dd3afb398e41902d608 100644 (file)
@@ -1,13 +1,13 @@
 
 running 2 tests
-test $DIR/failed-doctest-output.rs - OtherStruct (line 17) ... FAILED
-test $DIR/failed-doctest-output.rs - SomeStruct (line 11) ... FAILED
+test $DIR/failed-doctest-output.rs - OtherStruct (line 20) ... FAILED
+test $DIR/failed-doctest-output.rs - SomeStruct (line 10) ... FAILED
 
 failures:
 
----- $DIR/failed-doctest-output.rs - OtherStruct (line 17) stdout ----
+---- $DIR/failed-doctest-output.rs - OtherStruct (line 20) stdout ----
 error[E0425]: cannot find value `no` in this scope
- --> $DIR/failed-doctest-output.rs:18:1
+ --> $DIR/failed-doctest-output.rs:21:1
   |
 3 | no
   | ^^ not found in this scope
@@ -15,21 +15,25 @@ error[E0425]: cannot find value `no` in this scope
 error: aborting due to previous error
 
 For more information about this error, try `rustc --explain E0425`.
-thread '$DIR/failed-doctest-output.rs - OtherStruct (line 17)' panicked at 'couldn't compile the test', src/librustdoc/test.rs:320:13
+Couldn't compile the test.
+---- $DIR/failed-doctest-output.rs - SomeStruct (line 10) stdout ----
+Test executable failed (exit code 101).
+
+stdout:
+stdout 1
+stdout 2
+
+stderr:
+stderr 1
+stderr 2
+thread 'main' panicked at 'oh no', $DIR/failed-doctest-output.rs:7:1
 note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
 
----- $DIR/failed-doctest-output.rs - SomeStruct (line 11) stdout ----
-thread '$DIR/failed-doctest-output.rs - SomeStruct (line 11)' panicked at 'test executable failed:
-
-thread 'main' panicked at 'oh no', $DIR/failed-doctest-output.rs:3:1
-note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
-
-', src/librustdoc/test.rs:342:17
 
 
 failures:
-    $DIR/failed-doctest-output.rs - OtherStruct (line 17)
-    $DIR/failed-doctest-output.rs - SomeStruct (line 11)
+    $DIR/failed-doctest-output.rs - OtherStruct (line 20)
+    $DIR/failed-doctest-output.rs - SomeStruct (line 10)
 
 test result: FAILED. 0 passed; 2 failed; 0 ignored; 0 measured; 0 filtered out
 
diff --git a/src/test/rustdoc-ui/failed-doctest-should-panic.rs b/src/test/rustdoc-ui/failed-doctest-should-panic.rs
new file mode 100644 (file)
index 0000000..400fb97
--- /dev/null
@@ -0,0 +1,11 @@
+// FIXME: if/when the output of the test harness can be tested on its own, this test should be
+// adapted to use that, and that normalize line can go away
+
+// compile-flags:--test
+// normalize-stdout-test: "src/test/rustdoc-ui" -> "$$DIR"
+// failure-status: 101
+
+/// ```should_panic
+/// println!("Hello, world!");
+/// ```
+pub struct Foo;
diff --git a/src/test/rustdoc-ui/failed-doctest-should-panic.stdout b/src/test/rustdoc-ui/failed-doctest-should-panic.stdout
new file mode 100644 (file)
index 0000000..081b64b
--- /dev/null
@@ -0,0 +1,14 @@
+
+running 1 test
+test $DIR/failed-doctest-should-panic.rs - Foo (line 8) ... FAILED
+
+failures:
+
+---- $DIR/failed-doctest-should-panic.rs - Foo (line 8) stdout ----
+Test executable succeeded, but it's marked `should_panic`.
+
+failures:
+    $DIR/failed-doctest-should-panic.rs - Foo (line 8)
+
+test result: FAILED. 0 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out
+
index f31b64fbce36a9833696f4de00917060d1737477..0350c016436071649470192ac656dcd9fd830ea0 100644 (file)
@@ -13,9 +13,7 @@ error: unterminated double quote string
 
 error: aborting due to previous error
 
-thread '$DIR/unparseable-doc-test.rs - foo (line 6)' panicked at 'couldn't compile the test', src/librustdoc/test.rs:320:13
-note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
-
+Couldn't compile the test.
 
 failures:
     $DIR/unparseable-doc-test.rs - foo (line 6)
diff --git a/src/test/rustdoc/const-generics/add-impl.rs b/src/test/rustdoc/const-generics/add-impl.rs
new file mode 100644 (file)
index 0000000..ed45d33
--- /dev/null
@@ -0,0 +1,21 @@
+// ignore-tidy-linelength
+
+#![feature(const_generics)]
+
+#![crate_name = "foo"]
+
+use std::ops::Add;
+
+// @has foo/struct.Simd.html '//pre[@class="rust struct"]' 'pub struct Simd<T, const WIDTH: usize>'
+pub struct Simd<T, const WIDTH: usize> {
+    inner: T,
+}
+
+// @has foo/struct.Simd.html '//div[@id="implementations-list"]/h3/code' 'impl Add<Simd<u8, 16>> for Simd<u8, 16>'
+impl Add for Simd<u8, 16> {
+    type Output = Self;
+
+    fn add(self, rhs: Self) -> Self::Output {
+        Self { inner: 0 }
+    }
+}
diff --git a/src/test/rustdoc/const-generics/const-impl.rs b/src/test/rustdoc/const-generics/const-impl.rs
new file mode 100644 (file)
index 0000000..85ee6d3
--- /dev/null
@@ -0,0 +1,31 @@
+// ignore-tidy-linelength
+
+#![feature(const_generics)]
+
+#![crate_name = "foo"]
+
+pub enum Order {
+    Sorted,
+    Unsorted,
+}
+
+// @has foo/struct.VSet.html '//pre[@class="rust struct"]' 'pub struct VSet<T, const ORDER: Order>'
+// @has foo/struct.VSet.html '//h3[@id="impl-Send"]/code' 'impl<const ORDER: Order, T> Send for VSet<T, ORDER>'
+// @has foo/struct.VSet.html '//h3[@id="impl-Sync"]/code' 'impl<const ORDER: Order, T> Sync for VSet<T, ORDER>'
+pub struct VSet<T, const ORDER: Order> {
+    inner: Vec<T>,
+}
+
+// @has foo/struct.VSet.html '//h3[@id="impl"]/code' 'impl<T> VSet<T, { Order::Sorted }>'
+impl <T> VSet<T, {Order::Sorted}> {
+    pub fn new() -> Self {
+        Self { inner: Vec::new() }
+    }
+}
+
+// @has foo/struct.VSet.html '//h3[@id="impl-1"]/code' 'impl<T> VSet<T, { Order::Unsorted }>'
+impl <T> VSet<T, {Order::Unsorted}> {
+    pub fn new() -> Self {
+        Self { inner: Vec::new() }
+    }
+}
diff --git a/src/test/rustdoc/generic-const.rs b/src/test/rustdoc/generic-const.rs
deleted file mode 100644 (file)
index d6794ac..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#![feature(const_generics)]
-#![crate_name = "foo"]
-
-// ignore-tidy-linelength
-
-pub enum Order {
-    Sorted,
-    Unsorted,
-}
-
-// @has foo/struct.VSet.html '//pre[@class="rust struct"]' 'pub struct VSet<T, const ORDER: Order>'
-// @has foo/struct.VSet.html '//h3[@id="impl-Send"]/code' 'impl<const ORDER: Order, T> Send for VSet<T, ORDER>'
-// @has foo/struct.VSet.html '//h3[@id="impl-Sync"]/code' 'impl<const ORDER: Order, T> Sync for VSet<T, ORDER>'
-pub struct VSet<T, const ORDER: Order> {
-    inner: Vec<T>,
-}
-
-// @has foo/struct.VSet.html '//h3[@id="impl"]/code' 'impl<T> VSet<T, { Order::Sorted }>'
-impl <T> VSet<T, {Order::Sorted}> {
-    pub fn new() -> Self {
-        Self { inner: Vec::new() }
-    }
-}
-
-// @has foo/struct.VSet.html '//h3[@id="impl-1"]/code' 'impl<T> VSet<T, { Order::Unsorted }>'
-impl <T> VSet<T, {Order::Unsorted}> {
-    pub fn new() -> Self {
-        Self { inner: Vec::new() }
-    }
-}
diff --git a/src/test/rustdoc/issue-60482.rs b/src/test/rustdoc/issue-60482.rs
new file mode 100644 (file)
index 0000000..0fd1daa
--- /dev/null
@@ -0,0 +1,9 @@
+// This code caused a panic in `pulldown-cmark` 0.4.1.
+
+pub const BASIC_UNICODE: bool = true;
+
+
+/// # `BASIC_UNICODE`: `A` `|`
+/// ```text
+/// ```
+pub const BASIC_FONTS: bool = true;
index 2e2a124db9a5d28cbd1278d0c63d4d478409664e..8a1744ed5f8aeafb44e1dedb8f740131574c6ae5 100644 (file)
@@ -31,11 +31,11 @@ fn f4<F>(_: F) where F: for<'r> Fn(&(), &'r ()) {}
 fn f5<F>(_: F) where F: for<'r> Fn(&'r (), &'r ()) {}
 
 // Nested
-fn g1<F>(_: F) where F: Fn(&(), Box<Fn(&())>) {}
+fn g1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>) {}
 fn g2<F>(_: F) where F: Fn(&(), fn(&())) {}
-fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<Fn(&())>) {}
+fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<dyn Fn(&())>) {}
 fn g4<F>(_: F) where F: Fn(&(), for<'r> fn(&'r ())) {}
 
 // Mixed
-fn h1<F>(_: F) where F: Fn(&(), Box<Fn(&())>, &(), fn(&(), &())) {}
-fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<Fn(&())>, &'t0 (), fn(&(), &())) {}
+fn h1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>, &(), fn(&(), &())) {}
+fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<dyn Fn(&())>, &'t0 (), fn(&(), &())) {}
index 86547303978d6ea8a126a61cf6f634318483c108..0ca3ca8437463179baaea3a872fb1cf457a4068b 100644 (file)
@@ -149,8 +149,8 @@ LL |     g1(|_: (), _: ()| {});
 note: required by `g1`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:34:1
    |
-LL | fn g1<F>(_: F) where F: Fn(&(), Box<Fn(&())>) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn g1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:12:5
@@ -163,8 +163,8 @@ LL |     g1(|_: (), _: ()| {});
 note: required by `g1`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:34:1
    |
-LL | fn g1<F>(_: F) where F: Fn(&(), Box<Fn(&())>) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn g1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:14:5
@@ -205,8 +205,8 @@ LL |     g3(|_: (), _: ()| {});
 note: required by `g3`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:36:1
    |
-LL | fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<Fn(&())>) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<dyn Fn(&())>) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:16:5
@@ -219,8 +219,8 @@ LL |     g3(|_: (), _: ()| {});
 note: required by `g3`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:36:1
    |
-LL | fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<Fn(&())>) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn g3<F>(_: F) where F: for<'s> Fn(&'s (), Box<dyn Fn(&())>) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:18:5
@@ -261,8 +261,8 @@ LL |     h1(|_: (), _: (), _: (), _: ()| {});
 note: required by `h1`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:40:1
    |
-LL | fn h1<F>(_: F) where F: Fn(&(), Box<Fn(&())>, &(), fn(&(), &())) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn h1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>, &(), fn(&(), &())) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:20:5
@@ -275,8 +275,8 @@ LL |     h1(|_: (), _: (), _: (), _: ()| {});
 note: required by `h1`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:40:1
    |
-LL | fn h1<F>(_: F) where F: Fn(&(), Box<Fn(&())>, &(), fn(&(), &())) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn h1<F>(_: F) where F: Fn(&(), Box<dyn Fn(&())>, &(), fn(&(), &())) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:22:5
@@ -289,8 +289,8 @@ LL |     h2(|_: (), _: (), _: (), _: ()| {});
 note: required by `h2`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:41:1
    |
-LL | fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<Fn(&())>, &'t0 (), fn(&(), &())) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<dyn Fn(&())>, &'t0 (), fn(&(), &())) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0631]: type mismatch in closure arguments
   --> $DIR/anonymous-higher-ranked-lifetime.rs:22:5
@@ -303,8 +303,8 @@ LL |     h2(|_: (), _: (), _: (), _: ()| {});
 note: required by `h2`
   --> $DIR/anonymous-higher-ranked-lifetime.rs:41:1
    |
-LL | fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<Fn(&())>, &'t0 (), fn(&(), &())) {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | fn h2<F>(_: F) where F: for<'t0> Fn(&(), Box<dyn Fn(&())>, &'t0 (), fn(&(), &())) {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to 22 previous errors
 
index ab15ce6e8d8e087d2adddf116de592e7ca82fb87..2696aea5e89931bfa7e6287a80fe4db5464f3e36 100644 (file)
@@ -1,9 +1,11 @@
 fn main() {
     loop {
         |_: [_; break]| {} //~ ERROR: `break` outside of loop
+        //~^ ERROR mismatched types
     }
 
     loop {
         |_: [_; continue]| {} //~ ERROR: `continue` outside of loop
+        //~^ ERROR mismatched types
     }
 }
index 1cbf77a99f87ed14936c7a626c3454efdac24517..0e0dc8f623e6815cd98feaae98cf9605198ea1cf 100644 (file)
@@ -5,11 +5,30 @@ LL |         |_: [_; break]| {}
    |                 ^^^^^ cannot break outside of a loop
 
 error[E0268]: `continue` outside of loop
-  --> $DIR/array-break-length.rs:7:17
+  --> $DIR/array-break-length.rs:8:17
    |
 LL |         |_: [_; continue]| {}
    |                 ^^^^^^^^ cannot break outside of a loop
 
-error: aborting due to 2 previous errors
+error[E0308]: mismatched types
+  --> $DIR/array-break-length.rs:3:9
+   |
+LL |         |_: [_; break]| {}
+   |         ^^^^^^^^^^^^^^^^^^ expected (), found closure
+   |
+   = note: expected type `()`
+              found type `[closure@$DIR/array-break-length.rs:3:9: 3:27]`
+
+error[E0308]: mismatched types
+  --> $DIR/array-break-length.rs:8:9
+   |
+LL |         |_: [_; continue]| {}
+   |         ^^^^^^^^^^^^^^^^^^^^^ expected (), found closure
+   |
+   = note: expected type `()`
+              found type `[closure@$DIR/array-break-length.rs:8:9: 8:30]`
+
+error: aborting due to 4 previous errors
 
-For more information about this error, try `rustc --explain E0268`.
+Some errors have detailed explanations: E0268, E0308.
+For more information about an error, try `rustc --explain E0268`.
index 187708a60b4491798af019948d43992150bfba2d..cc3acd539562279c9bfcb7ed06afd6cbb920fb05 100644 (file)
@@ -6,7 +6,7 @@ trait Trait {
     const N: usize;
 }
 
-impl Trait {
+impl dyn Trait {
     //~^ ERROR the trait `Trait` cannot be made into an object [E0038]
     const fn n() -> usize { Self::N }
 }
index 44a92639b5d7e396f85b63aa25170532adab9097..dff268a55c909dd6e3e945e454459005a48661d4 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Trait` cannot be made into an object
   --> $DIR/associated-const-in-trait.rs:9:6
    |
-LL | impl Trait {
-   |      ^^^^^ the trait `Trait` cannot be made into an object
+LL | impl dyn Trait {
+   |      ^^^^^^^^^ the trait `Trait` cannot be made into an object
    |
    = note: the trait cannot contain associated consts like `N`
 
index df9143d685ff3a3747fc69a8fec679fe5eceed8a..7a678445796e65c4750c89bbc2a93fd0474e3681 100644 (file)
@@ -20,7 +20,7 @@ fn dent<C:BoxCar>(c: C, color: C::Color) {
     //~^ ERROR ambiguous associated type `Color` in bounds of `C`
 }
 
-fn dent_object<COLOR>(c: BoxCar<Color=COLOR>) {
+fn dent_object<COLOR>(c: dyn BoxCar<Color=COLOR>) {
     //~^ ERROR ambiguous associated type
     //~| ERROR the value of the associated type `Color` (from the trait `Vehicle`) must be specified
 }
index dd46ad64692c04b574f38506f2f4180f3aa4a776..6118ebef125a503652fa299b5a70449d5c78755c 100644 (file)
@@ -11,7 +11,7 @@ LL | fn dent<C:BoxCar>(c: C, color: C::Color) {
    |                                ^^^^^^^^ ambiguous associated type `Color`
 
 error[E0221]: ambiguous associated type `Color` in bounds of `BoxCar`
-  --> $DIR/associated-type-projection-from-multiple-supertraits.rs:23:33
+  --> $DIR/associated-type-projection-from-multiple-supertraits.rs:23:37
    |
 LL |     type Color;
    |     ----------- ambiguous `Color` from `Vehicle`
@@ -19,8 +19,8 @@ LL |     type Color;
 LL |     type Color;
    |     ----------- ambiguous `Color` from `Box`
 ...
-LL | fn dent_object<COLOR>(c: BoxCar<Color=COLOR>) {
-   |                                 ^^^^^^^^^^^ ambiguous associated type `Color`
+LL | fn dent_object<COLOR>(c: dyn BoxCar<Color=COLOR>) {
+   |                                     ^^^^^^^^^^^ ambiguous associated type `Color`
 
 error[E0191]: the value of the associated type `Color` (from the trait `Vehicle`) must be specified
   --> $DIR/associated-type-projection-from-multiple-supertraits.rs:23:26
@@ -28,8 +28,8 @@ error[E0191]: the value of the associated type `Color` (from the trait `Vehicle`
 LL |     type Color;
    |     ----------- `Color` defined here
 ...
-LL | fn dent_object<COLOR>(c: BoxCar<Color=COLOR>) {
-   |                          ^^^^^^^^^^^^^^^^^^^ associated type `Color` must be specified
+LL | fn dent_object<COLOR>(c: dyn BoxCar<Color=COLOR>) {
+   |                          ^^^^^^^^^^^^^^^^^^^^^^^ associated type `Color` must be specified
 
 error[E0221]: ambiguous associated type `Color` in bounds of `C`
   --> $DIR/associated-type-projection-from-multiple-supertraits.rs:28:29
index 1a58dcca9e24994c2cd8e3131e2a7332bb78d2f6..9366148b587d2dded4f117511c73acfd90848077 100644 (file)
@@ -28,7 +28,7 @@ fn foo2<I: Foo>(x: I) {
 }
 
 
-pub fn baz(x: &Foo<A=Bar>) {
+pub fn baz(x: &dyn Foo<A=Bar>) {
     let _: Bar = x.boo();
 }
 
index c93f3bec4d7d5f583da0fd800bf6aa50f8c633ea..4993b13121549323ba4bf354338a73cf56fc1cc3 100644 (file)
@@ -18,14 +18,14 @@ fn boo(&self) -> usize {
 }
 
 pub fn main() {
-    let a = &42isize as &Foo<A=usize, B=char>;
+    let a = &42isize as &dyn Foo<A=usize, B=char>;
 
-    let b = &42isize as &Foo<A=usize>;
+    let b = &42isize as &dyn Foo<A=usize>;
     //~^ ERROR the value of the associated type `B` (from the trait `Foo`) must be specified
 
-    let c = &42isize as &Foo<B=char>;
+    let c = &42isize as &dyn Foo<B=char>;
     //~^ ERROR the value of the associated type `A` (from the trait `Foo`) must be specified
 
-    let d = &42isize as &Foo;
+    let d = &42isize as &dyn Foo;
     //~^ ERROR the value of the associated types `A` (from the trait `Foo`), `B` (from the trait
 }
index d152e028eb733c3b6fe43067216b59ceb22baf03..b4c08f4a4cce5c020ee145e441bb58873cd8ec48 100644 (file)
@@ -4,8 +4,8 @@ error[E0191]: the value of the associated type `B` (from the trait `Foo`) must b
 LL |     type B;
    |     ------- `B` defined here
 ...
-LL |     let b = &42isize as &Foo<A=usize>;
-   |                          ^^^^^^^^^^^^ associated type `B` must be specified
+LL |     let b = &42isize as &dyn Foo<A=usize>;
+   |                          ^^^^^^^^^^^^^^^^ associated type `B` must be specified
 
 error[E0191]: the value of the associated type `A` (from the trait `Foo`) must be specified
   --> $DIR/associated-types-incomplete-object.rs:26:26
@@ -13,8 +13,8 @@ error[E0191]: the value of the associated type `A` (from the trait `Foo`) must b
 LL |     type A;
    |     ------- `A` defined here
 ...
-LL |     let c = &42isize as &Foo<B=char>;
-   |                          ^^^^^^^^^^^ associated type `A` must be specified
+LL |     let c = &42isize as &dyn Foo<B=char>;
+   |                          ^^^^^^^^^^^^^^^ associated type `A` must be specified
 
 error[E0191]: the value of the associated types `A` (from the trait `Foo`), `B` (from the trait `Foo`) must be specified
   --> $DIR/associated-types-incomplete-object.rs:29:26
@@ -24,8 +24,8 @@ LL |     type A;
 LL |     type B;
    |     ------- `B` defined here
 ...
-LL |     let d = &42isize as &Foo;
-   |                          ^^^
+LL |     let d = &42isize as &dyn Foo;
+   |                          ^^^^^^^
    |                          |
    |                          associated type `A` must be specified
    |                          associated type `B` must be specified
index 7467f33204725e3bbadc49f50249df03be97312c..109feb8e969a5f55de76f6b8cc85670124cf6cf8 100644 (file)
@@ -3,6 +3,6 @@
 trait I32Iterator = Iterator<Item = i32>;
 
 fn main() {
-    let _: &I32Iterator<Item = u32> = &vec![42].into_iter();
+    let _: &dyn I32Iterator<Item = u32> = &vec![42].into_iter();
     //~^ ERROR type mismatch
 }
index 85724cb7c6e851d1a20f8b441f9ba7ebe81c1fa5..aff067c289107a60db7cb4150658ebe39e1c8258 100644 (file)
@@ -1,8 +1,8 @@
 error[E0271]: type mismatch resolving `<std::vec::IntoIter<u32> as std::iter::Iterator>::Item == i32`
-  --> $DIR/associated-types-overridden-binding-2.rs:6:39
+  --> $DIR/associated-types-overridden-binding-2.rs:6:43
    |
-LL |     let _: &I32Iterator<Item = u32> = &vec![42].into_iter();
-   |                                       ^^^^^^^^^^^^^^^^^^^^^ expected u32, found i32
+LL |     let _: &dyn I32Iterator<Item = u32> = &vec![42].into_iter();
+   |                                           ^^^^^^^^^^^^^^^^^^^^^ expected u32, found i32
    |
    = note: expected type `u32`
               found type `i32`
index ea3a61b2befae9b847c12e84a40ca0a10a31bdf1..fa1889389fd5c5ecdb5fdc5c71939a847e8585b3 100644 (file)
@@ -7,5 +7,5 @@ trait Bar: Foo<Item = u32> {} //~ ERROR type annotations required
 trait U32Iterator = I32Iterator<Item = u32>;
 
 fn main() {
-    let _: &I32Iterator<Item = u32>;
+    let _: &dyn I32Iterator<Item = u32>;
 }
index 9258854245c84149a7f477eef49667f8c08dba38..36fa06cce4dd692bf43cb90e65d53b707eb1bba5 100644 (file)
@@ -1,14 +1,14 @@
 error[E0582]: binding for associated type `Output` references lifetime `'a`, which does not appear in the trait input types
-  --> $DIR/bound-lifetime-constrained.rs:28:56
+  --> $DIR/bound-lifetime-constrained.rs:28:60
    |
-LL | fn object1(_: Box<for<'a> Fn(<() as Foo<'a>>::Item) -> &'a i32>) {
-   |                                                        ^^^^^^^
+LL | fn object1(_: Box<dyn for<'a> Fn(<() as Foo<'a>>::Item) -> &'a i32>) {
+   |                                                            ^^^^^^^
 
 error[E0582]: binding for associated type `Output` references lifetime `'a`, which does not appear in the trait input types
-  --> $DIR/bound-lifetime-constrained.rs:33:35
+  --> $DIR/bound-lifetime-constrained.rs:33:39
    |
-LL | fn object2(_: Box<for<'a> Fn() -> <() as Foo<'a>>::Item>) {
-   |                                   ^^^^^^^^^^^^^^^^^^^^^
+LL | fn object2(_: Box<dyn for<'a> Fn() -> <() as Foo<'a>>::Item>) {
+   |                                       ^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to 2 previous errors
 
index b590f88b60dca48faef83f8fd14aa45935c64b26..fb82b3fa666606230e011d3dd3c39e0f61711be4 100644 (file)
@@ -25,12 +25,12 @@ fn func2(_: for<'a> fn() -> <() as Foo<'a>>::Item) {
 }
 
 #[cfg(object)]
-fn object1(_: Box<for<'a> Fn(<() as Foo<'a>>::Item) -> &'a i32>) {
+fn object1(_: Box<dyn for<'a> Fn(<() as Foo<'a>>::Item) -> &'a i32>) {
     //[object]~^ ERROR E0582
 }
 
 #[cfg(object)]
-fn object2(_: Box<for<'a> Fn() -> <() as Foo<'a>>::Item>) {
+fn object2(_: Box<dyn for<'a> Fn() -> <() as Foo<'a>>::Item>) {
     //[object]~^ ERROR E0582
 }
 
index fee64c0f663b766dbc5a08a513f82122848f2317..54f4bb9076b284422163eba7bb5c25edc67104f6 100644 (file)
@@ -17,10 +17,10 @@ LL | fn angle2<T>() where for<'a> T: Foo<Item=&'a i32> {
    |                                     ^^^^^^^^^^^^
 
 error[E0582]: binding for associated type `Item` references lifetime `'a`, which does not appear in the trait input types
-  --> $DIR/bound-lifetime-in-binding-only.rs:27:27
+  --> $DIR/bound-lifetime-in-binding-only.rs:27:31
    |
-LL | fn angle3(_: &for<'a> Foo<Item=&'a i32>) {
-   |                           ^^^^^^^^^^^^
+LL | fn angle3(_: &dyn for<'a> Foo<Item=&'a i32>) {
+   |                               ^^^^^^^^^^^^
 
 error: aborting due to 4 previous errors
 
index 8c9480027e62a113b6a1a2fe54c0d8f05df56a33..74bc84c222aa7554d9271c54d8f32965d943b8b1 100644 (file)
@@ -17,10 +17,10 @@ LL | fn paren2<T>() where for<'a> T: Fn() -> &'a i32 {
    |                                         ^^^^^^^
 
 error[E0582]: binding for associated type `Output` references lifetime `'a`, which does not appear in the trait input types
-  --> $DIR/bound-lifetime-in-binding-only.rs:47:31
+  --> $DIR/bound-lifetime-in-binding-only.rs:47:35
    |
-LL | fn paren3(_: &for<'a> Fn() -> &'a i32) {
-   |                               ^^^^^^^
+LL | fn paren3(_: &dyn for<'a> Fn() -> &'a i32) {
+   |                                   ^^^^^^^
 
 error: aborting due to 4 previous errors
 
index e1989d35bbb8c3b11b22fe40cde311bb8c1da0d3..843f5f0619588c6404901e9689e7d15c9056f920 100644 (file)
@@ -24,7 +24,7 @@ fn angle2<T>() where for<'a> T: Foo<Item=&'a i32> {
 }
 
 #[cfg(angle)]
-fn angle3(_: &for<'a> Foo<Item=&'a i32>) {
+fn angle3(_: &dyn for<'a> Foo<Item=&'a i32>) {
     //[angle]~^ ERROR binding for associated type `Item` references lifetime `'a`
 }
 
@@ -44,7 +44,7 @@ fn paren2<T>() where for<'a> T: Fn() -> &'a i32 {
 }
 
 #[cfg(paren)]
-fn paren3(_: &for<'a> Fn() -> &'a i32) {
+fn paren3(_: &dyn for<'a> Fn() -> &'a i32) {
     //[paren]~^ ERROR binding for associated type `Output` references lifetime `'a`
 }
 
index 5a7e086fd476c8987a3ddc5099ec5e42cf01144a..9c0dc61494d1f9cf1046da46568d19ec301b9f43 100644 (file)
@@ -38,11 +38,11 @@ fn elision(_: fn() -> &i32) {
 struct Parameterized<'a> { x: &'a str }
 
 #[cfg(ok)]
-fn ok1(_: &for<'a> Fn(&Parameterized<'a>) -> &'a i32) {
+fn ok1(_: &dyn for<'a> Fn(&Parameterized<'a>) -> &'a i32) {
 }
 
 #[cfg(ok)]
-fn ok2(_: &for<'a,'b> Fn<(&'b Parameterized<'a>,), Output=&'a i32>) {
+fn ok2(_: &dyn for<'a,'b> Fn<(&'b Parameterized<'a>,), Output=&'a i32>) {
 }
 
 #[rustc_error]
index 856a778078a61c323141838f3bb1f0d777afead4..e94a5f0853d72c7d4cbcede4469c2af31ed0d02c 100644 (file)
@@ -19,7 +19,7 @@ struct MyStream<C: ?Sized + MyClosure> {
 async fn get_future<C: ?Sized + MyClosure>(_stream: MyStream<C>) {}
 
 async fn f() {
-    let messages: MyStream<FnMut()> = unimplemented!();
+    let messages: MyStream<dyn FnMut()> = unimplemented!();
     await!(get_future(messages));
 }
 
index 9e4ff43ecd112486021e775a64f1a4e4a1cff8a5..2157cf7d4f7abe9aafce3e252adf2d7876df77ae 100644 (file)
@@ -35,7 +35,7 @@ fn poll(mut self: Pin<&mut Self>, cx: &mut task::Context) -> Poll<R> {
 }
 
 async fn __receive<WantFn, Fut>(want: WantFn) -> ()
-    where Fut: Future<Output = ()>, WantFn: Fn(&Box<Send + 'static>) -> Fut,
+    where Fut: Future<Output = ()>, WantFn: Fn(&Box<dyn Send + 'static>) -> Fut,
 {
     await!(lazy(|_| ()));
 }
index d6f18875c9e3abc6a42adc5f3342938193fab0b6..ad18f411875690413a23a64f3510ad54afb7215d 100644 (file)
@@ -9,7 +9,7 @@ trait SomeTrait: Send + Sync + 'static {
     fn do_something(&self);
 }
 
-async fn my_task(obj: Arc<SomeTrait>) {
+async fn my_task(obj: Arc<dyn SomeTrait>) {
     unimplemented!()
 }
 
index 0da4e456f088daaac736025b0776ad5e1ed3a7b0..b899c59ff2ea702b31c5f758c7bd7633789c4dd1 100644 (file)
@@ -1,7 +1,7 @@
 trait Trait {}
 
 pub fn main() {
-    let x: Vec<Trait + Sized> = Vec::new();
+    let x: Vec<dyn Trait + Sized> = Vec::new();
     //~^ ERROR only auto traits can be used as additional traits in a trait object
     //~| ERROR the size for values of type
     //~| ERROR the size for values of type
index 6307af5d725d139c0270ec9232ef643566b94a87..e9ded557281a445c69632749b607d8b04ec05a89 100644 (file)
@@ -1,29 +1,29 @@
 error[E0225]: only auto traits can be used as additional traits in a trait object
-  --> $DIR/bad-sized.rs:4:24
+  --> $DIR/bad-sized.rs:4:28
    |
-LL |     let x: Vec<Trait + Sized> = Vec::new();
-   |                -----   ^^^^^
-   |                |       |
-   |                |       additional non-auto trait
-   |                |       trait alias used in trait object type (additional use)
-   |                first non-auto trait
-   |                trait alias used in trait object type (first use)
+LL |     let x: Vec<dyn Trait + Sized> = Vec::new();
+   |                    -----   ^^^^^
+   |                    |       |
+   |                    |       additional non-auto trait
+   |                    |       trait alias used in trait object type (additional use)
+   |                    first non-auto trait
+   |                    trait alias used in trait object type (first use)
 
 error[E0277]: the size for values of type `dyn Trait` cannot be known at compilation time
   --> $DIR/bad-sized.rs:4:12
    |
-LL |     let x: Vec<Trait + Sized> = Vec::new();
-   |            ^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
+LL |     let x: Vec<dyn Trait + Sized> = Vec::new();
+   |            ^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `dyn Trait`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
    = note: required by `std::vec::Vec`
 
 error[E0277]: the size for values of type `dyn Trait` cannot be known at compilation time
-  --> $DIR/bad-sized.rs:4:33
+  --> $DIR/bad-sized.rs:4:37
    |
-LL |     let x: Vec<Trait + Sized> = Vec::new();
-   |                                 ^^^^^^^^ doesn't have a size known at compile-time
+LL |     let x: Vec<dyn Trait + Sized> = Vec::new();
+   |                                     ^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `dyn Trait`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index 5e853afd38c872090ab1c268c5888bdf7e767507..b4d85b60cd5afbb0e3f063d3c40f8e1959ce179f 100644 (file)
@@ -8,7 +8,7 @@ trait Foo {
     fn f2(&mut self);
 }
 
-fn test(x: &mut Foo) {
+fn test(x: &mut dyn Foo) {
     let y = x.f1();
     x.f2(); //~ ERROR cannot borrow `*x` as mutable
     y.use_ref();
index ed669c4d901516b124d0cfc8c4c356973c3b05eb..6b32d185b6fdf5c3dbdeafb01f67efeaf93f76e5 100644 (file)
@@ -2,10 +2,10 @@
 
 trait Foo { fn dummy(&self); }
 
-fn consume(_: Box<Foo>) {
+fn consume(_: Box<dyn Foo>) {
 }
 
-fn foo(b: Box<Foo+Send>) {
+fn foo(b: Box<dyn Foo + Send>) {
     consume(b);
     consume(b); //~ ERROR use of moved value
 }
index e8194ad69440367fac754a0b8479a9e19de7978a..356cda01e29c8eb3e3f5b55598e005f40528756f 100644 (file)
@@ -1,7 +1,7 @@
 error[E0382]: use of moved value: `b`
   --> $DIR/borrowck-consume-upcast-box.rs:10:13
    |
-LL | fn foo(b: Box<Foo+Send>) {
+LL | fn foo(b: Box<dyn Foo + Send>) {
    |        - move occurs because `b` has type `std::boxed::Box<dyn Foo + std::marker::Send>`, which does not implement the `Copy` trait
 LL |     consume(b);
    |             - value moved here
index a44e3031e256fd1d63adff4b6acd5224b0a705cc..b50d455637b9a5438e1ea269a86ba4d8e1145cd0 100644 (file)
@@ -6,7 +6,7 @@
 //    closure may outlive the current function, but it borrows `books`,
 //    which is owned by the current function
 
-fn foo<'a>(x: &'a i32) -> Box<FnMut()+'a> {
+fn foo<'a>(x: &'a i32) -> Box<dyn FnMut() + 'a> {
     let mut books = vec![1,2,3];
     Box::new(|| books.push(4))
     //~^ ERROR E0373
index 43bb652a024ff4793defb10d7ed37eb7b90379b3..c468740bc3bf573252005940caaf7fcae533b462 100644 (file)
@@ -1,6 +1,6 @@
 // check that borrowck looks inside consts/statics
 
-static FN : &'static (Fn() -> (Box<Fn()->Box<i32>>) + Sync) = &|| {
+static FN : &'static (dyn Fn() -> (Box<dyn Fn()->Box<i32>>) + Sync) = &|| {
     let x = Box::new(0);
     Box::new(|| x) //~ ERROR cannot move out of captured variable in an `Fn` closure
 };
index 495516cf97634ff1f808a002e2991a1ae46b6d9f..137a9adbc40ac36b23b2ee9f3a50146c747ca7e2 100644 (file)
@@ -8,26 +8,26 @@ trait Foo {
     fn mut_borrowed(&mut self) -> &();
 }
 
-fn borrowed_receiver(x: &Foo) {
+fn borrowed_receiver(x: &dyn Foo) {
     let y = x.borrowed();
     let z = x.borrowed();
     z.use_ref();
     y.use_ref();
 }
 
-fn mut_borrowed_receiver(x: &mut Foo) {
+fn mut_borrowed_receiver(x: &mut dyn Foo) {
     let y = x.borrowed();
     let z = x.mut_borrowed(); //~ ERROR cannot borrow
     y.use_ref();
 }
 
-fn mut_owned_receiver(mut x: Box<Foo>) {
+fn mut_owned_receiver(mut x: Box<dyn Foo>) {
     let y = x.borrowed();
     let z = &mut x; //~ ERROR cannot borrow
     y.use_ref();
 }
 
-fn imm_owned_receiver(mut x: Box<Foo>) {
+fn imm_owned_receiver(mut x: Box<dyn Foo>) {
     let y = x.borrowed();
     let z = &x;
     z.use_ref();
index 1e272372f6c9435cd51498d9fbada1b206d558b4..3ce72161814949f9896dccd488bb0964085bc688 100644 (file)
@@ -6,5 +6,5 @@ impl Foo for i32 { }
 
 fn main() {
     let x: &i32;
-    let y = x as *const Foo; //~ ERROR [E0381]
+    let y = x as *const dyn Foo; //~ ERROR [E0381]
 }
index df610cbb5618f8aed2b0d5cc01fa70ea19eefbb0..2b80140c6b376e714b33fd353405d2b15a76432f 100644 (file)
@@ -1,7 +1,7 @@
 error[E0381]: borrow of possibly uninitialized variable: `x`
   --> $DIR/borrowck-use-uninitialized-in-cast-trait.rs:9:13
    |
-LL |     let y = x as *const Foo;
+LL |     let y = x as *const dyn Foo;
    |             ^ use of possibly uninitialized `*x`
 
 error: aborting due to previous error
index 62ddf4decfcabd276d4a17cce071d2a501ba80fd..d8bef927fd722f4a853cdcb73c182cdaabeb5159 100644 (file)
@@ -1,4 +1,4 @@
-fn with_int(f: &mut FnMut(&isize)) {
+fn with_int(f: &mut dyn FnMut(&isize)) {
 }
 
 fn main() {
index fca425da34d37412f6db8bfa5f4a691086b1ec5b..baf122df5e268e27515371644a682e728c23b11f 100644 (file)
@@ -29,7 +29,7 @@ LL |         f(f(10));
 error[E0382]: use of moved value: `f`
   --> $DIR/two-phase-nonrecv-autoref.rs:80:11
    |
-LL |     fn twice_ten_oo(f: Box<FnOnce(i32) -> i32>) {
+LL |     fn twice_ten_oo(f: Box<dyn FnOnce(i32) -> i32>) {
    |                     - move occurs because `f` has type `std::boxed::Box<dyn std::ops::FnOnce(i32) -> i32>`, which does not implement the `Copy` trait
 LL |         f(f(10));
    |         - ^ value used here after move
index c0a117d6766d52840353d2660dfa9039e359923a..b29664e3d8cbd67a30a2c47fa54e2765635213a3 100644 (file)
@@ -68,15 +68,15 @@ fn twice_ten_so<F: FnOnce(i32) -> i32>(f: Box<F>) {
         //[g2p]~^^  ERROR use of moved value: `f`
     }
 
-    fn twice_ten_om(f: &mut FnMut(i32) -> i32) {
+    fn twice_ten_om(f: &mut dyn FnMut(i32) -> i32) {
         f(f(10));
         //[nll]~^   ERROR cannot borrow `*f` as mutable more than once at a time
         //[g2p]~^^  ERROR cannot borrow `*f` as mutable more than once at a time
     }
-    fn twice_ten_oi(f: &mut Fn(i32) -> i32) {
+    fn twice_ten_oi(f: &mut dyn Fn(i32) -> i32) {
         f(f(10));
     }
-    fn twice_ten_oo(f: Box<FnOnce(i32) -> i32>) {
+    fn twice_ten_oo(f: Box<dyn FnOnce(i32) -> i32>) {
         f(f(10));
         //[nll]~^   ERROR use of moved value: `f`
         //[g2p]~^^  ERROR use of moved value: `f`
index 8abfe3e4b7623bde133aa65822600122fef909ff..31aa4011b91143ba750f1d1aa57bd8ee44878350 100644 (file)
@@ -2,6 +2,6 @@
 type B = for<'b, 'a: 'b,> fn(); //~ ERROR lifetime bounds cannot be used in this context
 type C = for<'b, 'a: 'b +> fn(); //~ ERROR lifetime bounds cannot be used in this context
 type D = for<'a, T> fn(); //~ ERROR only lifetime parameters can be used in this context
-type E = for<T> Fn(); //~ ERROR only lifetime parameters can be used in this context
+type E = dyn for<T> Fn(); //~ ERROR only lifetime parameters can be used in this context
 
 fn main() {}
index 21a7814626746a8bd66980bd8750620b41c966b1..a0395ed49045f75a3cf54f21d23a783e15af5ea5 100644 (file)
@@ -23,10 +23,10 @@ LL | type D = for<'a, T> fn();
    |                  ^
 
 error: only lifetime parameters can be used in this context
-  --> $DIR/bounds-lifetime.rs:5:14
+  --> $DIR/bounds-lifetime.rs:5:18
    |
-LL | type E = for<T> Fn();
-   |              ^
+LL | type E = dyn for<T> Fn();
+   |                  ^
 
 error: aborting due to 5 previous errors
 
index ac859c512637e0943aaaee7101fddec47128434c..5342b595c7c5e9f1d2c7891e8fb59a4b7d968e06 100644 (file)
@@ -1,4 +1,4 @@
 fn main() {
-    &1 as Send; //~ ERROR cast to unsized
-    Box::new(1) as Send; //~ ERROR cast to unsized
+    &1 as dyn Send; //~ ERROR cast to unsized
+    Box::new(1) as dyn Send; //~ ERROR cast to unsized
 }
index bd7a0e1834aa7d43d06e7f3ef2fafb2093f39965..ffa02533d8b66db7869c917abf13b15225b8c4e8 100644 (file)
@@ -1,18 +1,18 @@
 error[E0620]: cast to unsized type: `&{integer}` as `dyn std::marker::Send`
   --> $DIR/cast-to-unsized-trait-object-suggestion.rs:2:5
    |
-LL |     &1 as Send;
-   |     ^^^^^^----
+LL |     &1 as dyn Send;
+   |     ^^^^^^--------
    |           |
-   |           help: try casting to a reference instead: `&Send`
+   |           help: try casting to a reference instead: `&dyn Send`
 
 error[E0620]: cast to unsized type: `std::boxed::Box<{integer}>` as `dyn std::marker::Send`
   --> $DIR/cast-to-unsized-trait-object-suggestion.rs:3:5
    |
-LL |     Box::new(1) as Send;
-   |     ^^^^^^^^^^^^^^^----
+LL |     Box::new(1) as dyn Send;
+   |     ^^^^^^^^^^^^^^^--------
    |                    |
-   |                    help: try casting to a `Box` instead: `Box<Send>`
+   |                    help: try casting to a `Box` instead: `Box<dyn Send>`
 
 error: aborting due to 2 previous errors
 
index cba178104c99fc13703a5e76b028b4ff91212a57..d4a0f9613055ee5abf87eccec3fffe4df7a0dff1 100644 (file)
@@ -5,7 +5,7 @@ fn foo() -> Box<impl fmt::Debug+?Sized> {
     x
 }
 fn bar() -> Box<impl fmt::Debug+?Sized> {
-    let y: Box<fmt::Debug> = Box::new([0]);
+    let y: Box<dyn fmt::Debug> = Box::new([0]);
     y
 }
 
index 3ae4987254fce3874d368fe1fc1113e8fb5a7b77..bb4c3fac93806e8303d9301609558cb083dfd653 100644 (file)
@@ -49,6 +49,6 @@ fn cat(in_x : usize, in_y : isize, in_name: String) -> Cat {
 }
 
 fn main() {
-  let nyan: Box<Noisy> = box cat(0, 2, "nyan".to_string()) as Box<Noisy>;
+  let nyan: Box<dyn Noisy> = box cat(0, 2, "nyan".to_string()) as Box<dyn Noisy>;
   nyan.eat(); //~ ERROR no method named `eat` found
 }
index e5840181e41ef99f5cdfd703bfad9c945a7dccea..0a015ea1436c5d69df9138d0a3aec50f2080e72c 100644 (file)
@@ -1,4 +1,4 @@
-fn foo() -> Box<Fn()> {
+fn foo() -> Box<dyn Fn()> {
     let num = 5;
 
     let closure = || { //~ ERROR expected a closure that
index d33420c52a0355a714e2e0bab34b89b6dd6b9a73..511690e9dd4b380048bb989bab49855c15db5bee 100644 (file)
@@ -1,4 +1,4 @@
-fn get_closure() -> Box<Fn() -> Vec<u8>> {
+fn get_closure() -> Box<dyn Fn() -> Vec<u8>> {
     let vec = vec![1u8, 2u8];
 
     let closure = move || { //~ ERROR expected a closure
index ac17bfdc941c8d30b255a3cd5b421d59125a669e..a7f16d70ba8600d083f246acc285f0f9c6fb24d7 100644 (file)
@@ -2,6 +2,8 @@ fn main() {
     |_: [_; continue]| {}; //~ ERROR: `continue` outside of loop
 
     while |_: [_; continue]| {} {} //~ ERROR: `continue` outside of loop
+    //~^ ERROR mismatched types
 
     while |_: [_; break]| {} {} //~ ERROR: `break` outside of loop
+    //~^ ERROR mismatched types
 }
index 9b78aa16a580fabc10079b9822722d8bae234df2..46fbd3e0fae0be8d7b980ff9971850bc3d23b502 100644 (file)
@@ -11,11 +11,30 @@ LL |     while |_: [_; continue]| {} {}
    |                   ^^^^^^^^ cannot break outside of a loop
 
 error[E0268]: `break` outside of loop
-  --> $DIR/closure-array-break-length.rs:6:19
+  --> $DIR/closure-array-break-length.rs:7:19
    |
 LL |     while |_: [_; break]| {} {}
    |                   ^^^^^ cannot break outside of a loop
 
-error: aborting due to 3 previous errors
+error[E0308]: mismatched types
+  --> $DIR/closure-array-break-length.rs:4:11
+   |
+LL |     while |_: [_; continue]| {} {}
+   |           ^^^^^^^^^^^^^^^^^^^^^ expected bool, found closure
+   |
+   = note: expected type `bool`
+              found type `[closure@$DIR/closure-array-break-length.rs:4:11: 4:32]`
+
+error[E0308]: mismatched types
+  --> $DIR/closure-array-break-length.rs:7:11
+   |
+LL |     while |_: [_; break]| {} {}
+   |           ^^^^^^^^^^^^^^^^^^ expected bool, found closure
+   |
+   = note: expected type `bool`
+              found type `[closure@$DIR/closure-array-break-length.rs:7:11: 7:29]`
+
+error: aborting due to 5 previous errors
 
-For more information about this error, try `rustc --explain E0268`.
+Some errors have detailed explanations: E0268, E0308.
+For more information about an error, try `rustc --explain E0268`.
index 03240d4857ca8a5a1c9f33dd4b1e866816efa2ef..102f1f94a36e1da366b0bbf49c88f7d2208be6be 100644 (file)
@@ -2,7 +2,7 @@
 
 // Point at the captured immutable outer variable
 
-fn foo(mut f: Box<FnMut()>) {
+fn foo(mut f: Box<dyn FnMut()>) {
     f();
 }
 
index 8fa9e44845d5b41d640c9e4c88be32ee814e52ca..6eb43b372c96cc3bc23d5a8288c7e7cf2a49e63e 100644 (file)
@@ -2,7 +2,7 @@
 
 // Point at the captured immutable outer variable
 
-fn foo(mut f: Box<FnMut()>) {
+fn foo(mut f: Box<dyn FnMut()>) {
     f();
 }
 
index f35fbad7cd6dfaf7deef18e4bfc0b9def89847fc..414acfd84ce4e2e6369af9478c52ad6a2686bc9b 100644 (file)
@@ -1,6 +1,6 @@
 #![allow(dead_code)]
 
 trait C {}
-impl C { fn f() {} } //~ ERROR duplicate
-impl C { fn f() {} }
+impl dyn C { fn f() {} } //~ ERROR duplicate
+impl dyn C { fn f() {} }
 fn main() { }
index 16cdca774ba371109ea946d4503e4cffb09c7291..a97161b131d496038d003443f6963555b1438549 100644 (file)
@@ -1,10 +1,10 @@
 error[E0592]: duplicate definitions with name `f`
-  --> $DIR/coherence-overlapping-inherent-impl-trait.rs:4:10
+  --> $DIR/coherence-overlapping-inherent-impl-trait.rs:4:14
    |
-LL | impl C { fn f() {} }
-   |          ^^^^^^^^^ duplicate definitions for `f`
-LL | impl C { fn f() {} }
-   |          --------- other definition for `f`
+LL | impl dyn C { fn f() {} }
+   |              ^^^^^^^^^ duplicate definitions for `f`
+LL | impl dyn C { fn f() {} }
+   |              --------- other definition for `f`
 
 error: aborting due to previous error
 
index db8ab14e67371246bc3fba63a1bf6227f02469c3..b4d2f5d3c6d0949c812bf70590d5943334c7d242 100644 (file)
@@ -2,4 +2,4 @@
 
 trait Foo { }
 
-type Bar = Foo;
+type Bar = dyn Foo;
index 9a4e134cb39a499ed48e3c92edff2aa7ceb3eb41..c139e823c2aef64e07f1b01528e7aa99e21e51c1 100644 (file)
@@ -10,23 +10,23 @@ pub fn main() {
     let _ = box if true { [1, 2, 3] } else { [1, 3, 4] }: Box<[i32]>; //~ ERROR mismatched types
     let _ = box match true { true => [1, 2, 3], false => [1, 3, 4] }: Box<[i32]>;
     //~^ ERROR mismatched types
-    let _ = box { |x| (x as u8) }: Box<Fn(i32) -> _>; //~ ERROR mismatched types
-    let _ = box if true { false } else { true }: Box<Debug>; //~ ERROR mismatched types
-    let _ = box match true { true => 'a', false => 'b' }: Box<Debug>; //~ ERROR mismatched types
+    let _ = box { |x| (x as u8) }: Box<dyn Fn(i32) -> _>; //~ ERROR mismatched types
+    let _ = box if true { false } else { true }: Box<dyn Debug>; //~ ERROR mismatched types
+    let _ = box match true { true => 'a', false => 'b' }: Box<dyn Debug>; //~ ERROR mismatched types
 
     let _ = &{ [1, 2, 3] }: &[i32]; //~ ERROR mismatched types
     let _ = &if true { [1, 2, 3] } else { [1, 3, 4] }: &[i32]; //~ ERROR mismatched types
     let _ = &match true { true => [1, 2, 3], false => [1, 3, 4] }: &[i32];
     //~^ ERROR mismatched types
-    let _ = &{ |x| (x as u8) }: &Fn(i32) -> _; //~ ERROR mismatched types
-    let _ = &if true { false } else { true }: &Debug; //~ ERROR mismatched types
-    let _ = &match true { true => 'a', false => 'b' }: &Debug; //~ ERROR mismatched types
+    let _ = &{ |x| (x as u8) }: &dyn Fn(i32) -> _; //~ ERROR mismatched types
+    let _ = &if true { false } else { true }: &dyn Debug; //~ ERROR mismatched types
+    let _ = &match true { true => 'a', false => 'b' }: &dyn Debug; //~ ERROR mismatched types
 
     let _ = Box::new([1, 2, 3]): Box<[i32]>; //~ ERROR mismatched types
-    let _ = Box::new(|x| (x as u8)): Box<Fn(i32) -> _>; //~ ERROR mismatched types
+    let _ = Box::new(|x| (x as u8)): Box<dyn Fn(i32) -> _>; //~ ERROR mismatched types
 
     let _ = vec![
         Box::new(|x| (x as u8)),
         box |x| (x as i16 as u8),
-    ]: Vec<Box<Fn(i32) -> _>>;
+    ]: Vec<Box<dyn Fn(i32) -> _>>;
 }
index be362c9a78b98855570b182728c4fe6d5e808bb1..3b81610a06e097d9e8dcd5af2f9a6c20c0fd72f2 100644 (file)
@@ -28,7 +28,7 @@ LL |     let _ = box match true { true => [1, 2, 3], false => [1, 3, 4] }: Box<[
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:13:13
    |
-LL |     let _ = box { |x| (x as u8) }: Box<Fn(i32) -> _>;
+LL |     let _ = box { |x| (x as u8) }: Box<dyn Fn(i32) -> _>;
    |             ^^^^^^^^^^^^^^^^^^^^^ expected trait std::ops::Fn, found closure
    |
    = note: expected type `std::boxed::Box<dyn std::ops::Fn(i32) -> u8>`
@@ -37,7 +37,7 @@ LL |     let _ = box { |x| (x as u8) }: Box<Fn(i32) -> _>;
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:14:13
    |
-LL |     let _ = box if true { false } else { true }: Box<Debug>;
+LL |     let _ = box if true { false } else { true }: Box<dyn Debug>;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected trait std::fmt::Debug, found bool
    |
    = note: expected type `std::boxed::Box<dyn std::fmt::Debug>`
@@ -46,7 +46,7 @@ LL |     let _ = box if true { false } else { true }: Box<Debug>;
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:15:13
    |
-LL |     let _ = box match true { true => 'a', false => 'b' }: Box<Debug>;
+LL |     let _ = box match true { true => 'a', false => 'b' }: Box<dyn Debug>;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected trait std::fmt::Debug, found char
    |
    = note: expected type `std::boxed::Box<dyn std::fmt::Debug>`
@@ -82,7 +82,7 @@ LL |     let _ = &match true { true => [1, 2, 3], false => [1, 3, 4] }: &[i32];
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:21:13
    |
-LL |     let _ = &{ |x| (x as u8) }: &Fn(i32) -> _;
+LL |     let _ = &{ |x| (x as u8) }: &dyn Fn(i32) -> _;
    |             ^^^^^^^^^^^^^^^^^^ expected trait std::ops::Fn, found closure
    |
    = note: expected type `&dyn std::ops::Fn(i32) -> u8`
@@ -91,7 +91,7 @@ LL |     let _ = &{ |x| (x as u8) }: &Fn(i32) -> _;
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:22:13
    |
-LL |     let _ = &if true { false } else { true }: &Debug;
+LL |     let _ = &if true { false } else { true }: &dyn Debug;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected trait std::fmt::Debug, found bool
    |
    = note: expected type `&dyn std::fmt::Debug`
@@ -100,7 +100,7 @@ LL |     let _ = &if true { false } else { true }: &Debug;
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:23:13
    |
-LL |     let _ = &match true { true => 'a', false => 'b' }: &Debug;
+LL |     let _ = &match true { true => 'a', false => 'b' }: &dyn Debug;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected trait std::fmt::Debug, found char
    |
    = note: expected type `&dyn std::fmt::Debug`
@@ -118,7 +118,7 @@ LL |     let _ = Box::new([1, 2, 3]): Box<[i32]>;
 error[E0308]: mismatched types
   --> $DIR/coerce-expect-unsized-ascribed.rs:26:13
    |
-LL |     let _ = Box::new(|x| (x as u8)): Box<Fn(i32) -> _>;
+LL |     let _ = Box::new(|x| (x as u8)): Box<dyn Fn(i32) -> _>;
    |             ^^^^^^^^^^^^^^^^^^^^^^^ expected trait std::ops::Fn, found closure
    |
    = note: expected type `std::boxed::Box<dyn std::ops::Fn(i32) -> _>`
index b48f6bbfb94173b5014619501417e84bc9081ea7..c38d7456a995219eed1a3848c044b1eaa133784a 100644 (file)
@@ -1,7 +1,7 @@
 error[E0038]: the trait `NotObjectSafe` cannot be made into an object
   --> $DIR/coherence-impl-trait-for-trait-object-safe.rs:11:6
    |
-LL | impl NotObjectSafe for NotObjectSafe { }
+LL | impl NotObjectSafe for dyn NotObjectSafe { }
    |      ^^^^^^^^^^^^^ the trait `NotObjectSafe` cannot be made into an object
    |
    = note: method `eq` references the `Self` type in its arguments or return type
index b48f6bbfb94173b5014619501417e84bc9081ea7..c38d7456a995219eed1a3848c044b1eaa133784a 100644 (file)
@@ -1,7 +1,7 @@
 error[E0038]: the trait `NotObjectSafe` cannot be made into an object
   --> $DIR/coherence-impl-trait-for-trait-object-safe.rs:11:6
    |
-LL | impl NotObjectSafe for NotObjectSafe { }
+LL | impl NotObjectSafe for dyn NotObjectSafe { }
    |      ^^^^^^^^^^^^^ the trait `NotObjectSafe` cannot be made into an object
    |
    = note: method `eq` references the `Self` type in its arguments or return type
index 803e8fc6bca64c558a1de5cd95a6f01f8431ef8b..b4c88e937830e738c60f5817518de76fc1fb1506 100644 (file)
@@ -8,7 +8,7 @@
 // If the trait is not object-safe, we give a more tailored message
 // because we're such schnuckels:
 trait NotObjectSafe { fn eq(&self, other: Self); }
-impl NotObjectSafe for NotObjectSafe { }
+impl NotObjectSafe for dyn NotObjectSafe { }
 //[old]~^ ERROR E0038
 //[re]~^^ ERROR E0038
 
index 324747603f91128fbaf2e6f519f686abacab4d2d..4819ce9260e708cc2dd7150d80bab95474ffab04 100644 (file)
@@ -1,20 +1,20 @@
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Foo`
   --> $DIR/coherence-impl-trait-for-trait.rs:13:1
    |
-LL | impl Foo for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Foo`
+LL | impl Foo for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Foo`
 
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Bar`
   --> $DIR/coherence-impl-trait-for-trait.rs:16:1
    |
-LL | impl Bar for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Bar`
+LL | impl Bar for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Bar`
 
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Baz`
   --> $DIR/coherence-impl-trait-for-trait.rs:19:1
    |
-LL | impl Baz for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Baz`
+LL | impl Baz for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Baz`
 
 error: aborting due to 3 previous errors
 
index 324747603f91128fbaf2e6f519f686abacab4d2d..4819ce9260e708cc2dd7150d80bab95474ffab04 100644 (file)
@@ -1,20 +1,20 @@
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Foo`
   --> $DIR/coherence-impl-trait-for-trait.rs:13:1
    |
-LL | impl Foo for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Foo`
+LL | impl Foo for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Foo`
 
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Bar`
   --> $DIR/coherence-impl-trait-for-trait.rs:16:1
    |
-LL | impl Bar for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Bar`
+LL | impl Bar for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Bar`
 
 error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Baz`
   --> $DIR/coherence-impl-trait-for-trait.rs:19:1
    |
-LL | impl Baz for Baz { }
-   | ^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Baz`
+LL | impl Baz for dyn Baz { }
+   | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Baz`
 
 error: aborting due to 3 previous errors
 
index dcaf564fdecfed1fb4be5b77d75dc4dccc82823e..3ce3dca0660b94ec8735fb069d73e0313c54ffb3 100644 (file)
@@ -10,18 +10,18 @@ trait Bar: Foo { }
 trait Baz: Bar { }
 
 // Supertraits of Baz are not legal:
-impl Foo for Baz { }
+impl Foo for dyn Baz { }
 //[old]~^ ERROR E0371
 //[re]~^^ ERROR E0371
-impl Bar for Baz { }
+impl Bar for dyn Baz { }
 //[old]~^ ERROR E0371
 //[re]~^^ ERROR E0371
-impl Baz for Baz { }
+impl Baz for dyn Baz { }
 //[old]~^ ERROR E0371
 //[re]~^^ ERROR E0371
 
 // But other random traits are:
 trait Other { }
-impl Other for Baz { } // OK, Other not a supertrait of Baz
+impl Other for dyn Baz { } // OK, Other not a supertrait of Baz
 
 fn main() { }
index c242b6c2c20a28047a87918c1ebe2385284ec52c..8aef091fe31860c1d8ceb9b5a7b6fd9b305ba8a7 100644 (file)
@@ -14,7 +14,7 @@ struct Obj<F> where F: FnOnce() -> u32 {
 }
 
 struct BoxedObj {
-    boxed_closure: Box<FnOnce() -> u32>,
+    boxed_closure: Box<dyn FnOnce() -> u32>,
 }
 
 struct Wrapper<F> where F: FnMut() -> u32 {
@@ -25,8 +25,8 @@ fn func() -> u32 {
     0
 }
 
-fn check_expression() -> Obj<Box<FnOnce() -> u32>> {
-    Obj { closure: Box::new(|| 42_u32) as Box<FnOnce() -> u32>, not_closure: 42 }
+fn check_expression() -> Obj<Box<dyn FnOnce() -> u32>> {
+    Obj { closure: Box::new(|| 42_u32) as Box<dyn FnOnce() -> u32>, not_closure: 42 }
 }
 
 fn main() {
@@ -44,7 +44,7 @@ fn main() {
     let boxed_fn = BoxedObj { boxed_closure: Box::new(func) };
     boxed_fn.boxed_closure();//~ ERROR no method named `boxed_closure` found
 
-    let boxed_closure = BoxedObj { boxed_closure: Box::new(|| 42_u32) as Box<FnOnce() -> u32> };
+    let boxed_closure = BoxedObj { boxed_closure: Box::new(|| 42_u32) as Box<dyn FnOnce() -> u32> };
     boxed_closure.boxed_closure();//~ ERROR no method named `boxed_closure` found
 
     // test expression writing in the notes
index 02c6838d41941ba5936994c046978f4385a974e3..5a024aa4b67492d7fde0c0eaf930a8e0f4424b48 100644 (file)
@@ -1,5 +1,5 @@
 struct Example {
-    example: Box<Fn(i32) -> i32>
+    example: Box<dyn Fn(i32) -> i32>
 }
 
 fn main() {
diff --git a/src/test/ui/const-generics/broken-mir-1.rs b/src/test/ui/const-generics/broken-mir-1.rs
new file mode 100644 (file)
index 0000000..9a11bd3
--- /dev/null
@@ -0,0 +1,17 @@
+// run-pass
+
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+pub trait Foo {
+    fn foo(&self);
+}
+
+
+impl<T, const N: usize> Foo for [T; N] {
+    fn foo(&self) {
+        let _ = &self;
+    }
+}
+
+fn main() {}
diff --git a/src/test/ui/const-generics/broken-mir-1.stderr b/src/test/ui/const-generics/broken-mir-1.stderr
new file mode 100644 (file)
index 0000000..55dc7fc
--- /dev/null
@@ -0,0 +1,6 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/broken-mir-1.rs:3:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
diff --git a/src/test/ui/const-generics/broken-mir-2.rs b/src/test/ui/const-generics/broken-mir-2.rs
new file mode 100644 (file)
index 0000000..fb9a63e
--- /dev/null
@@ -0,0 +1,9 @@
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+use std::fmt::Debug;
+
+#[derive(Debug)]
+struct S<T: Debug, const N: usize>([T; N]); //~ ERROR `[T; _]` doesn't implement `std::fmt::Debug`
+
+fn main() {}
diff --git a/src/test/ui/const-generics/broken-mir-2.stderr b/src/test/ui/const-generics/broken-mir-2.stderr
new file mode 100644 (file)
index 0000000..fb9b88b
--- /dev/null
@@ -0,0 +1,19 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/broken-mir-2.rs:1:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
+error[E0277]: `[T; _]` doesn't implement `std::fmt::Debug`
+  --> $DIR/broken-mir-2.rs:7:36
+   |
+LL | struct S<T: Debug, const N: usize>([T; N]);
+   |                                    ^^^^^^ `[T; _]` cannot be formatted using `{:?}` because it doesn't implement `std::fmt::Debug`
+   |
+   = help: the trait `std::fmt::Debug` is not implemented for `[T; _]`
+   = note: required because of the requirements on the impl of `std::fmt::Debug` for `&[T; _]`
+   = note: required for the cast to the object type `dyn std::fmt::Debug`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0277`.
index c3f5e360fe28084c73d7b0f8061f125a18966930..f592e486be951fdc6c25b9f8fab427780426fad8 100644 (file)
@@ -1,11 +1,13 @@
+// compile-pass
 #![feature(const_generics)]
 //~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
 
-// We should probably be able to infer the types here. However, this test is checking that we don't
-// get an ICE in this case. It may be modified later to not be an error.
+// This test confirms that the types can be inferred correctly for this example with const
+// generics. Previously this would ICE, and more recently error.
 
 struct Foo<const NUM_BYTES: usize>(pub [u8; NUM_BYTES]);
 
 fn main() {
     let _ = Foo::<3>([1, 2, 3]); //~ ERROR type annotations needed
+    //~^ ERROR mismatched types
 }
index a0641bd2fdc96d1a56fca57c2f682ac0ffb7738e..52907bbb67720c919d8115145e31c3d83530206b 100644 (file)
@@ -1,15 +1,6 @@
 warning: the feature `const_generics` is incomplete and may cause the compiler to crash
-  --> $DIR/cannot-infer-type-for-const-param.rs:1:12
+  --> $DIR/cannot-infer-type-for-const-param.rs:2:12
    |
 LL | #![feature(const_generics)]
    |            ^^^^^^^^^^^^^^
 
-error[E0282]: type annotations needed
-  --> $DIR/cannot-infer-type-for-const-param.rs:10:19
-   |
-LL |     let _ = Foo::<3>([1, 2, 3]);
-   |                   ^ cannot infer type for `{integer}`
-
-error: aborting due to previous error
-
-For more information about this error, try `rustc --explain E0282`.
diff --git a/src/test/ui/const-generics/fn-taking-const-generic-array.rs b/src/test/ui/const-generics/fn-taking-const-generic-array.rs
new file mode 100644 (file)
index 0000000..d3d17cc
--- /dev/null
@@ -0,0 +1,16 @@
+// run-pass
+
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+use std::fmt::Display;
+
+fn print_slice<T: Display, const N: usize>(slice: &[T; N]) {
+    for x in slice.iter() {
+        println!("{}", x);
+    }
+}
+
+fn main() {
+    print_slice(&[1, 2, 3]);
+}
diff --git a/src/test/ui/const-generics/fn-taking-const-generic-array.stderr b/src/test/ui/const-generics/fn-taking-const-generic-array.stderr
new file mode 100644 (file)
index 0000000..3670412
--- /dev/null
@@ -0,0 +1,6 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/fn-taking-const-generic-array.rs:3:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
diff --git a/src/test/ui/const-generics/issue-60818-struct-constructors.rs b/src/test/ui/const-generics/issue-60818-struct-constructors.rs
new file mode 100644 (file)
index 0000000..0b4aeae
--- /dev/null
@@ -0,0 +1,10 @@
+// compile-pass
+
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+struct Generic<const V: usize>;
+
+fn main() {
+    let _ = Generic::<0>;
+}
diff --git a/src/test/ui/const-generics/issue-60818-struct-constructors.stderr b/src/test/ui/const-generics/issue-60818-struct-constructors.stderr
new file mode 100644 (file)
index 0000000..4b8f50b
--- /dev/null
@@ -0,0 +1,6 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/issue-60818-struct-constructors.rs:3:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
diff --git a/src/test/ui/const-generics/uninferred-consts-during-codegen-1.rs b/src/test/ui/const-generics/uninferred-consts-during-codegen-1.rs
new file mode 100644 (file)
index 0000000..1e064fb
--- /dev/null
@@ -0,0 +1,18 @@
+// run-pass
+
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+use std::fmt;
+
+struct Array<T, const N: usize>([T; N]);
+
+impl<T: fmt::Debug, const N: usize> fmt::Debug for Array<T, {N}> {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        f.debug_list().entries(self.0.iter()).finish()
+    }
+}
+
+fn main() {
+    assert_eq!(format!("{:?}", Array([1, 2, 3])), "[1, 2, 3]");
+}
diff --git a/src/test/ui/const-generics/uninferred-consts-during-codegen-1.stderr b/src/test/ui/const-generics/uninferred-consts-during-codegen-1.stderr
new file mode 100644 (file)
index 0000000..eb2e446
--- /dev/null
@@ -0,0 +1,6 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/uninferred-consts-during-codegen-1.rs:3:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
diff --git a/src/test/ui/const-generics/uninferred-consts-during-codegen-2.rs b/src/test/ui/const-generics/uninferred-consts-during-codegen-2.rs
new file mode 100644 (file)
index 0000000..0cf5059
--- /dev/null
@@ -0,0 +1,18 @@
+// run-pass
+
+#![feature(const_generics)]
+//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
+
+use std::fmt;
+
+struct Array<T>(T);
+
+impl<T: fmt::Debug, const N: usize> fmt::Debug for Array<[T; N]> {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        f.debug_list().entries((&self.0 as &[T]).iter()).finish()
+    }
+}
+
+fn main() {
+    assert_eq!(format!("{:?}", Array([1, 2, 3])), "[1, 2, 3]");
+}
diff --git a/src/test/ui/const-generics/uninferred-consts-during-codegen-2.stderr b/src/test/ui/const-generics/uninferred-consts-during-codegen-2.stderr
new file mode 100644 (file)
index 0000000..eaa20bb
--- /dev/null
@@ -0,0 +1,6 @@
+warning: the feature `const_generics` is incomplete and may cause the compiler to crash
+  --> $DIR/uninferred-consts-during-codegen-2.rs:3:12
+   |
+LL | #![feature(const_generics)]
+   |            ^^^^^^^^^^^^^^
+
index 2f9b30b51d10abd31c2a8e738edeecf27cf8ac77..2f5661e32a90e37dde994653e5b6472649e4e423 100644 (file)
@@ -4,8 +4,12 @@
 const IDX: usize = 3;
 const VAL: i32 = ARR[IDX];
 const BONG: [i32; (ARR[0] - 41) as usize] = [5];
-const BLUB: [i32; (ARR[0] - 40) as usize] = [5]; //~ ERROR: mismatched types
-const BOO: [i32; (ARR[0] - 41) as usize] = [5, 99]; //~ ERROR: mismatched types
+const BLUB: [i32; (ARR[0] - 40) as usize] = [5];
+//~^ ERROR: mismatched types
+//~| expected an array with a fixed size of 2 elements, found one with 1 element
+const BOO: [i32; (ARR[0] - 41) as usize] = [5, 99];
+//~^ ERROR: mismatched types
+//~| expected an array with a fixed size of 1 element, found one with 2 elements
 
 fn main() {
     let _ = VAL;
index 00286b0b0e0f8c439659539fbce03a569d245a0b..987e7ddf4d91e66ce42ee0236319ac6b1fa8fd2b 100644 (file)
@@ -2,16 +2,16 @@ error[E0308]: mismatched types
   --> $DIR/const-array-oob-arith.rs:7:45
    |
 LL | const BLUB: [i32; (ARR[0] - 40) as usize] = [5];
-   |                                             ^^^ expected an array with a fixed size of 2 elements, found one with 1 elements
+   |                                             ^^^ expected an array with a fixed size of 2 elements, found one with 1 element
    |
    = note: expected type `[i32; 2]`
               found type `[i32; 1]`
 
 error[E0308]: mismatched types
-  --> $DIR/const-array-oob-arith.rs:8:44
+  --> $DIR/const-array-oob-arith.rs:10:44
    |
 LL | const BOO: [i32; (ARR[0] - 41) as usize] = [5, 99];
-   |                                            ^^^^^^^ expected an array with a fixed size of 1 elements, found one with 2 elements
+   |                                            ^^^^^^^ expected an array with a fixed size of 1 element, found one with 2 elements
    |
    = note: expected type `[i32; 1]`
               found type `[i32; 2]`
index e4f7fb155ab90d26c45b7e627ab7fca7dbbfddab..4726f9dde3a845498827cb72ab178c02d4794991 100644 (file)
@@ -41,7 +41,7 @@ struct VTable {
     bar: for<'a> fn(&'a Foo) -> u32,
 }
 
-const FOO: &Bar = &Foo { foo: 128, bar: false };
+const FOO: &dyn Bar = &Foo { foo: 128, bar: false };
 const G: Fat = unsafe { Transmute { t: FOO }.u };
 const F: Option<for<'a> fn(&'a mut Foo)> = G.1.drop;
 const H: for<'a> fn(&'a Foo) -> u32 = G.1.bar;
index 89834aa94fc516ce6521d29fb2830562fff94634..e8ac5a90880cebc08e46d62822701b6a21be1ef1 100644 (file)
@@ -1,6 +1,6 @@
 // compile-pass
 
-pub const STATIC_TRAIT: &Test = &();
+pub const STATIC_TRAIT: &dyn Test = &();
 
 fn main() {}
 
index 9b7bca6b72d61eeb6a9273312a649527c0aa3c41..0a427cd8857e840c3edbc52b2b81e7adda4b49df 100644 (file)
@@ -3,7 +3,7 @@
 
 use std::mem;
 
-const BAD_UPVAR: &FnOnce() = &{ //~ ERROR it is undefined behavior to use this value
+const BAD_UPVAR: &dyn FnOnce() = &{ //~ ERROR it is undefined behavior to use this value
     let bad_ref: &'static u16 = unsafe { mem::transmute(0usize) };
     let another_var = 13;
     move || { let _ = bad_ref; let _ = another_var; }
index 21d2847db1e8aa9566583e19a2097fc9aa18a97b..f8273ba902a88ee5a92b2c06d41ef4bcf2e62b23 100644 (file)
@@ -1,7 +1,7 @@
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/ub-upvars.rs:6:1
    |
-LL | / const BAD_UPVAR: &FnOnce() = &{
+LL | / const BAD_UPVAR: &dyn FnOnce() = &{
 LL | |     let bad_ref: &'static u16 = unsafe { mem::transmute(0usize) };
 LL | |     let another_var = 13;
 LL | |     move || { let _ = bad_ref; let _ = another_var; }
index 13489c50a1223140a5b4de258680f1ffd85c1055..d5405f3441fec2915b06e5f2df06c9af07e9d425 100644 (file)
@@ -59,7 +59,7 @@ union DynTransmute {
     repr: DynRepr,
     repr2: DynRepr2,
     bad: BadDynRepr,
-    rust: &'static Trait,
+    rust: &'static dyn Trait,
 }
 
 trait Trait {}
@@ -94,17 +94,17 @@ impl Trait for bool {}
 //~^ ERROR it is undefined behavior to use this value
 
 // bad trait object
-const D: &Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
+const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
 //~^ ERROR it is undefined behavior to use this value
 // bad trait object
-const E: &Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
+const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
 //~^ ERROR it is undefined behavior to use this value
 // bad trait object
-const F: &Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
+const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
 //~^ ERROR it is undefined behavior to use this value
 
 // bad data *inside* the trait object
-const G: &Trait = &unsafe { BoolTransmute { val: 3 }.bl };
+const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
 //~^ ERROR it is undefined behavior to use this value
 
 // bad data *inside* the slice
index 761a5fc4445edba3931e507a09e556b74d483814..5048a97d19514ee28098ec9d6da729edbba75fbf 100644 (file)
@@ -41,32 +41,32 @@ LL | const C3: &[u8] = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, l
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/union-ub-fat-ptr.rs:97:1
    |
-LL | const D: &Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered invalid drop fn in vtable
+LL | const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered invalid drop fn in vtable
    |
    = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
 
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/union-ub-fat-ptr.rs:100:1
    |
-LL | const E: &Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered invalid drop fn in vtable
+LL | const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered invalid drop fn in vtable
    |
    = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
 
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/union-ub-fat-ptr.rs:103:1
    |
-LL | const F: &Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-pointer vtable in fat pointer
+LL | const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-pointer vtable in fat pointer
    |
    = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
 
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/union-ub-fat-ptr.rs:107:1
    |
-LL | const G: &Trait = &unsafe { BoolTransmute { val: 3 }.bl };
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.<dyn-downcast>, but expected something less or equal to 1
+LL | const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.<dyn-downcast>, but expected something less or equal to 1
    |
    = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
 
index 3762f5e3d6ad8b27cd2601f0ce2ca95475ea50bd..113ec29239616c4a4fd470ee2d70d5dc9741f797 100644 (file)
@@ -5,7 +5,7 @@ LL |     bytes: [u8; std::mem::size_of::<Foo>()]
    |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: ...which requires const-evaluating `Foo::bytes::{{constant}}#0`...
-  --> $SRC_DIR/libcore/mem.rs:LL:COL
+  --> $SRC_DIR/libcore/mem/mod.rs:LL:COL
    |
 LL |     intrinsics::size_of::<T>()
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
index e20ded68ceb96c1bfe8cad1044f74f9d373aecfa..319b8ef97deaeeb71b17d5b9b5c5045b02e06613 100644 (file)
@@ -1,12 +1,12 @@
 use std::fmt::Debug;
 
-const CONST_0: Debug+Sync = *(&0 as &(Debug+Sync));
+const CONST_0: dyn Debug + Sync = *(&0 as &(dyn Debug + Sync));
 //~^ ERROR the size for values of type
 
 const CONST_FOO: str = *"foo";
 //~^ ERROR the size for values of type
 
-static STATIC_1: Debug+Sync = *(&1 as &(Debug+Sync));
+static STATIC_1: dyn Debug + Sync = *(&1 as &(dyn Debug + Sync));
 //~^ ERROR the size for values of type
 
 static STATIC_BAR: str = *"bar";
index 0f996fcd9434090fca87e8876717f1595ce7ccf9..beeea87bfb1d33f0d4c556056f044cf3dc716565 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the size for values of type `(dyn std::fmt::Debug + std::marker::Sync + 'static)` cannot be known at compilation time
   --> $DIR/const-unsized.rs:3:16
    |
-LL | const CONST_0: Debug+Sync = *(&0 as &(Debug+Sync));
-   |                ^^^^^^^^^^ doesn't have a size known at compile-time
+LL | const CONST_0: dyn Debug + Sync = *(&0 as &(dyn Debug + Sync));
+   |                ^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::fmt::Debug + std::marker::Sync + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -19,8 +19,8 @@ LL | const CONST_FOO: str = *"foo";
 error[E0277]: the size for values of type `(dyn std::fmt::Debug + std::marker::Sync + 'static)` cannot be known at compilation time
   --> $DIR/const-unsized.rs:9:18
    |
-LL | static STATIC_1: Debug+Sync = *(&1 as &(Debug+Sync));
-   |                  ^^^^^^^^^^ doesn't have a size known at compile-time
+LL | static STATIC_1: dyn Debug + Sync = *(&1 as &(dyn Debug + Sync));
+   |                  ^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::fmt::Debug + std::marker::Sync + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index 8d962384a121ad00e37dc34be1e758e20bbf4e85..7a10c469c51a0c2dbc985eea14af9c65638ee19d 100644 (file)
@@ -298,8 +298,8 @@ LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
 error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
   --> $DIR/min_const_fn.rs:144:41
    |
-LL | const fn really_no_traits_i_mean_it() { (&() as &std::fmt::Debug, ()).1 }
-   |                                         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
+   |                                         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see issue https://github.com/rust-lang/rust/issues/57563
    = help: add #![feature(const_fn)] to the crate attributes to enable
index 783c79005ae37a35f809cb886c632d6549abc3bc..96b6057c8fd2d571f3e7e144961a9c503774e866 100644 (file)
@@ -141,7 +141,7 @@ const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
 
 const fn no_unsafe() { unsafe {} }
 
-const fn really_no_traits_i_mean_it() { (&() as &std::fmt::Debug, ()).1 }
+const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
 //~^ ERROR trait bounds other than `Sized`
 
 const fn no_fn_ptrs(_x: fn()) {}
index 93b57bc24a82f0cbba7ed9527b7c44a4771860d4..e388b443d23445d95f3e40a1de8278649d894c64 100644 (file)
@@ -302,8 +302,8 @@ LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
 error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
   --> $DIR/min_const_fn.rs:144:41
    |
-LL | const fn really_no_traits_i_mean_it() { (&() as &std::fmt::Debug, ()).1 }
-   |                                         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
+   |                                         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see issue https://github.com/rust-lang/rust/issues/57563
    = help: add #![feature(const_fn)] to the crate attributes to enable
index d8d7537f24a61b52a52d2d0dc13bc4b787540ed2..274cdad75ec2adbca8a4aecb816ae68b6c1f2402 100644 (file)
@@ -6,8 +6,8 @@ trait Trait { fn foo(&self) {} }
 impl Trait for Foo {}
 
 pub fn main() {
-    let x: Box<Trait> = Box::new(Foo);
-    let _y: &Trait = x; //~ ERROR E0308
-                        //~| expected type `&dyn Trait`
-                        //~| found type `std::boxed::Box<dyn Trait>`
+    let x: Box<dyn Trait> = Box::new(Foo);
+    let _y: &dyn Trait = x; //~ ERROR E0308
+                            //~| expected type `&dyn Trait`
+                            //~| found type `std::boxed::Box<dyn Trait>`
 }
index b35f59658c042ce13595a8aea498a794fde698db..ada1c0204eb0151814c67f7a08a4fd6d2c089453 100644 (file)
@@ -1,11 +1,11 @@
 error[E0308]: mismatched types
-  --> $DIR/cross-borrow-trait.rs:10:22
+  --> $DIR/cross-borrow-trait.rs:10:26
    |
-LL |     let _y: &Trait = x;
-   |                      ^
-   |                      |
-   |                      expected &dyn Trait, found struct `std::boxed::Box`
-   |                      help: consider borrowing here: `&x`
+LL |     let _y: &dyn Trait = x;
+   |                          ^
+   |                          |
+   |                          expected &dyn Trait, found struct `std::boxed::Box`
+   |                          help: consider borrowing here: `&x`
    |
    = note: expected type `&dyn Trait`
               found type `std::boxed::Box<dyn Trait>`
diff --git a/src/test/ui/custom-derive/auxiliary/plugin.rs b/src/test/ui/custom-derive/auxiliary/plugin.rs
deleted file mode 100644 (file)
index 5e500de..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_derive(Foo)]
-pub fn derive_foo(input: TokenStream) -> TokenStream {
-    input
-}
-
-#[proc_macro_derive(Bar)]
-pub fn derive_bar(input: TokenStream) -> TokenStream {
-    panic!("lolnope");
-}
-
-#[proc_macro_derive(WithHelper, attributes(helper))]
-pub fn with_helper(input: TokenStream) -> TokenStream {
-    TokenStream::new()
-}
-
-#[proc_macro_attribute]
-pub fn helper(_: TokenStream, input: TokenStream) -> TokenStream {
-    input
-}
diff --git a/src/test/ui/custom-derive/derive-in-mod.rs b/src/test/ui/custom-derive/derive-in-mod.rs
deleted file mode 100644 (file)
index 8478ff1..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// compile-pass
-// aux-build:plugin.rs
-
-extern crate plugin;
-
-mod inner {
-    use plugin::WithHelper;
-
-    #[derive(WithHelper)]
-    struct S;
-}
-
-fn main() {}
diff --git a/src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.rs b/src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.rs
deleted file mode 100644 (file)
index ba072ba..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-// aux-build:plugin.rs
-
-#[macro_use(WithHelper)]
-extern crate plugin;
-
-use plugin::helper;
-
-#[derive(WithHelper)]
-#[helper] //~ ERROR `helper` is ambiguous
-struct S;
-
-fn main() {}
diff --git a/src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.stderr b/src/test/ui/custom-derive/helper-attr-blocked-by-import-ambig.stderr
deleted file mode 100644 (file)
index e83c291..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-error[E0659]: `helper` is ambiguous (derive helper attribute vs any other name)
-  --> $DIR/helper-attr-blocked-by-import-ambig.rs:9:3
-   |
-LL | #[helper]
-   |   ^^^^^^ ambiguous name
-   |
-note: `helper` could refer to the derive helper attribute defined here
-  --> $DIR/helper-attr-blocked-by-import-ambig.rs:8:10
-   |
-LL | #[derive(WithHelper)]
-   |          ^^^^^^^^^^
-note: `helper` could also refer to the attribute macro imported here
-  --> $DIR/helper-attr-blocked-by-import-ambig.rs:6:5
-   |
-LL | use plugin::helper;
-   |     ^^^^^^^^^^^^^^
-   = help: use `crate::helper` to refer to this attribute macro unambiguously
-
-error: aborting due to previous error
-
-For more information about this error, try `rustc --explain E0659`.
diff --git a/src/test/ui/custom-derive/helper-attr-blocked-by-import.rs b/src/test/ui/custom-derive/helper-attr-blocked-by-import.rs
deleted file mode 100644 (file)
index abbf014..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-// compile-pass
-// aux-build:plugin.rs
-
-#[macro_use(WithHelper)]
-extern crate plugin;
-
-use self::one::*;
-use self::two::*;
-
-mod helper {}
-
-mod one {
-    use helper;
-
-    #[derive(WithHelper)]
-    #[helper]
-    struct One;
-}
-
-mod two {
-    use helper;
-
-    #[derive(WithHelper)]
-    #[helper]
-    struct Two;
-}
-
-fn main() {}
diff --git a/src/test/ui/custom-derive/issue-36935.rs b/src/test/ui/custom-derive/issue-36935.rs
deleted file mode 100644 (file)
index 7a5d19f..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-// aux-build:plugin.rs
-
-
-#[macro_use] extern crate plugin;
-
-#[derive(Foo, Bar)] //~ ERROR proc-macro derive panicked
-struct Baz {
-    a: i32,
-    b: i32,
-}
-
-fn main() {}
diff --git a/src/test/ui/custom-derive/issue-36935.stderr b/src/test/ui/custom-derive/issue-36935.stderr
deleted file mode 100644 (file)
index 2875bc5..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-error: proc-macro derive panicked
-  --> $DIR/issue-36935.rs:6:15
-   |
-LL | #[derive(Foo, Bar)]
-   |               ^^^
-   |
-   = help: message: lolnope
-
-error: aborting due to previous error
-
index a8aac6ec1427a1853518c3a2c5435fd03cce5e7b..aee0040ef4de413f98c51077c904940351cc02b4 100644 (file)
@@ -5,7 +5,7 @@
 #![test_runner(crate::foo_runner)]
 
 #[cfg(test)]
-fn foo_runner(ts: &[&Fn(usize)->()]) {
+fn foo_runner(ts: &[&dyn Fn(usize)->()]) {
     for (i, t) in ts.iter().enumerate() {
         t(i);
     }
index d658753eb242bc80500ef73819f13f91dbb3d754..6175b7df1107ad78029a5ffc4f4231a2d105a05b 100644 (file)
@@ -1,7 +1,7 @@
 // Test a cycle where a type parameter on a trait has a default that
 // again references the trait.
 
-trait Foo<X = Box<Foo>> {
+trait Foo<X = Box<dyn Foo>> {
     //~^ ERROR cycle detected
 }
 
index aa45462a52e41e702cd06b07e042e81355297a46..e89d25742a0acfd589c0dd0a8e8e09d3521809e1 100644 (file)
@@ -1,15 +1,15 @@
 error[E0391]: cycle detected when processing `Foo::X`
-  --> $DIR/cycle-trait-default-type-trait.rs:4:19
+  --> $DIR/cycle-trait-default-type-trait.rs:4:23
    |
-LL | trait Foo<X = Box<Foo>> {
-   |                   ^^^
+LL | trait Foo<X = Box<dyn Foo>> {
+   |                       ^^^
    |
    = note: ...which again requires processing `Foo::X`, completing the cycle
 note: cycle used when collecting item types in top-level module
   --> $DIR/cycle-trait-default-type-trait.rs:4:1
    |
-LL | trait Foo<X = Box<Foo>> {
-   | ^^^^^^^^^^^^^^^^^^^^^^^
+LL | trait Foo<X = Box<dyn Foo>> {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index 66be493cb1f9764c72bcd02dca748a35c1b45dd3..71cf37ca84951a22ddff2f5aace00d3e2283dad9 100644 (file)
@@ -18,27 +18,28 @@ fn main() {
     // if n > m, it's a type mismatch error.
 
     // n < m
-    let &x = &(&1isize as &T);
-    let &x = &&(&1isize as &T);
-    let &&x = &&(&1isize as &T);
+    let &x = &(&1isize as &dyn T);
+    let &x = &&(&1isize as &dyn T);
+    let &&x = &&(&1isize as &dyn T);
 
     // n == m
-    let &x = &1isize as &T;      //~ ERROR type `&dyn T` cannot be dereferenced
-    let &&x = &(&1isize as &T);  //~ ERROR type `&dyn T` cannot be dereferenced
-    let box x = box 1isize as Box<T>; //~ ERROR type `std::boxed::Box<dyn T>` cannot be dereferenced
+    let &x = &1isize as &dyn T;      //~ ERROR type `&dyn T` cannot be dereferenced
+    let &&x = &(&1isize as &dyn T);  //~ ERROR type `&dyn T` cannot be dereferenced
+    let box x = box 1isize as Box<dyn T>;
+    //~^ ERROR type `std::boxed::Box<dyn T>` cannot be dereferenced
 
     // n > m
-    let &&x = &1isize as &T;
+    let &&x = &1isize as &dyn T;
     //~^ ERROR mismatched types
     //~| expected type `dyn T`
     //~| found type `&_`
     //~| expected trait T, found reference
-    let &&&x = &(&1isize as &T);
+    let &&&x = &(&1isize as &dyn T);
     //~^ ERROR mismatched types
     //~| expected type `dyn T`
     //~| found type `&_`
     //~| expected trait T, found reference
-    let box box x = box 1isize as Box<T>;
+    let box box x = box 1isize as Box<dyn T>;
     //~^ ERROR mismatched types
     //~| expected type `dyn T`
     //~| found type `std::boxed::Box<_>`
index bc3013b78b38c8a0886f4df0834fdeb89c49bad9..d3ad21eb24ffb39e5c6251e3dbfd2cabe689ea66 100644 (file)
@@ -1,25 +1,25 @@
 error[E0033]: type `&dyn T` cannot be dereferenced
   --> $DIR/destructure-trait-ref.rs:26:9
    |
-LL |     let &x = &1isize as &T;
+LL |     let &x = &1isize as &dyn T;
    |         ^^ type `&dyn T` cannot be dereferenced
 
 error[E0033]: type `&dyn T` cannot be dereferenced
   --> $DIR/destructure-trait-ref.rs:27:10
    |
-LL |     let &&x = &(&1isize as &T);
+LL |     let &&x = &(&1isize as &dyn T);
    |          ^^ type `&dyn T` cannot be dereferenced
 
 error[E0033]: type `std::boxed::Box<dyn T>` cannot be dereferenced
   --> $DIR/destructure-trait-ref.rs:28:9
    |
-LL |     let box x = box 1isize as Box<T>;
+LL |     let box x = box 1isize as Box<dyn T>;
    |         ^^^^^ type `std::boxed::Box<dyn T>` cannot be dereferenced
 
 error[E0308]: mismatched types
-  --> $DIR/destructure-trait-ref.rs:31:10
+  --> $DIR/destructure-trait-ref.rs:32:10
    |
-LL |     let &&x = &1isize as &T;
+LL |     let &&x = &1isize as &dyn T;
    |          ^^
    |          |
    |          expected trait T, found reference
@@ -29,9 +29,9 @@ LL |     let &&x = &1isize as &T;
               found type `&_`
 
 error[E0308]: mismatched types
-  --> $DIR/destructure-trait-ref.rs:36:11
+  --> $DIR/destructure-trait-ref.rs:37:11
    |
-LL |     let &&&x = &(&1isize as &T);
+LL |     let &&&x = &(&1isize as &dyn T);
    |           ^^
    |           |
    |           expected trait T, found reference
@@ -41,9 +41,9 @@ LL |     let &&&x = &(&1isize as &T);
               found type `&_`
 
 error[E0308]: mismatched types
-  --> $DIR/destructure-trait-ref.rs:41:13
+  --> $DIR/destructure-trait-ref.rs:42:13
    |
-LL |     let box box x = box 1isize as Box<T>;
+LL |     let box box x = box 1isize as Box<dyn T>;
    |             ^^^^^ expected trait T, found struct `std::boxed::Box`
    |
    = note: expected type `dyn T`
index aad95dc2c20e075bb07d0d898b5f3c2576bdae19..095df640c38f296e3e809e0d7d431a9353385a0f 100644 (file)
@@ -1,3 +1,5 @@
+#![allow(bare_trait_objects)]
+
 trait Foo {}
 
 struct Bar<'a> {
index 44e6ddd0eac8feb0a496ce2e743ad8b17d516665..58ac6e90823f6d24ed2a8a0c12a8535cda161237 100644 (file)
@@ -1,23 +1,23 @@
 error[E0178]: expected a path on the left-hand side of `+`, not `&'a Foo`
-  --> $DIR/E0178.rs:4:8
+  --> $DIR/E0178.rs:6:8
    |
 LL |     w: &'a Foo + Copy,
    |        ^^^^^^^^^^^^^^ help: try adding parentheses: `&'a (Foo + Copy)`
 
 error[E0178]: expected a path on the left-hand side of `+`, not `&'a Foo`
-  --> $DIR/E0178.rs:5:8
+  --> $DIR/E0178.rs:7:8
    |
 LL |     x: &'a Foo + 'a,
    |        ^^^^^^^^^^^^ help: try adding parentheses: `&'a (Foo + 'a)`
 
 error[E0178]: expected a path on the left-hand side of `+`, not `&'a mut Foo`
-  --> $DIR/E0178.rs:6:8
+  --> $DIR/E0178.rs:8:8
    |
 LL |     y: &'a mut Foo + 'a,
    |        ^^^^^^^^^^^^^^^^ help: try adding parentheses: `&'a mut (Foo + 'a)`
 
 error[E0178]: expected a path on the left-hand side of `+`, not `fn() -> Foo`
-  --> $DIR/E0178.rs:7:8
+  --> $DIR/E0178.rs:9:8
    |
 LL |     z: fn() -> Foo + 'a,
    |        ^^^^^^^^^^^^^^^^ perhaps you forgot parentheses?
index 85e36f887be087d94c293a9f6831617fe4d672b6..fccfb7911cecf5636db62ca774f0ba902ef7d3fc 100644 (file)
@@ -24,7 +24,7 @@
 
 // Qualified paths cannot appear in bounds, so the recovery
 // should apply to the whole sum and not `(Send)`.
-type G = 'static + (Send)::AssocTy;
+type G = dyn 'static + (Send)::AssocTy;
 //~^ ERROR missing angle brackets in associated item path
 //~| ERROR ambiguous associated type
 
index 8c694f9d42b3e49239d2bd1b56fdf3adc6a17f68..0ae64edcc0546584e6541c4098bf50b547f5daf9 100644 (file)
@@ -37,8 +37,8 @@ LL | type F = &'static (u8)::AssocTy;
 error: missing angle brackets in associated item path
   --> $DIR/bad-assoc-ty.rs:27:10
    |
-LL | type G = 'static + (Send)::AssocTy;
-   |          ^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `<'static + (Send)>::AssocTy`
+LL | type G = dyn 'static + (Send)::AssocTy;
+   |          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `<dyn 'static + (Send)>::AssocTy`
 
 error: missing angle brackets in associated item path
   --> $DIR/bad-assoc-ty.rs:44:10
@@ -94,8 +94,8 @@ LL | type F = &'static (u8)::AssocTy;
 error[E0223]: ambiguous associated type
   --> $DIR/bad-assoc-ty.rs:27:10
    |
-LL | type G = 'static + (Send)::AssocTy;
-   |          ^^^^^^^^^^^^^^^^^^^^^^^^^ help: use fully-qualified syntax: `<(dyn std::marker::Send + 'static) as Trait>::AssocTy`
+LL | type G = dyn 'static + (Send)::AssocTy;
+   |          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use fully-qualified syntax: `<(dyn std::marker::Send + 'static) as Trait>::AssocTy`
 
 error[E0223]: ambiguous associated type
   --> $DIR/bad-assoc-ty.rs:33:10
index 75ea02b6a9d4a24a6fcadecf59c0a4d94a977c4e..a1184f757e2abe82d0bd514c80d8c5335b155d6e 100644 (file)
@@ -1,4 +1,4 @@
-impl X { //~ ERROR cannot be made into an object
+impl dyn X { //~ ERROR cannot be made into an object
 //~^ ERROR missing
     Y
 }
index f6f7fe5fa38c3f8fe6693f67acee1b8abee7d73d..87e48cd1e1cd9dddf3a8ff1db19157749ec30b44 100644 (file)
@@ -1,8 +1,8 @@
 error: missing `fn`, `type`, or `const` for impl-item declaration
-  --> $DIR/issue-40006.rs:1:9
+  --> $DIR/issue-40006.rs:1:13
    |
-LL |   impl X {
-   |  _________^
+LL |   impl dyn X {
+   |  _____________^
 LL | |
 LL | |     Y
    | |____^ missing `fn`, `type`, or `const`
@@ -59,8 +59,8 @@ LL |     pub hello_method(&self) {
 error[E0038]: the trait `X` cannot be made into an object
   --> $DIR/issue-40006.rs:1:6
    |
-LL | impl X {
-   |      ^ the trait `X` cannot be made into an object
+LL | impl dyn X {
+   |      ^^^^^ the trait `X` cannot be made into an object
    |
    = note: method `xxx` has no receiver
 
index a05227416cfd7abd4374475f79f703ac0f3113e4..c9a097d3610a12eb0f001c7fec3d0363c3bb7336 100644 (file)
@@ -1,3 +1,5 @@
+#![allow(bare_trait_objects)]
+
 fn main() {
     let _: &Copy + 'static; //~ ERROR expected a path
     //~^ ERROR cannot be made into an object
index de1efcd7e0f7d350fd657e99998075b24b4102d7..8c6c33b11865b38ab114f727ba5e18dc971e3478 100644 (file)
@@ -1,17 +1,17 @@
 error[E0178]: expected a path on the left-hand side of `+`, not `&Copy`
-  --> $DIR/trait-object-reference-without-parens-suggestion.rs:2:12
+  --> $DIR/trait-object-reference-without-parens-suggestion.rs:4:12
    |
 LL |     let _: &Copy + 'static;
    |            ^^^^^^^^^^^^^^^ help: try adding parentheses: `&(Copy + 'static)`
 
 error[E0178]: expected a path on the left-hand side of `+`, not `&'static Copy`
-  --> $DIR/trait-object-reference-without-parens-suggestion.rs:4:12
+  --> $DIR/trait-object-reference-without-parens-suggestion.rs:6:12
    |
 LL |     let _: &'static Copy + 'static;
    |            ^^^^^^^^^^^^^^^^^^^^^^^ help: try adding parentheses: `&'static (Copy + 'static)`
 
 error[E0038]: the trait `std::marker::Copy` cannot be made into an object
-  --> $DIR/trait-object-reference-without-parens-suggestion.rs:2:12
+  --> $DIR/trait-object-reference-without-parens-suggestion.rs:4:12
    |
 LL |     let _: &Copy + 'static;
    |            ^^^^^ the trait `std::marker::Copy` cannot be made into an object
index 128bbb04ee0eaa375752228577c75872a009679d..bea77dc9f5c4fdabaea3d8bd818502345a4d5e48 100644 (file)
@@ -63,14 +63,14 @@ fn drop(&mut self) {
 }
 
 trait Obj<'a> : HasId {
-    fn set0(&self, b: &'a Box<Obj<'a>>);
-    fn set1(&self, b: &'a Box<Obj<'a>>);
+    fn set0(&self, b: &'a Box<dyn Obj<'a>>);
+    fn set1(&self, b: &'a Box<dyn Obj<'a>>);
 }
 
 struct O<'a> {
     id: Id,
-    obj0: CheckId<Cell<Option<&'a Box<Obj<'a>>>>>,
-    obj1: CheckId<Cell<Option<&'a Box<Obj<'a>>>>>,
+    obj0: CheckId<Cell<Option<&'a Box<dyn Obj<'a>>>>>,
+    obj1: CheckId<Cell<Option<&'a Box<dyn Obj<'a>>>>>,
 }
 
 impl<'a> HasId for O<'a> {
@@ -87,7 +87,7 @@ fn new() -> Box<O<'a>> {
     }
 }
 
-impl<'a> HasId for Cell<Option<&'a Box<Obj<'a>>>> {
+impl<'a> HasId for Cell<Option<&'a Box<dyn Obj<'a>>>> {
     fn count(&self) -> usize {
         match self.get() {
             None => 1,
@@ -97,17 +97,17 @@ fn count(&self) -> usize {
 }
 
 impl<'a> Obj<'a> for O<'a> {
-    fn set0(&self, b: &'a Box<Obj<'a>>) {
+    fn set0(&self, b: &'a Box<dyn Obj<'a>>) {
         self.obj0.v.set(Some(b))
     }
-    fn set1(&self, b: &'a Box<Obj<'a>>) {
+    fn set1(&self, b: &'a Box<dyn Obj<'a>>) {
         self.obj1.v.set(Some(b))
     }
 }
 
 
 fn f() {
-    let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
+    let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
     o1.set0(&o2); //~ ERROR `o2` does not live long enough
     o1.set1(&o3); //~ ERROR `o3` does not live long enough
     o2.set0(&o2); //~ ERROR `o2` does not live long enough
index 8c669b597c3c059fe0890c55e4fb7482e6aee6e1..1e779208e58a5cdcc3221a9533500b32d040f86b 100644 (file)
@@ -1,8 +1,8 @@
 error[E0597]: `o2` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:111:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                                   -------- cast requires that `o2` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                               -------- cast requires that `o2` is borrowed for `'static`
 LL |     o1.set0(&o2);
    |             ^^^ borrowed value does not live long enough
 ...
@@ -12,8 +12,8 @@ LL | }
 error[E0597]: `o3` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:112:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                                             -------- cast requires that `o3` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                                         -------- cast requires that `o3` is borrowed for `'static`
 LL |     o1.set0(&o2);
 LL |     o1.set1(&o3);
    |             ^^^ borrowed value does not live long enough
@@ -24,8 +24,8 @@ LL | }
 error[E0597]: `o2` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:113:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                                   -------- cast requires that `o2` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                               -------- cast requires that `o2` is borrowed for `'static`
 ...
 LL |     o2.set0(&o2);
    |             ^^^ borrowed value does not live long enough
@@ -36,8 +36,8 @@ LL | }
 error[E0597]: `o3` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:114:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                                             -------- cast requires that `o3` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                                         -------- cast requires that `o3` is borrowed for `'static`
 ...
 LL |     o2.set1(&o3);
    |             ^^^ borrowed value does not live long enough
@@ -48,8 +48,8 @@ LL | }
 error[E0597]: `o1` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:115:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                         -------- cast requires that `o1` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                     -------- cast requires that `o1` is borrowed for `'static`
 ...
 LL |     o3.set0(&o1);
    |             ^^^ borrowed value does not live long enough
@@ -60,8 +60,8 @@ LL | }
 error[E0597]: `o2` does not live long enough
   --> $DIR/dropck_trait_cycle_checked.rs:116:13
    |
-LL |     let (o1, o2, o3): (Box<Obj>, Box<Obj>, Box<Obj>) = (O::new(), O::new(), O::new());
-   |                                                                   -------- cast requires that `o2` is borrowed for `'static`
+LL |     let (o1, o2, o3): (Box<dyn Obj>, Box<dyn Obj>, Box<dyn Obj>) = (O::new(), O::new(), O::new());
+   |                                                                               -------- cast requires that `o2` is borrowed for `'static`
 ...
 LL |     o3.set1(&o2);
    |             ^^^ borrowed value does not live long enough
index b4f72d034f5c512aef091f5acde6d371a48c8856..7ba31bf2e517283572626c1b92937f299f923f05 100644 (file)
@@ -30,8 +30,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::new(Bar1 {f: 36});
+    let f5: &mut Fat<dyn ToBar> = &mut Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
+    let z: Box<dyn ToBar> = Box::new(Bar1 {f: 36});
     f5.ptr = *z;
     //~^ ERROR the size for values of type
 
index 5124abc7d8222d9f362a012fa2f8318d622ecdf5..691909a2317431938b20ac248aa3bbb1f160994b 100644 (file)
@@ -28,8 +28,8 @@ fn to_val(&self) -> isize {
 
 pub fn main() {
     // Assignment.
-    let f5: &mut Fat<ToBar> = &mut (5, "some str", Bar1 {f :42});
-    let z: Box<ToBar> = Box::new(Bar1 {f: 36});
+    let f5: &mut Fat<dyn ToBar> = &mut (5, "some str", Bar1 {f :42});
+    let z: Box<dyn ToBar> = Box::new(Bar1 {f: 36});
     f5.2 = Bar1 {f: 36};
     //~^ ERROR mismatched types
     //~| expected type `dyn ToBar`
index 003c80b4dc423b1165f510b9e616a1f162aefe14..4f2648653f051703d5e560ae46349323059b9353 100644 (file)
@@ -30,8 +30,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::new(Bar1 {f: 36});
+    let f5: &mut Fat<dyn ToBar> = &mut Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
+    let z: Box<dyn ToBar> = Box::new(Bar1 {f: 36});
     f5.ptr = Bar1 {f: 36};
     //~^ ERROR mismatched types
     //~| expected type `dyn ToBar`
index 8ca34234c03177ffa05f0a01b2c8b8aa55eee24e..7ef237e39e36ed98a8fdb6ec0b844f85e4eb70a0 100644 (file)
@@ -19,7 +19,7 @@ pub fn main() {
     // With a trait.
     let f1 = Fat { ptr: Foo };
     let f2: &Fat<Foo> = &f1;
-    let f3: &Fat<Bar> = f2;
+    let f3: &Fat<dyn Bar> = f2;
     //~^ ERROR `Foo: Bar` is not satisfied
 
     // Tuple with a vec of isize.
@@ -31,6 +31,6 @@ pub fn main() {
     // Tuple with a trait.
     let f1 = (Foo,);
     let f2: &(Foo,) = &f1;
-    let f3: &(Bar,) = f2;
+    let f3: &(dyn Bar,) = f2;
     //~^ ERROR `Foo: Bar` is not satisfied
 }
index 3776ce71c611f82fce59b6cdde8511d43700701f..a48f37b20be975975a4348c406be68c705b2e1fe 100644 (file)
@@ -8,10 +8,10 @@ LL |     let f3: &Fat<[usize]> = f2;
               found type `&Fat<[isize; 3]>`
 
 error[E0277]: the trait bound `Foo: Bar` is not satisfied
-  --> $DIR/dst-bad-coerce1.rs:22:25
+  --> $DIR/dst-bad-coerce1.rs:22:29
    |
-LL |     let f3: &Fat<Bar> = f2;
-   |                         ^^ the trait `Bar` is not implemented for `Foo`
+LL |     let f3: &Fat<dyn Bar> = f2;
+   |                             ^^ the trait `Bar` is not implemented for `Foo`
    |
    = note: required for the cast to the object type `dyn Bar`
 
@@ -25,10 +25,10 @@ LL |     let f3: &([usize],) = f2;
               found type `&([isize; 3],)`
 
 error[E0277]: the trait bound `Foo: Bar` is not satisfied
-  --> $DIR/dst-bad-coerce1.rs:34:23
+  --> $DIR/dst-bad-coerce1.rs:34:27
    |
-LL |     let f3: &(Bar,) = f2;
-   |                       ^^ the trait `Bar` is not implemented for `Foo`
+LL |     let f3: &(dyn Bar,) = f2;
+   |                           ^^ the trait `Bar` is not implemented for `Foo`
    |
    = note: required for the cast to the object type `dyn Bar`
 
index 2bc7ecced0aabfa4abcd15a6ae1a41d9dc8790c4..e7ce20b8958793b7415d0987a49dd58c2f367dd0 100644 (file)
@@ -17,7 +17,7 @@ pub fn main() {
     // With a trait.
     let f1 = Fat { ptr: Foo };
     let f2: &Fat<Foo> = &f1;
-    let f3: &mut Fat<Bar> = f2; //~ ERROR mismatched types
+    let f3: &mut Fat<dyn Bar> = f2; //~ ERROR mismatched types
 
     // Tuple with a vec of ints.
     let f1 = ([1, 2, 3],);
@@ -27,5 +27,5 @@ pub fn main() {
     // Tuple with a trait.
     let f1 = (Foo,);
     let f2: &(Foo,) = &f1;
-    let f3: &mut (Bar,) = f2; //~ ERROR mismatched types
+    let f3: &mut (dyn Bar,) = f2; //~ ERROR mismatched types
 }
index cae4ec51c37cc7e5de1184b3a12a35064b242888..d1da9b6ca074910e7cc33f82aff034c0d6df9999 100644 (file)
@@ -8,10 +8,10 @@ LL |     let f3: &mut Fat<[isize]> = f2;
               found type `&Fat<[isize; 3]>`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coerce2.rs:20:29
+  --> $DIR/dst-bad-coerce2.rs:20:33
    |
-LL |     let f3: &mut Fat<Bar> = f2;
-   |                             ^^ types differ in mutability
+LL |     let f3: &mut Fat<dyn Bar> = f2;
+   |                                 ^^ types differ in mutability
    |
    = note: expected type `&mut Fat<dyn Bar>`
               found type `&Fat<Foo>`
@@ -26,10 +26,10 @@ LL |     let f3: &mut ([isize],) = f2;
               found type `&([isize; 3],)`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coerce2.rs:30:27
+  --> $DIR/dst-bad-coerce2.rs:30:31
    |
-LL |     let f3: &mut (Bar,) = f2;
-   |                           ^^ types differ in mutability
+LL |     let f3: &mut (dyn Bar,) = f2;
+   |                               ^^ types differ in mutability
    |
    = note: expected type `&mut (dyn Bar,)`
               found type `&(Foo,)`
index 58c988520eb0d1827afcdec25afee7d1b371a486..fd5ee3b57bb4201765e0cf00714baa18ea5a776a 100644 (file)
@@ -19,7 +19,7 @@ fn baz<'a>() {
     // With a trait.
     let f1 = Fat { ptr: Foo };
     let f2: &Fat<Foo> = &f1; //~ ERROR `f1` does not live long enough
-    let f3: &'a Fat<Bar> = f2;
+    let f3: &'a Fat<dyn Bar> = f2;
 
     // Tuple with a vec of ints.
     let f1 = ([1, 2, 3],);
@@ -29,7 +29,7 @@ fn baz<'a>() {
     // Tuple with a trait.
     let f1 = (Foo,);
     let f2: &(Foo,) = &f1; //~ ERROR `f1` does not live long enough
-    let f3: &'a (Bar,) = f2;
+    let f3: &'a (dyn Bar,) = f2;
 }
 
 pub fn main() {
index 289d451f02a7f9b8e322d4892565f0bc65b3e542..957e98bbeee96c7e6e38569fa3ad5577a735be4e 100644 (file)
@@ -20,8 +20,8 @@ LL | fn baz<'a>() {
 ...
 LL |     let f2: &Fat<Foo> = &f1;
    |                         ^^^ borrowed value does not live long enough
-LL |     let f3: &'a Fat<Bar> = f2;
-   |             ------------ type annotation requires that `f1` is borrowed for `'a`
+LL |     let f3: &'a Fat<dyn Bar> = f2;
+   |             ---------------- type annotation requires that `f1` is borrowed for `'a`
 ...
 LL | }
    | - `f1` dropped here while still borrowed
@@ -48,8 +48,8 @@ LL | fn baz<'a>() {
 ...
 LL |     let f2: &(Foo,) = &f1;
    |                       ^^^ borrowed value does not live long enough
-LL |     let f3: &'a (Bar,) = f2;
-   |             ---------- type annotation requires that `f1` is borrowed for `'a`
+LL |     let f3: &'a (dyn Bar,) = f2;
+   |             -------------- type annotation requires that `f1` is borrowed for `'a`
 LL | }
    | - `f1` dropped here while still borrowed
 
index 9aa697225d5b669029869906820a789ecc7821db..bffef378c921cde4041900d93fb577a9e944958e 100644 (file)
@@ -12,15 +12,15 @@ pub fn main() {
     // Test that we cannot convert from *-ptr to &S and &T
     let x: *const S = &S;
     let y: &S = x; //~ ERROR mismatched types
-    let y: &T = x; //~ ERROR mismatched types
+    let y: &dyn T = x; //~ ERROR mismatched types
 
     // Test that we cannot convert from *-ptr to &S and &T (mut version)
     let x: *mut S = &mut S;
     let y: &S = x; //~ ERROR mismatched types
-    let y: &T = x; //~ ERROR mismatched types
+    let y: &dyn T = x; //~ ERROR mismatched types
 
     // Test that we cannot convert an immutable ptr to a mutable one using *-ptrs
-    let x: &mut T = &S; //~ ERROR mismatched types
-    let x: *mut T = &S; //~ ERROR mismatched types
+    let x: &mut dyn T = &S; //~ ERROR mismatched types
+    let x: *mut dyn T = &S; //~ ERROR mismatched types
     let x: *mut S = &S; //~ ERROR mismatched types
 }
index 27016829a07f3253064a472ad153ab687c42108e..e4bc6ee0010a2acc5086dbfe80691326f9a5e037 100644 (file)
@@ -8,13 +8,13 @@ LL |     let y: &S = x;
               found type `*const S`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coercions.rs:15:17
+  --> $DIR/dst-bad-coercions.rs:15:21
    |
-LL |     let y: &T = x;
-   |                 ^
-   |                 |
-   |                 expected &dyn T, found *-ptr
-   |                 help: consider borrowing here: `&x`
+LL |     let y: &dyn T = x;
+   |                     ^
+   |                     |
+   |                     expected &dyn T, found *-ptr
+   |                     help: consider borrowing here: `&x`
    |
    = note: expected type `&dyn T`
               found type `*const S`
@@ -29,31 +29,31 @@ LL |     let y: &S = x;
               found type `*mut S`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coercions.rs:20:17
+  --> $DIR/dst-bad-coercions.rs:20:21
    |
-LL |     let y: &T = x;
-   |                 ^
-   |                 |
-   |                 expected &dyn T, found *-ptr
-   |                 help: consider borrowing here: `&x`
+LL |     let y: &dyn T = x;
+   |                     ^
+   |                     |
+   |                     expected &dyn T, found *-ptr
+   |                     help: consider borrowing here: `&x`
    |
    = note: expected type `&dyn T`
               found type `*mut S`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coercions.rs:23:21
+  --> $DIR/dst-bad-coercions.rs:23:25
    |
-LL |     let x: &mut T = &S;
-   |                     ^^ types differ in mutability
+LL |     let x: &mut dyn T = &S;
+   |                         ^^ types differ in mutability
    |
    = note: expected type `&mut dyn T`
               found type `&S`
 
 error[E0308]: mismatched types
-  --> $DIR/dst-bad-coercions.rs:24:21
+  --> $DIR/dst-bad-coercions.rs:24:25
    |
-LL |     let x: *mut T = &S;
-   |                     ^^ types differ in mutability
+LL |     let x: *mut dyn T = &S;
+   |                         ^^ types differ in mutability
    |
    = note: expected type `*mut dyn T`
               found type `&S`
index 71ff067bbd9dc0c6da51cf3d79b58047105b9bc8..fced3144eb85b5c9eb670f4c26cb4b5a8b41781c 100644 (file)
@@ -19,9 +19,9 @@ fn index(&self, _: usize) -> &str {
 struct T;
 
 impl Index<usize> for T {
-    type Output = Debug + 'static;
+    type Output = dyn Debug + 'static;
 
-    fn index<'a>(&'a self, idx: usize) -> &'a (Debug + 'static) {
+    fn index<'a>(&'a self, idx: usize) -> &'a (dyn Debug + 'static) {
         static x: usize = 42;
         &x
     }
index f4ee1783a2e3434410460ac3fa41d48fcd376690..3cd5b1ed6f46232475c7e7c42dc68c876db30f7a 100644 (file)
@@ -5,22 +5,22 @@ impl Foo for str {}
 impl Foo for [u8] {}
 
 fn test1<T: ?Sized + Foo>(t: &T) {
-    let u: &Foo = t;
+    let u: &dyn Foo = t;
     //~^ ERROR the size for values of type
 }
 
 fn test2<T: ?Sized + Foo>(t: &T) {
-    let v: &Foo = t as &Foo;
+    let v: &dyn Foo = t as &dyn Foo;
     //~^ ERROR the size for values of type
 }
 
 fn test3() {
-    let _: &[&Foo] = &["hi"];
+    let _: &[&dyn Foo] = &["hi"];
     //~^ ERROR the size for values of type
 }
 
 fn test4(x: &[u8]) {
-    let _: &Foo = x as &Foo;
+    let _: &dyn Foo = x as &dyn Foo;
     //~^ ERROR the size for values of type
 }
 
index 4851ca108285fa686cc8a10427d89299eba722d2..55ac625fc985b723c516371ed2aff701db759fc4 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the size for values of type `T` cannot be known at compilation time
-  --> $DIR/dst-object-from-unsized-type.rs:8:19
+  --> $DIR/dst-object-from-unsized-type.rs:8:23
    |
-LL |     let u: &Foo = t;
-   |                   ^ doesn't have a size known at compile-time
+LL |     let u: &dyn Foo = t;
+   |                       ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `T`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -10,10 +10,10 @@ LL |     let u: &Foo = t;
    = note: required for the cast to the object type `dyn Foo`
 
 error[E0277]: the size for values of type `T` cannot be known at compilation time
-  --> $DIR/dst-object-from-unsized-type.rs:13:19
+  --> $DIR/dst-object-from-unsized-type.rs:13:23
    |
-LL |     let v: &Foo = t as &Foo;
-   |                   ^ doesn't have a size known at compile-time
+LL |     let v: &dyn Foo = t as &dyn Foo;
+   |                       ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `T`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -21,20 +21,20 @@ LL |     let v: &Foo = t as &Foo;
    = note: required for the cast to the object type `dyn Foo`
 
 error[E0277]: the size for values of type `str` cannot be known at compilation time
-  --> $DIR/dst-object-from-unsized-type.rs:18:24
+  --> $DIR/dst-object-from-unsized-type.rs:18:28
    |
-LL |     let _: &[&Foo] = &["hi"];
-   |                        ^^^^ doesn't have a size known at compile-time
+LL |     let _: &[&dyn Foo] = &["hi"];
+   |                            ^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `str`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
    = note: required for the cast to the object type `dyn Foo`
 
 error[E0277]: the size for values of type `[u8]` cannot be known at compilation time
-  --> $DIR/dst-object-from-unsized-type.rs:23:19
+  --> $DIR/dst-object-from-unsized-type.rs:23:23
    |
-LL |     let _: &Foo = x as &Foo;
-   |                   ^ doesn't have a size known at compile-time
+LL |     let _: &dyn Foo = x as &dyn Foo;
+   |                       ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `[u8]`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index e68358fd978bfd3dece15b47ec78e6de61277c83..7d87b0a7756b123013bdc5fa9ad1c63b88d7d0f1 100644 (file)
@@ -13,6 +13,6 @@ fn new() -> Self {
 fn main() {
     let (a, b, c) = (A::new(), A::new()); // This tuple is 2 elements, should be three
     //~^ ERROR mismatched types
-    let ts: Vec<&T> = vec![&a, &b, &c];
+    let ts: Vec<&dyn T> = vec![&a, &b, &c];
     // There is no E0277 error above, as `a`, `b` and `c` are `TyErr`
 }
index 0f0b8d864dc43c15d9df99d69c13de35bc8ba402..6a27b07fa8b778737024895f6ffdf44f3dc1d800 100644 (file)
@@ -5,7 +5,7 @@ trait SomeTrait {
 }
 
 fn main() {
-    let trait_obj: &SomeTrait = SomeTrait;
+    let trait_obj: &dyn SomeTrait = SomeTrait;
     //~^ ERROR expected value, found trait `SomeTrait`
     //~| ERROR E0038
     //~| method `foo` has no receiver
index 1b78820cae07b7827640bebcb0e95f4ca4bc5fc6..fb630de7fc14776cf3f8ad0c68bbf5cd537b7417 100644 (file)
@@ -1,14 +1,14 @@
 error[E0423]: expected value, found trait `SomeTrait`
-  --> $DIR/E0033-teach.rs:8:33
+  --> $DIR/E0033-teach.rs:8:37
    |
-LL |     let trait_obj: &SomeTrait = SomeTrait;
-   |                                 ^^^^^^^^^ not a value
+LL |     let trait_obj: &dyn SomeTrait = SomeTrait;
+   |                                     ^^^^^^^^^ not a value
 
 error[E0038]: the trait `SomeTrait` cannot be made into an object
   --> $DIR/E0033-teach.rs:8:20
    |
-LL |     let trait_obj: &SomeTrait = SomeTrait;
-   |                    ^^^^^^^^^^ the trait `SomeTrait` cannot be made into an object
+LL |     let trait_obj: &dyn SomeTrait = SomeTrait;
+   |                    ^^^^^^^^^^^^^^ the trait `SomeTrait` cannot be made into an object
    |
    = note: method `foo` has no receiver
 
index 5a4f3cbce60e48a2524d051cda90caef130430cb..582600e110ba0a00194eafc64922248639f99b47 100644 (file)
@@ -3,7 +3,7 @@ trait SomeTrait {
 }
 
 fn main() {
-    let trait_obj: &SomeTrait = SomeTrait;
+    let trait_obj: &dyn SomeTrait = SomeTrait;
     //~^ ERROR expected value, found trait `SomeTrait`
     //~| ERROR E0038
     //~| method `foo` has no receiver
index 976b0e0286fa03c39bcda8315fe33200fc8198f4..fe9f45d86a6a030ad7be68ecb1b790279910ca91 100644 (file)
@@ -1,14 +1,14 @@
 error[E0423]: expected value, found trait `SomeTrait`
-  --> $DIR/E0033.rs:6:33
+  --> $DIR/E0033.rs:6:37
    |
-LL |     let trait_obj: &SomeTrait = SomeTrait;
-   |                                 ^^^^^^^^^ not a value
+LL |     let trait_obj: &dyn SomeTrait = SomeTrait;
+   |                                     ^^^^^^^^^ not a value
 
 error[E0038]: the trait `SomeTrait` cannot be made into an object
   --> $DIR/E0033.rs:6:20
    |
-LL |     let trait_obj: &SomeTrait = SomeTrait;
-   |                    ^^^^^^^^^^ the trait `SomeTrait` cannot be made into an object
+LL |     let trait_obj: &dyn SomeTrait = SomeTrait;
+   |                    ^^^^^^^^^^^^^^ the trait `SomeTrait` cannot be made into an object
    |
    = note: method `foo` has no receiver
 
index b2226803da7fa128dfc06ce492a1aebe577dd66b..9757e2ab10c7a983075557e97c58974de833d448 100644 (file)
@@ -2,7 +2,7 @@ trait Trait {
     fn foo(&self) -> Self;
 }
 
-fn call_foo(x: Box<Trait>) {
+fn call_foo(x: Box<dyn Trait>) {
     //~^ ERROR E0038
     let y = x.foo();
 }
index 74b77338c85c02d90461a82f8521eca9d52fa063..e3d7593e42a7105b4e9f670a9c95be081a9d6728 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Trait` cannot be made into an object
   --> $DIR/E0038.rs:5:1
    |
-LL | fn call_foo(x: Box<Trait>) {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Trait` cannot be made into an object
+LL | fn call_foo(x: Box<dyn Trait>) {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Trait` cannot be made into an object
    |
    = note: method `foo` references the `Self` type in its arguments or return type
 
index 049707415e50562bb210692935b16937d5120894..287a4088183f4d516423f113dc3c90ff482eeb8b 100644 (file)
@@ -1,6 +1,6 @@
 trait MyTrait { fn foo() {} }
 
-impl Drop for MyTrait {
+impl Drop for dyn MyTrait {
               //~^ ERROR E0120
     fn drop(&mut self) {}
 }
index 9b6603dbaca9c282108bf0bfb379f6227edfa4af..68ca7d800d5ced08a7c12dc29e05708b6ab865c6 100644 (file)
@@ -1,8 +1,8 @@
 error[E0120]: the Drop trait may only be implemented on structures
   --> $DIR/E0120.rs:3:15
    |
-LL | impl Drop for MyTrait {
-   |               ^^^^^^^ implementing Drop requires a struct
+LL | impl Drop for dyn MyTrait {
+   |               ^^^^^^^^^^^ implementing Drop requires a struct
 
 error: aborting due to previous error
 
index 356110671e715d1343eb583c23a0aa29099f46ba..22f739b9e76c2228218f69e2c0265ca93f4183e3 100644 (file)
@@ -2,6 +2,6 @@ trait Trait {
     type Bar;
 }
 
-type Foo = Trait; //~ ERROR E0191
+type Foo = dyn Trait; //~ ERROR E0191
 
 fn main() {}
index 2d9fdfe5d29c7fe2eb262f398bea9bc21a25fabd..92fa85bca0eff5b987adb481178571672c177e08 100644 (file)
@@ -4,8 +4,8 @@ error[E0191]: the value of the associated type `Bar` (from the trait `Trait`) mu
 LL |     type Bar;
    |     --------- `Bar` defined here
 ...
-LL | type Foo = Trait;
-   |            ^^^^^ associated type `Bar` must be specified
+LL | type Foo = dyn Trait;
+   |            ^^^^^^^^^ associated type `Bar` must be specified
 
 error: aborting due to previous error
 
index f4798042538ddc90adc35208ada0baad34b9bdb9..e11a570df79d5b232ecdfa12bc154d04d19fee5a 100644 (file)
@@ -2,7 +2,7 @@ trait Trait {
     type Bar;
 }
 
-type Foo = Trait<F=i32>; //~ ERROR E0220
-                         //~| ERROR E0191
+type Foo = dyn Trait<F=i32>; //~ ERROR E0220
+                             //~| ERROR E0191
 fn main() {
 }
index bd2205fb752743ae8d281a2167237775009a04d1..5da302748cdaffb7e63303dce9b36a1a585e9aec 100644 (file)
@@ -1,8 +1,8 @@
 error[E0220]: associated type `F` not found for `Trait`
-  --> $DIR/E0220.rs:5:18
+  --> $DIR/E0220.rs:5:22
    |
-LL | type Foo = Trait<F=i32>;
-   |                  ^^^^^ associated type `F` not found
+LL | type Foo = dyn Trait<F=i32>;
+   |                      ^^^^^ associated type `F` not found
 
 error[E0191]: the value of the associated type `Bar` (from the trait `Trait`) must be specified
   --> $DIR/E0220.rs:5:12
@@ -10,8 +10,8 @@ error[E0191]: the value of the associated type `Bar` (from the trait `Trait`) mu
 LL |     type Bar;
    |     --------- `Bar` defined here
 ...
-LL | type Foo = Trait<F=i32>;
-   |            ^^^^^^^^^^^^ associated type `Bar` must be specified
+LL | type Foo = dyn Trait<F=i32>;
+   |            ^^^^^^^^^^^^^^^^ associated type `Bar` must be specified
 
 error: aborting due to 2 previous errors
 
index bdd4deafc838e164c510d4a709ec5dad65da8147..0c1a369806d8f399cb460a9b04d1a75cd91a6b20 100644 (file)
@@ -1,6 +1,6 @@
 trait A<T=Self> {}
 
-fn together_we_will_rule_the_galaxy(son: &A) {}
+fn together_we_will_rule_the_galaxy(son: &dyn A) {}
 //~^ ERROR E0393
 
 fn main() {
index bf564ef10210a0d944afb9b0b8bbb7ac4083351b..543e3213633c81c1aefaf585d1a6075b23e5fe94 100644 (file)
@@ -1,8 +1,8 @@
 error[E0393]: the type parameter `T` must be explicitly specified
-  --> $DIR/E0393.rs:3:43
+  --> $DIR/E0393.rs:3:47
    |
-LL | fn together_we_will_rule_the_galaxy(son: &A) {}
-   |                                           ^ missing reference to `T`
+LL | fn together_we_will_rule_the_galaxy(son: &dyn A) {}
+   |                                               ^ missing reference to `T`
    |
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
index 1b5ca09d5a6c4411a9d7f353955b54c5161fa3ab..b1562dc0a8ba0e51e99dea8f233bf1479992e1e7 100644 (file)
@@ -1,7 +1,7 @@
 trait Wedding<'t>: 't { }
 
 struct Prince<'kiss, 'SnowWhite> {
-    child: Box<Wedding<'kiss> + 'SnowWhite>, //~ ERROR E0478
+    child: Box<dyn Wedding<'kiss> + 'SnowWhite>, //~ ERROR E0478
 }
 
 fn main() {
index 71e490364d7abaec3cebe256edaf6d09e65cfb80..587125fdc336e4110ec335bbff433b43aa88890a 100644 (file)
@@ -1,8 +1,8 @@
 error[E0478]: lifetime bound not satisfied
   --> $DIR/E0478.rs:4:5
    |
-LL |     child: Box<Wedding<'kiss> + 'SnowWhite>,
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     child: Box<dyn Wedding<'kiss> + 'SnowWhite>,
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: lifetime parameter instantiated with the lifetime 'SnowWhite as defined on the struct at 3:22
   --> $DIR/E0478.rs:3:22
index 6b572f49cee8b13cfad5aa65c1741141b038fdc1..3311e190937cc4e9e093f8d30a7de828deed8655 100644 (file)
@@ -3,12 +3,12 @@ trait Foo: Iterator<Item = i32, Item = i32> {}
 
 type Unit = ();
 
-fn test() -> Box<Iterator<Item = (), Item = Unit>> {
+fn test() -> Box<dyn Iterator<Item = (), Item = Unit>> {
 //~^ ERROR is already specified
     Box::new(None.into_iter())
 }
 
 fn main() {
-    let _: &Iterator<Item = i32, Item = i32>;
+    let _: &dyn Iterator<Item = i32, Item = i32>;
     test();
 }
index 5854cd7e1438b46c0aa769b88cf37d0152e57b6c..c5b9a71c65994493a1180e9b932782b4d5824aef 100644 (file)
@@ -7,12 +7,12 @@ LL | trait Foo: Iterator<Item = i32, Item = i32> {}
    |                     `Item` bound here first
 
 error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
-  --> $DIR/E0719.rs:6:38
+  --> $DIR/E0719.rs:6:42
    |
-LL | fn test() -> Box<Iterator<Item = (), Item = Unit>> {
-   |                           ---------  ^^^^^^^^^^^ re-bound here
-   |                           |
-   |                           `Item` bound here first
+LL | fn test() -> Box<dyn Iterator<Item = (), Item = Unit>> {
+   |                               ---------  ^^^^^^^^^^^ re-bound here
+   |                               |
+   |                               `Item` bound here first
 
 error: aborting due to 2 previous errors
 
index eb419ba2036a45988b27401dbb3775718469d680..a0fad583a1645a069f3fbbf0be75dd329ac0a648 100644 (file)
@@ -19,6 +19,6 @@ fn main() {
     q as *const [i32]; //~ ERROR cannot cast
 
     // #21397
-    let t: *mut (Trait + 'static) = 0 as *mut _; //~ ERROR casting
+    let t: *mut (dyn Trait + 'static) = 0 as *mut _; //~ ERROR casting
     let mut fail: *const str = 0 as *const str; //~ ERROR casting
 }
index bb7a4d3ff7f6a452d084424d398bec9ec0c92780..93e1471838f72acdf8d97aa1bc05924c15275d52 100644 (file)
@@ -53,10 +53,10 @@ LL |     q as *const [i32];
    |     ^^^^^^^^^^^^^^^^^
 
 error[E0606]: casting `usize` as `*mut (dyn Trait + 'static)` is invalid
-  --> $DIR/fat-ptr-cast.rs:22:37
+  --> $DIR/fat-ptr-cast.rs:22:41
    |
-LL |     let t: *mut (Trait + 'static) = 0 as *mut _;
-   |                                     ^^^^^^^^^^^
+LL |     let t: *mut (dyn Trait + 'static) = 0 as *mut _;
+   |                                         ^^^^^^^^^^^
 
 error[E0606]: casting `usize` as `*const str` is invalid
   --> $DIR/fat-ptr-cast.rs:23:32
index e5028f2f8aa78f5d012b117d5ed0f7db36b86e53..3dbaf5dea250e4f8c0946b33f213cfccd997ee0e 100644 (file)
@@ -52,8 +52,8 @@ struct Dst<X: ?Sized> {
 struct TwoStrs(str, str) where str: Sized; //~ ERROR
 
 
-fn unsized_local() where Dst<A>: Sized { //~ ERROR
-    let x: Dst<A> = *(Box::new(Dst { x: 1 }) as Box<Dst<A>>);
+fn unsized_local() where Dst<dyn A>: Sized { //~ ERROR
+    let x: Dst<dyn A> = *(Box::new(Dst { x: 1 }) as Box<Dst<dyn A>>);
 }
 
 fn return_str() -> str where str: Sized { //~ ERROR
index b04a6e4d671baf7f6b60c7f3f300a982facf3f24..1d346fd42ffa45a99c2ea19c5483648e95d63533 100644 (file)
@@ -102,8 +102,8 @@ LL | struct TwoStrs(str, str) where str: Sized;
 error[E0277]: the size for values of type `(dyn A + 'static)` cannot be known at compilation time
   --> $DIR/feature-gate-trivial_bounds.rs:55:1
    |
-LL | / fn unsized_local() where Dst<A>: Sized {
-LL | |     let x: Dst<A> = *(Box::new(Dst { x: 1 }) as Box<Dst<A>>);
+LL | / fn unsized_local() where Dst<dyn A>: Sized {
+LL | |     let x: Dst<dyn A> = *(Box::new(Dst { x: 1 }) as Box<Dst<dyn A>>);
 LL | | }
    | |_^ doesn't have a size known at compile-time
    |
index a8f81f3f113c997fa9b3da625ef1ebc1535d0111..3686e7b37f4c442e3127df748b00eadf2c02849e 100644 (file)
@@ -1,4 +1,4 @@
-fn f(f: FnOnce()) {}
+fn f(f: dyn FnOnce()) {}
 //~^ ERROR E0277
 
 fn main() {
index bde39cbeaeb285643a62fe0e630b4d0498645614..d20b9e2981e8cf7d1e7ca3e38b84e274ffc4e2cf 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: the size for values of type `(dyn std::ops::FnOnce() + 'static)` cannot be known at compilation time
   --> $DIR/feature-gate-unsized_locals.rs:1:6
    |
-LL | fn f(f: FnOnce()) {}
+LL | fn f(f: dyn FnOnce()) {}
    |      ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::ops::FnOnce() + 'static)`
index f781bc9aeddd1815003118652ed0009d610a3a2d..c3d62a231e5e4f21441017e67a146cef181bf47c 100644 (file)
@@ -1,4 +1,4 @@
 fn main() {
-    let _ : &(Send,) = &((),);
+    let _ : &(dyn Send,) = &((),);
     //~^ ERROR unsized tuple coercion is not stable enough
 }
index 669e87ceadaf50ea45c5e6992ef2b5fa170f1951..5b93c889db1c2215b2ca3554aceeb57eabf52c7e 100644 (file)
@@ -1,8 +1,8 @@
 error[E0658]: unsized tuple coercion is not stable enough for use and is subject to change
-  --> $DIR/feature-gate-unsized_tuple_coercion.rs:2:24
+  --> $DIR/feature-gate-unsized_tuple_coercion.rs:2:28
    |
-LL |     let _ : &(Send,) = &((),);
-   |                        ^^^^^^
+LL |     let _ : &(dyn Send,) = &((),);
+   |                            ^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/42877
    = help: add #![feature(unsized_tuple_coercion)] to the crate attributes to enable
index 21da39dd4004f074a3b1fa380b211e3f652af36c..5c16c1a7e88b7d53a47f95b5f8fba1702991d927 100644 (file)
@@ -3,15 +3,15 @@
 fn needs_fn<F>(x: F) where F: Fn(isize) -> isize {}
 
 fn main() {
-    let _: () = (box |_: isize| {}) as Box<FnOnce(isize)>;
+    let _: () = (box |_: isize| {}) as Box<dyn FnOnce(isize)>;
     //~^ ERROR mismatched types
     //~| expected type `()`
     //~| found type `std::boxed::Box<dyn std::ops::FnOnce(isize)>`
-    let _: () = (box |_: isize, isize| {}) as Box<Fn(isize, isize)>;
+    let _: () = (box |_: isize, isize| {}) as Box<dyn Fn(isize, isize)>;
     //~^ ERROR mismatched types
     //~| expected type `()`
     //~| found type `std::boxed::Box<dyn std::ops::Fn(isize, isize)>`
-    let _: () = (box || -> isize { unimplemented!() }) as Box<FnMut() -> isize>;
+    let _: () = (box || -> isize { unimplemented!() }) as Box<dyn FnMut() -> isize>;
     //~^ ERROR mismatched types
     //~| expected type `()`
     //~| found type `std::boxed::Box<dyn std::ops::FnMut() -> isize>`
index 6b76a6c914f006aa8ab006920822d776f9b415b5..504bc2605ec38ed8a5fca5c61c118b2b4457c3d6 100644 (file)
@@ -1,8 +1,8 @@
 error[E0308]: mismatched types
   --> $DIR/fn-trait-formatting.rs:6:17
    |
-LL |     let _: () = (box |_: isize| {}) as Box<FnOnce(isize)>;
-   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
+LL |     let _: () = (box |_: isize| {}) as Box<dyn FnOnce(isize)>;
+   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
    |
    = note: expected type `()`
               found type `std::boxed::Box<dyn std::ops::FnOnce(isize)>`
@@ -10,8 +10,8 @@ LL |     let _: () = (box |_: isize| {}) as Box<FnOnce(isize)>;
 error[E0308]: mismatched types
   --> $DIR/fn-trait-formatting.rs:10:17
    |
-LL |     let _: () = (box |_: isize, isize| {}) as Box<Fn(isize, isize)>;
-   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
+LL |     let _: () = (box |_: isize, isize| {}) as Box<dyn Fn(isize, isize)>;
+   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
    |
    = note: expected type `()`
               found type `std::boxed::Box<dyn std::ops::Fn(isize, isize)>`
@@ -19,8 +19,8 @@ LL |     let _: () = (box |_: isize, isize| {}) as Box<Fn(isize, isize)>;
 error[E0308]: mismatched types
   --> $DIR/fn-trait-formatting.rs:14:17
    |
-LL |     let _: () = (box || -> isize { unimplemented!() }) as Box<FnMut() -> isize>;
-   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
+LL |     let _: () = (box || -> isize { unimplemented!() }) as Box<dyn FnMut() -> isize>;
+   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found struct `std::boxed::Box`
    |
    = note: expected type `()`
               found type `std::boxed::Box<dyn std::ops::FnMut() -> isize>`
index 546f4d436633363bfcb31ec4821b93ba00054470..f3393347d90dc5a74c9e6b94308eb9729a5d9061 100644 (file)
@@ -58,12 +58,12 @@ fn bar4<'a, 'b, F>(
 struct S_fnty(for<'xa, 'xb: 'xa> fn(&'xa i32, &'xb i32) -> &'xa i32);
 //~^ ERROR lifetime bounds cannot be used in this context
 
-type T1 = Box<for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>;
+type T1 = Box<dyn for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>;
 //~^ ERROR lifetime bounds cannot be used in this context
 
 fn main() {
     let _ : Option<for<'xa, 'xb: 'xa> fn(&'xa i32, &'xb i32) -> &'xa i32> = None;
     //~^ ERROR lifetime bounds cannot be used in this context
-    let _ : Option<Box<for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>> = None;
+    let _ : Option<Box<dyn for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>> = None;
     //~^ ERROR lifetime bounds cannot be used in this context
 }
index 431a89f5eb81b5c44ca6b2d3427626a688ca7dd6..bc6d2288cdfc4fc6fa7b5681a426376055c666c4 100644 (file)
@@ -47,10 +47,10 @@ LL | struct S_fnty(for<'xa, 'xb: 'xa> fn(&'xa i32, &'xb i32) -> &'xa i32);
    |                             ^^^
 
 error: lifetime bounds cannot be used in this context
-  --> $DIR/higher-lifetime-bounds.rs:61:29
+  --> $DIR/higher-lifetime-bounds.rs:61:33
    |
-LL | type T1 = Box<for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>;
-   |                             ^^^
+LL | type T1 = Box<dyn for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>;
+   |                                 ^^^
 
 error: lifetime bounds cannot be used in this context
   --> $DIR/higher-lifetime-bounds.rs:65:34
@@ -59,10 +59,10 @@ LL |     let _ : Option<for<'xa, 'xb: 'xa> fn(&'xa i32, &'xb i32) -> &'xa i32> =
    |                                  ^^^
 
 error: lifetime bounds cannot be used in this context
-  --> $DIR/higher-lifetime-bounds.rs:67:38
+  --> $DIR/higher-lifetime-bounds.rs:67:42
    |
-LL |     let _ : Option<Box<for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>> = None;
-   |                                      ^^^
+LL |     let _ : Option<Box<dyn for<'xa, 'xb: 'xa> Fn(&'xa i32, &'xb i32) -> &'xa i32>> = None;
+   |                                          ^^^
 
 error: aborting due to 11 previous errors
 
diff --git a/src/test/ui/impl-trait/hidden-lifetimes.rs b/src/test/ui/impl-trait/hidden-lifetimes.rs
new file mode 100644 (file)
index 0000000..2ee004a
--- /dev/null
@@ -0,0 +1,63 @@
+// Test to show what happens if we were not careful and allowed invariant
+// lifetimes to escape though an impl trait.
+//
+// Specifically we swap a long lived and short lived reference, giving us a
+// dangling pointer.
+
+use std::cell::RefCell;
+use std::rc::Rc;
+
+trait Swap: Sized {
+    fn swap(self, other: Self);
+}
+
+impl<T> Swap for &mut T {
+    fn swap(self, other: Self) {
+        std::mem::swap(self, other);
+    }
+}
+
+impl<T> Swap for Rc<RefCell<T>> {
+    fn swap(self, other: Self) {
+        <RefCell<T>>::swap(&self, &other);
+    }
+}
+
+// Here we are hiding `'b` making the caller believe that `&'a mut &'s T` and
+// `&'a mut &'l T` are the same type.
+fn hide_ref<'a, 'b, T: 'static>(x: &'a mut &'b T) -> impl Swap + 'a {
+    //~^ ERROR hidden type
+    x
+}
+
+fn dangle_ref() -> &'static [i32; 3] {
+    let mut res = &[4, 5, 6];
+    let x = [1, 2, 3];
+    hide_ref(&mut res).swap(hide_ref(&mut &x));
+    res
+}
+
+// Here we are hiding `'b` making the caller believe that `Rc<RefCell<&'s T>>`
+// and `Rc<RefCell<&'l T>>` are the same type.
+//
+// This is different to the previous example because the concrete return type
+// only has a single lifetime.
+fn hide_rc_refcell<'a, 'b: 'a, T: 'static>(x: Rc<RefCell<&'b T>>) -> impl Swap + 'a {
+    //~^ ERROR hidden type
+    x
+}
+
+fn dangle_rc_refcell() -> &'static [i32; 3] {
+    let long = Rc::new(RefCell::new(&[4, 5, 6]));
+    let x = [1, 2, 3];
+    let short = Rc::new(RefCell::new(&x));
+    hide_rc_refcell(long.clone()).swap(hide_rc_refcell(short));
+    let res: &'static [i32; 3] = *long.borrow();
+    res
+}
+
+fn main() {
+    // both will print nonsense values.
+    println!("{:?}", dangle_ref());
+    println!("{:?}", dangle_rc_refcell())
+}
diff --git a/src/test/ui/impl-trait/hidden-lifetimes.stderr b/src/test/ui/impl-trait/hidden-lifetimes.stderr
new file mode 100644 (file)
index 0000000..6501617
--- /dev/null
@@ -0,0 +1,27 @@
+error[E0700]: hidden type for `impl Trait` captures lifetime that does not appear in bounds
+  --> $DIR/hidden-lifetimes.rs:28:54
+   |
+LL | fn hide_ref<'a, 'b, T: 'static>(x: &'a mut &'b T) -> impl Swap + 'a {
+   |                                                      ^^^^^^^^^^^^^^
+   |
+note: hidden type `&'a mut &'b T` captures the lifetime 'b as defined on the function body at 28:17
+  --> $DIR/hidden-lifetimes.rs:28:17
+   |
+LL | fn hide_ref<'a, 'b, T: 'static>(x: &'a mut &'b T) -> impl Swap + 'a {
+   |                 ^^
+
+error[E0700]: hidden type for `impl Trait` captures lifetime that does not appear in bounds
+  --> $DIR/hidden-lifetimes.rs:45:70
+   |
+LL | fn hide_rc_refcell<'a, 'b: 'a, T: 'static>(x: Rc<RefCell<&'b T>>) -> impl Swap + 'a {
+   |                                                                      ^^^^^^^^^^^^^^
+   |
+note: hidden type `std::rc::Rc<std::cell::RefCell<&'b T>>` captures the lifetime 'b as defined on the function body at 45:24
+  --> $DIR/hidden-lifetimes.rs:45:24
+   |
+LL | fn hide_rc_refcell<'a, 'b: 'a, T: 'static>(x: Rc<RefCell<&'b T>>) -> impl Swap + 'a {
+   |                        ^^
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0700`.
diff --git a/src/test/ui/impl-trait/multiple-lifetimes.rs b/src/test/ui/impl-trait/multiple-lifetimes.rs
new file mode 100644 (file)
index 0000000..8346542
--- /dev/null
@@ -0,0 +1,12 @@
+// Test that multiple liftimes are allowed in impl trait types.
+// compile-pass
+
+trait X<'x>: Sized {}
+
+impl<U> X<'_> for U {}
+
+fn multiple_lifeteimes<'a, 'b, T: 'static>(x: &'a mut &'b T) -> impl X<'b> + 'a {
+    x
+}
+
+fn main() {}
index 26150c7d4a16b77de5f4a76803006e4b48e3bf24..8198c1816a1412976164632b6d1c6b1b5899fc11 100644 (file)
 mod m {
     use iso1::any as are_you_okay1;
     use ::iso2::any as are_you_okay2;
-    type AreYouOkay1 = iso3::any::Any;
-    type AreYouOkay2 = ::iso4::any::Any;
+    type AreYouOkay1 = dyn iso3::any::Any;
+    type AreYouOkay2 = dyn (::iso4::any::Any);
 
     use core::any as are_you_okay3;
     use ::core::any as are_you_okay4;
-    type AreYouOkay3 = core::any::Any;
-    type AreYouOkay4 = ::core::any::Any;
+    type AreYouOkay3 = dyn core::any::Any;
+    type AreYouOkay4 = dyn (::core::any::Any);
 }
 
 fn main() {}
index d4535ac442538db6b58dec9050faa3d394576d5f..d131a944721d01fe7272d50f37736779338e8c19 100644 (file)
@@ -4,8 +4,8 @@ trait Trait {}
 struct Struct;
 
 impl Deref for Struct {
-    type Target = Trait;
-    fn deref(&self) -> &Trait {
+    type Target = dyn Trait;
+    fn deref(&self) -> &dyn Trait {
         unimplemented!();
     }
 }
index e56a56e2dae215367a8209f37d89c11207104c4a..b50a926c63795aa4a6e08a759097535a730247a0 100644 (file)
@@ -1,13 +1,13 @@
 error[E0495]: cannot infer an appropriate lifetime for lifetime parameter in generic type due to conflicting requirements
   --> $DIR/mismatched_trait_impl-2.rs:8:5
    |
-LL |     fn deref(&self) -> &Trait {
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     fn deref(&self) -> &dyn Trait {
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: first, the lifetime cannot outlive the anonymous lifetime #1 defined on the method body at 8:5...
   --> $DIR/mismatched_trait_impl-2.rs:8:5
    |
-LL | /     fn deref(&self) -> &Trait {
+LL | /     fn deref(&self) -> &dyn Trait {
 LL | |         unimplemented!();
 LL | |     }
    | |_____^
diff --git a/src/test/ui/issue-53912.rs b/src/test/ui/issue-53912.rs
new file mode 100644 (file)
index 0000000..d2347c3
--- /dev/null
@@ -0,0 +1,37 @@
+// compile-pass
+
+// This test is the same code as in ui/symbol-names/issue-60925.rs but this checks that the
+// reproduction compiles successfully and doesn't segfault, whereas that test just checks that the
+// symbol mangling fix produces the correct result.
+
+fn dummy() {}
+
+mod llvm {
+    pub(crate) struct Foo;
+}
+mod foo {
+    pub(crate) struct Foo<T>(T);
+
+    impl Foo<::llvm::Foo> {
+        pub(crate) fn foo() {
+            for _ in 0..0 {
+                for _ in &[::dummy()] {
+                    ::dummy();
+                    ::dummy();
+                    ::dummy();
+                }
+            }
+        }
+    }
+
+    pub(crate) fn foo() {
+        Foo::foo();
+        Foo::foo();
+    }
+}
+
+pub fn foo() {
+    foo::foo();
+}
+
+fn main() {}
index 45f29fd79565b09c70349ea23fb1915d6c465aca..a7b827d27a87bb8d22249b67322db3f485074c6f 100644 (file)
@@ -3,7 +3,7 @@ error: lifetime may not live long enough
    |
 LL | fn test<'x>(x: &'x isize) {
    |         -- lifetime `'x` defined here
-LL |     drop::<Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+LL |     drop::<Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
 LL |         x
    |         ^ returning this value requires that `'x` must outlive `'static`
 
index 877b0aba473920fe697e9d6651d13222fe26056f..559c5fcac954bd5f21ac77c9892616cf63da7596 100644 (file)
@@ -1,5 +1,5 @@
 fn test<'x>(x: &'x isize) {
-    drop::<Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+    drop::<Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
         x //~ ERROR E0312
     }));
 }
index 0d653e6ced1efc4dad41af274bfe3321cafbb36b..5e63469da59f57980a53e85890327092081175a0 100644 (file)
@@ -4,11 +4,11 @@ error[E0312]: lifetime of reference outlives lifetime of borrowed content...
 LL |         x
    |         ^
    |
-note: ...the reference is valid for the anonymous lifetime #2 defined on the body at 2:65...
-  --> $DIR/issue-10291.rs:2:65
+note: ...the reference is valid for the anonymous lifetime #2 defined on the body at 2:69...
+  --> $DIR/issue-10291.rs:2:69
    |
-LL |       drop::<Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
-   |  _________________________________________________________________^
+LL |       drop::<Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+   |  _____________________________________________________________________^
 LL | |         x
 LL | |     }));
    | |_____^
index 672386bc8a6c23466f1f538e427bb5007592487a..5e7f8ed7fd5d260d91347a5b8b43e6bc8cf1859b 100644 (file)
@@ -4,16 +4,16 @@
 
 pub mod two_tuple {
     pub trait T { fn dummy(&self) { } }
-    pub struct P<'a>(&'a (T + 'a), &'a (T + 'a));
-    pub fn f<'a>(car: &'a T, cdr: &'a T) -> P<'a> {
+    pub struct P<'a>(&'a (dyn T + 'a), &'a (dyn T + 'a));
+    pub fn f<'a>(car: &'a dyn T, cdr: &'a dyn T) -> P<'a> {
         P(car, cdr)
     }
 }
 
 pub mod two_fields {
     pub trait T { fn dummy(&self) { } }
-    pub struct P<'a> { car: &'a (T + 'a), cdr: &'a (T + 'a) }
-    pub fn f<'a>(car: &'a T, cdr: &'a T) -> P<'a> {
+    pub struct P<'a> { car: &'a (dyn T + 'a), cdr: &'a (dyn T + 'a) }
+    pub fn f<'a>(car: &'a dyn T, cdr: &'a dyn T) -> P<'a> {
         P{ car: car, cdr: cdr }
     }
 }
index f00da0acf8124c878a516dd56ee9725deaf1c1d1..7519ba2826e7a1c76ac49ee4138983da06ceaf35 100644 (file)
@@ -2,11 +2,11 @@
 use std::vec;
 
 pub struct Container<'a> {
-    reader: &'a mut Read
+    reader: &'a mut dyn Read
 }
 
 impl<'a> Container<'a> {
-    pub fn wrap<'s>(reader: &'s mut io::Read) -> Container<'s> {
+    pub fn wrap<'s>(reader: &'s mut dyn io::Read) -> Container<'s> {
         Container { reader: reader }
     }
 
@@ -17,7 +17,7 @@ pub fn read_to(&mut self, vec: &mut [u8]) {
 
 pub fn for_stdin<'a>() -> Container<'a> {
     let mut r = io::stdin();
-    Container::wrap(&mut r as &mut io::Read)
+    Container::wrap(&mut r as &mut dyn io::Read)
 }
 
 fn main() {
index 7eab2a26178af96683102468c0c54a9c5a8a6c5a..a7671b9282a9976ffebb7684878343be69f7bce8 100644 (file)
@@ -1,10 +1,10 @@
 #![feature(box_syntax)]
 
 struct Test {
-    func: Box<FnMut()+'static>
+    func: Box<dyn FnMut() + 'static>
 }
 
 fn main() {
-    let closure: Box<Fn()+'static> = Box::new(|| ());
+    let closure: Box<dyn Fn() + 'static> = Box::new(|| ());
     let test = box Test { func: closure }; //~ ERROR mismatched types
 }
index 4d6f4656d589d2576ddce222653edae31ef3bfe8..fd4fb2443cbe7487fc23550303afe38462382aef 100644 (file)
@@ -14,11 +14,11 @@ struct B<'a, T:'a> {
 
 impl<'a, T> A for B<'a, T> {}
 
-fn foo(_: &A) {}
+fn foo(_: &dyn A) {}
 
 fn bar<G>(b: &B<G>) {
     foo(b);       // Coercion should work
-    foo(b as &A); // Explicit cast should work as well
+    foo(b as &dyn A); // Explicit cast should work as well
 }
 
 fn main() {}
index 77b78c8a1f723343bd77dce96836811be257f79c..0ade359923a0e6c6449d8d4385e61f1c7ccb1186 100644 (file)
@@ -16,10 +16,10 @@ fn get_i(&self) -> isize {
 }
 
 struct A<'a> {
-    p: &'a (X+'a)
+    p: &'a (dyn X + 'a)
 }
 
-fn make_a<'a>(p: &'a X) -> A<'a> {
+fn make_a<'a>(p: &'a dyn X) -> A<'a> {
     A { p: p }
 }
 
index a6c9e9712c05080222956e090190387abd657458..e5274eb823d465809afc1e7224505635a8b1d2d9 100644 (file)
@@ -1,11 +1,11 @@
 trait Foo {
-    fn bar(&mut self, other: &mut Foo);
+    fn bar(&mut self, other: &mut dyn Foo);
 }
 
 struct Baz;
 
 impl Foo for Baz {
-    fn bar(&mut self, other: &Foo) {}
+    fn bar(&mut self, other: &dyn Foo) {}
     //~^ ERROR method `bar` has an incompatible type for trait
     //~| expected type `fn(&mut Baz, &mut dyn Foo)`
     //~| found type `fn(&mut Baz, &dyn Foo)`
index d1e8eb31c8834d76b56418a45feddf3c9d9de7e1..195d0c39b29833beae6a9da0f241e3b4f1d334d5 100644 (file)
@@ -1,18 +1,18 @@
 error[E0053]: method `bar` has an incompatible type for trait
   --> $DIR/issue-13033.rs:8:30
    |
-LL |     fn bar(&mut self, other: &mut Foo);
-   |                              -------- type in trait
+LL |     fn bar(&mut self, other: &mut dyn Foo);
+   |                              ------------ type in trait
 ...
-LL |     fn bar(&mut self, other: &Foo) {}
-   |                              ^^^^ types differ in mutability
+LL |     fn bar(&mut self, other: &dyn Foo) {}
+   |                              ^^^^^^^^ types differ in mutability
    |
    = note: expected type `fn(&mut Baz, &mut dyn Foo)`
               found type `fn(&mut Baz, &dyn Foo)`
 help: consider change the type to match the mutability in trait
    |
-LL |     fn bar(&mut self, other: &mut Foo) {}
-   |                              ^^^^^^^^
+LL |     fn bar(&mut self, other: &mut dyn Foo) {}
+   |                              ^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index c711e3b713f29c38ce6a1f3415d3a64e945addb8..e6995be27d20e728c68b03c262bde9a259296077 100644 (file)
@@ -1,6 +1,6 @@
 // ignore-cloudabi no std::process
 
-fn foo(_: Box<FnMut()>) {}
+fn foo(_: Box<dyn FnMut()>) {}
 
 fn main() {
     foo(loop {
index b58f2bd3b3b7c96541ff23d7477478261f82bd3b..27319c98d6e358c371e3cff2c2b59b62573d5d11 100644 (file)
@@ -2,5 +2,5 @@ trait FromStructReader<'a> { }
 trait ResponseHook {
      fn get(&self);
 }
-fn foo(res : Box<ResponseHook>) { res.get } //~ ERROR attempted to take value of method
+fn foo(res : Box<dyn ResponseHook>) { res.get } //~ ERROR attempted to take value of method
 fn main() {}
index 0853f5cffb762a3628043acc42e120cf84c553ed..ea3b38940cf01523e707a5f7823c0323667122e8 100644 (file)
@@ -1,8 +1,8 @@
 error[E0615]: attempted to take value of method `get` on type `std::boxed::Box<(dyn ResponseHook + 'static)>`
-  --> $DIR/issue-13853-2.rs:5:39
+  --> $DIR/issue-13853-2.rs:5:43
    |
-LL | fn foo(res : Box<ResponseHook>) { res.get }
-   |                                       ^^^ help: use parentheses to call the method: `get()`
+LL | fn foo(res : Box<dyn ResponseHook>) { res.get }
+   |                                           ^^^ help: use parentheses to call the method: `get()`
 
 error: aborting due to previous error
 
index 934d72a67ca1937457ad2d98df45754c1d76bd7c..2ba9ff717739caf6ef97b7c708c73e93b934af47 100644 (file)
@@ -6,9 +6,9 @@ fn dummy(&self) { }
 
 impl Foo for A {}
 
-struct B<'a>(&'a (Foo+'a));
+struct B<'a>(&'a (dyn Foo + 'a));
 
-fn foo<'a>(a: &Foo) -> B<'a> {
+fn foo<'a>(a: &dyn Foo) -> B<'a> {
     B(a)    //~ ERROR explicit lifetime required in the type of `a` [E0621]
 }
 
index c180ed03e540b57621570ab5d56e76727ebc6260..5c07066018e838dd2255692f8d9d626a3c36d00d 100644 (file)
@@ -1,8 +1,8 @@
 error[E0621]: explicit lifetime required in the type of `a`
   --> $DIR/issue-14285.rs:12:5
    |
-LL | fn foo<'a>(a: &Foo) -> B<'a> {
-   |               ---- help: add explicit lifetime `'a` to the type of `a`: `&'a (dyn Foo + 'a)`
+LL | fn foo<'a>(a: &dyn Foo) -> B<'a> {
+   |               -------- help: add explicit lifetime `'a` to the type of `a`: `&'a (dyn Foo + 'a)`
 LL |     B(a)
    |     ^^^^ lifetime `'a` required
 
index a6298f25d470bf83a8ae4580b411bc475be778de..bb338860d8b7783242564bf65e597a7acce836a4 100644 (file)
@@ -1,4 +1,4 @@
 fn main() {
-    let _x = "test" as &::std::any::Any;
+    let _x = "test" as &dyn (::std::any::Any);
     //~^ ERROR the size for values of type
 }
index a3588bb8ebe124e3dba59035600ba0a1aff01ba7..542d8a904c4e30299d8ac03fda271e094631f0f0 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: the size for values of type `str` cannot be known at compilation time
   --> $DIR/issue-14366.rs:2:14
    |
-LL |     let _x = "test" as &::std::any::Any;
+LL |     let _x = "test" as &dyn (::std::any::Any);
    |              ^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `str`
index 61b2b64ddf0c173690af9df3af244f153c5c77ca..9b89c1631df15236faa81b91262eeb22d5dc3fdc 100644 (file)
@@ -2,7 +2,7 @@
 pub trait Reader {}
 
 enum Wrapper<'a> {
-    WrapReader(&'a (Reader + 'a))
+    WrapReader(&'a (dyn Reader + 'a))
 }
 
 trait Wrap<'a> {
@@ -11,7 +11,7 @@ trait Wrap<'a> {
 
 impl<'a, R: Reader> Wrap<'a> for &'a mut R {
     fn wrap(self) -> Wrapper<'a> {
-        Wrapper::WrapReader(self as &'a mut Reader)
+        Wrapper::WrapReader(self as &'a mut dyn Reader)
     }
 }
 
index 78ae21e2837af55cc43aa88e5f2d9c4eaab6a427..60daaafbcc8bd27ca49806503aef445a66317e88 100644 (file)
@@ -26,20 +26,20 @@ fn find<T>(&self) -> Option<T> {
     }
 }
 
-impl<'b> Fn<(&'b mut (Response+'b),)> for SendFile {
-    extern "rust-call" fn call(&self, (_res,): (&'b mut (Response+'b),)) {}
+impl<'b> Fn<(&'b mut (dyn Response + 'b),)> for SendFile {
+    extern "rust-call" fn call(&self, (_res,): (&'b mut (dyn Response + 'b),)) {}
 }
 
-impl<'b> FnMut<(&'b mut (Response+'b),)> for SendFile {
-    extern "rust-call" fn call_mut(&mut self, (_res,): (&'b mut (Response+'b),)) {
+impl<'b> FnMut<(&'b mut (dyn Response + 'b),)> for SendFile {
+    extern "rust-call" fn call_mut(&mut self, (_res,): (&'b mut (dyn Response+'b),)) {
         self.call((_res,))
     }
 }
 
-impl<'b> FnOnce<(&'b mut (Response+'b),)> for SendFile {
+impl<'b> FnOnce<(&'b mut (dyn Response + 'b),)> for SendFile {
     type Output = ();
 
-    extern "rust-call" fn call_once(self, (_res,): (&'b mut (Response+'b),)) {
+    extern "rust-call" fn call_once(self, (_res,): (&'b mut (dyn Response+'b),)) {
         self.call((_res,))
     }
 }
index f69ca4677c9c3095664fd328c90042f7417bec45..b570a2ced67bcea61f637a9b2e610b713fb8a0dc 100644 (file)
@@ -1,7 +1,7 @@
 // compile-pass
 #![allow(dead_code)]
 struct Parser<'a, I, O> {
-    parse: Box<FnMut(I) -> Result<O, String> + 'a>
+    parse: Box<dyn FnMut(I) -> Result<O, String> + 'a>
 }
 
 impl<'a, I: 'a, O: 'a> Parser<'a, I, O> {
index 1e865515c4b74de109182e3ac71b97414c88bc9f..10a5cccbceef023d228a22bdfc3fd2d8d6437052 100644 (file)
@@ -1,7 +1,7 @@
 use std::any::Any;
 
-fn foo<T: Any>(value: &T) -> Box<Any> {
-    Box::new(value) as Box<Any>
+fn foo<T: Any>(value: &T) -> Box<dyn Any> {
+    Box::new(value) as Box<dyn Any>
     //~^ ERROR explicit lifetime required in the type of `value` [E0621]
 }
 
index 1f3b3fe739c4420c3db599680c70f94550e776de..4e3d3ecb9c03adb9ac77dc974c0a25bf4eb80de2 100644 (file)
@@ -1,9 +1,9 @@
 error[E0621]: explicit lifetime required in the type of `value`
   --> $DIR/issue-16922.rs:4:5
    |
-LL | fn foo<T: Any>(value: &T) -> Box<Any> {
+LL | fn foo<T: Any>(value: &T) -> Box<dyn Any> {
    |                       -- help: add explicit lifetime `'static` to the type of `value`: `&'static T`
-LL |     Box::new(value) as Box<Any>
+LL |     Box::new(value) as Box<dyn Any>
    |     ^^^^^^^^^^^^^^^ lifetime `'static` required
 
 error: aborting due to previous error
index d356ce8a4da407bb2b602ed45afe703ab27fee56..d5f1b1310eb5c5a91868f9a7298cddaf92b67ec4 100644 (file)
@@ -1,6 +1,6 @@
 // compile-pass
 // skip-codegen
-fn cb<'a,T>(_x: Box<Fn((&'a i32, &'a (Vec<&'static i32>, bool))) -> T>) -> T {
+fn cb<'a,T>(_x: Box<dyn Fn((&'a i32, &'a (Vec<&'static i32>, bool))) -> T>) -> T {
     panic!()
 }
 
index cfb2fe674edf722609b97c1644c9d46252f80dbb..b9813ef1eef77aef791270945a073cf785b12ea1 100644 (file)
@@ -2,10 +2,10 @@ fn main() {
     let _foo = &[1_usize, 2] as [usize];
     //~^ ERROR cast to unsized type: `&[usize; 2]` as `[usize]`
 
-    let _bar = Box::new(1_usize) as std::fmt::Debug;
+    let _bar = Box::new(1_usize) as dyn std::fmt::Debug;
     //~^ ERROR cast to unsized type: `std::boxed::Box<usize>` as `dyn std::fmt::Debug`
 
-    let _baz = 1_usize as std::fmt::Debug;
+    let _baz = 1_usize as dyn std::fmt::Debug;
     //~^ ERROR cast to unsized type: `usize` as `dyn std::fmt::Debug`
 
     let _quux = [1_usize, 2] as [usize];
index 436ee7325f8e5339ad9554779aaebab7b06f0316..0ab035515a0515220d72b1824996c69d6641681c 100644 (file)
@@ -13,21 +13,21 @@ LL |     let _foo = &[1_usize, 2] as [usize];
 error[E0620]: cast to unsized type: `std::boxed::Box<usize>` as `dyn std::fmt::Debug`
   --> $DIR/issue-17441.rs:5:16
    |
-LL |     let _bar = Box::new(1_usize) as std::fmt::Debug;
-   |                ^^^^^^^^^^^^^^^^^^^^^---------------
+LL |     let _bar = Box::new(1_usize) as dyn std::fmt::Debug;
+   |                ^^^^^^^^^^^^^^^^^^^^^-------------------
    |                                     |
-   |                                     help: try casting to a `Box` instead: `Box<std::fmt::Debug>`
+   |                                     help: try casting to a `Box` instead: `Box<dyn std::fmt::Debug>`
 
 error[E0620]: cast to unsized type: `usize` as `dyn std::fmt::Debug`
   --> $DIR/issue-17441.rs:8:16
    |
-LL |     let _baz = 1_usize as std::fmt::Debug;
-   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     let _baz = 1_usize as dyn std::fmt::Debug;
+   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 help: consider using a box or reference as appropriate
   --> $DIR/issue-17441.rs:8:16
    |
-LL |     let _baz = 1_usize as std::fmt::Debug;
+LL |     let _baz = 1_usize as dyn std::fmt::Debug;
    |                ^^^^^^^
 
 error[E0620]: cast to unsized type: `[usize; 2]` as `[usize]`
index d56f346ecd45a4899148bb15e55dcaf2683db2e0..73865ae2d2eb6160fde0d29ca35bcb162fbd88cf 100644 (file)
@@ -17,5 +17,5 @@ fn drop(&mut self) {
 }
 
 fn main() {
-    let x:G<Bar>;
+    let x:G<dyn Bar>;
 }
index 184d122d5cd615b96aac5c8d49ade78cc1b02409..122940f1c1726e52ec0f68738e3beedec17a6adb 100644 (file)
@@ -1,7 +1,7 @@
 pub trait AbstractRenderer {}
 
 fn _create_render(_: &()) ->
-    AbstractRenderer
+    dyn AbstractRenderer
 //~^ ERROR the size for values of type
 {
     match 0 {
index 23b58c3f6df3d88fb072c93f8c00ddb46d68cb54..9bdf470413b1cbc66c091ca52c81e50fd96c6aa0 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the size for values of type `(dyn AbstractRenderer + 'static)` cannot be known at compilation time
   --> $DIR/issue-18107.rs:4:5
    |
-LL |     AbstractRenderer
-   |     ^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
+LL |     dyn AbstractRenderer
+   |     ^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn AbstractRenderer + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index 8e39dc15597e7c944f32d4ebeb22cea0397f6527..4d0c4464759c6ee85edfdf37bb726d9c3798ecdb 100644 (file)
@@ -5,7 +5,7 @@ pub trait Promisable: Send + Sync {}
 impl<T: Send + Sync> Promisable for T {}
 
 pub fn propagate<'a, T, E, F, G>(mut action: F)
-    -> Box<FnMut(Result<T, E>) -> Result<T, E> + 'a>
+    -> Box<dyn FnMut(Result<T, E>) -> Result<T, E> + 'a>
     where
         T: Promisable + Clone + 'a,
         E: Promisable + Clone + 'a,
index 2f05ece31979f71f05d763ff5e00f2bd0806f700..3e04a914d4586fbc4b3ca8edbf8ddc15aa415866 100644 (file)
@@ -6,7 +6,7 @@ trait T {
     fn foo(&self) -> i32 { 0 }
 }
 
-impl<'a> T + 'a {
+impl<'a> dyn T + 'a {
     fn foo(&self) -> i32 { 1 }
 }
 
index 64c89df3868cca243fd83b980c5a7f72e8842a7f..a2e238da03a3e999fbd484ff83bfa4c9676c534e 100644 (file)
@@ -5,7 +5,7 @@ trait T {
     fn foo(&self);
 }
 
-impl<'a> T + 'a {
+impl<'a> dyn T + 'a {
     fn foo(&self) {}
 }
 
@@ -14,6 +14,6 @@ fn foo(&self) {}
 }
 
 fn main() {
-    let x: &T = &0i32;
+    let x: &dyn T = &0i32;
     x.foo(); //~ ERROR multiple applicable items in scope [E0034]
 }
index b84a1adb42569627df7691ae44178601cc0ae877..d4851ac14187ec0433abcdb2675f02a86fee2e09 100644 (file)
@@ -18,11 +18,11 @@ fn ufcs() {
 }
 
 trait Push<'c> {
-    fn push<'f: 'c>(&self, push: Box<FnMut() + 'f>);
+    fn push<'f: 'c>(&self, push: Box<dyn FnMut() + 'f>);
 }
 
-impl<'c> Push<'c> for RefCell<Vec<Box<FnMut() + 'c>>> {
-    fn push<'f: 'c>(&self, fun: Box<FnMut() + 'f>) {
+impl<'c> Push<'c> for RefCell<Vec<Box<dyn FnMut() + 'c>>> {
+    fn push<'f: 'c>(&self, fun: Box<dyn FnMut() + 'f>) {
         self.borrow_mut().push(fun)
     }
 }
index 80db056e7dd3aa5ca2e7cc352366b080408827a2..e634c55f824fdf770f04658e7181b4ccdb79d119 100644 (file)
@@ -8,7 +8,7 @@ impl Foo for X {
     type Item = bool;
 }
 
-fn print_x(_: &Foo<Item=bool>, extra: &str) {
+fn print_x(_: &dyn Foo<Item=bool>, extra: &str) {
     println!("{}", extra);
 }
 
index eb7e4ad405fa11df50c412f2bfc4587dea088d6e..41e8470ecd04f260ec598a7d36eb9342724c6a1b 100644 (file)
@@ -1,8 +1,8 @@
 error[E0061]: this function takes 2 parameters but 1 parameter was supplied
   --> $DIR/issue-18819.rs:16:5
    |
-LL | fn print_x(_: &Foo<Item=bool>, extra: &str) {
-   | ------------------------------------------- defined here
+LL | fn print_x(_: &dyn Foo<Item=bool>, extra: &str) {
+   | ----------------------------------------------- defined here
 ...
 LL |     print_x(X);
    |     ^^^^^^^^^^ expected 2 parameters
index 9db3084918239805f3b5f6fd309f15fa12fe5cee..91fbb13cd69885253925aa8a8c79d47efa9e1b5b 100644 (file)
@@ -1,4 +1,4 @@
-type FuncType<'f> = Fn(&isize) -> isize + 'f;
+type FuncType<'f> = dyn Fn(&isize) -> isize + 'f;
 
 fn ho_func(f: Option<FuncType>) {
     //~^ ERROR the size for values of type
index f3824765f237a9f94403d9080262581f1281c983..ab4c9c736d8963326a99ff1a483ac0e57c7151b2 100644 (file)
@@ -6,7 +6,7 @@
 struct MyString<'a>(&'a String);
 
 struct B {
-    list: Vec<Box<fmt::Debug>>,
+    list: Vec<Box<dyn fmt::Debug>>,
 }
 
 trait A<'a> {
index b07800928bc2231e10066f7e113e4e6222fb7f8f..4b6f04e251b947abb349e15a8610664469a5e233 100644 (file)
@@ -8,13 +8,13 @@ fn foo<T>(&self, _: &T) {}
 }
 
 #[inline(never)]
-fn foo(b: &Bar) {
+fn foo(b: &dyn Bar) {
     //~^ ERROR E0038
     b.foo(&0)
 }
 
 fn main() {
     let mut thing = Thing;
-    let test: &Bar = &mut thing;
+    let test: &dyn Bar = &mut thing;
     foo(test);
 }
index 939390102c3870ade9ab116f37b2427cba59522d..63c33b7f4472d298f565c17b38e63bb4ac5b7834 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/issue-18959.rs:11:1
    |
-LL | fn foo(b: &Bar) {
-   | ^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn foo(b: &dyn Bar) {
+   | ^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `foo` has generic type parameters
 
index e03934866495b0c0df1a7172ed25f4e91e294030..7fe662e907d733f3fc6af5f623ec3460a821d6d1 100644 (file)
@@ -3,7 +3,7 @@
 pub trait Foo : Send { }
 
 pub struct MyFoo {
-    children: Vec<Box<Foo>>,
+    children: Vec<Box<dyn Foo>>,
 }
 
 impl Foo for MyFoo { }
index efbc5a0346ac5fafcd921e6afdc8b10151486a74..5c10e2067e408adc290d328a503639174a6913da 100644 (file)
@@ -8,7 +8,7 @@ fn qiz() {}
 }
 
 struct Bar {
-  foos: &'static [&'static (Qiz + 'static)]
+  foos: &'static [&'static (dyn Qiz + 'static)]
 //~^ ERROR E0038
 }
 
index 060e160f2e484f3440260565ae200f83a4b84483..27e3ff57bf9ab484addb2496365b7043c10adf86 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Qiz` cannot be made into an object
   --> $DIR/issue-19380.rs:11:3
    |
-LL |   foos: &'static [&'static (Qiz + 'static)]
-   |   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Qiz` cannot be made into an object
+LL |   foos: &'static [&'static (dyn Qiz + 'static)]
+   |   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Qiz` cannot be made into an object
    |
    = note: method `qiz` has no receiver
 
index cdec74fe9684db8301bb72a4f9a115e3309140d9..59544393bae05f02fddc75ddba568ff454572c9c 100644 (file)
@@ -12,10 +12,10 @@ trait Component: 'static {}
 impl Component for Engine {}
 
 trait Env {
-    fn get_component_type_id(&self, type_id: TypeId) -> Option<Fp<Component>>;
+    fn get_component_type_id(&self, type_id: TypeId) -> Option<Fp<dyn Component>>;
 }
 
-impl<'a> Env+'a {
+impl<'a> dyn Env + 'a {
     fn get_component<T: Component>(&self) -> Option<Fp<T>> {
         let x = self.get_component_type_id(TypeId::of::<T>());
         None
@@ -23,13 +23,13 @@ fn get_component<T: Component>(&self) -> Option<Fp<T>> {
 }
 
 trait Figment {
-    fn init(&mut self, env: &Env);
+    fn init(&mut self, env: &dyn Env);
 }
 
 struct MyFigment;
 
 impl Figment for MyFigment {
-    fn init(&mut self, env: &Env) {
+    fn init(&mut self, env: &dyn Env) {
         let engine = env.get_component::<Engine>();
     }
 }
index 6ba334905499ed3c424fc38c3a19c3cb6ab14ecd..9e4b77d87f8b59e1482a8da4c3f3986219ab5289 100644 (file)
@@ -7,7 +7,7 @@ trait Foo {
     fn dummy(&self) { }
 }
 
-fn bar(x: &Foo) {}
+fn bar(x: &dyn Foo) {}
 //~^ ERROR the associated type `A` (from the trait `Foo`) must be specified
 
 pub fn main() {}
index a8894f84e743d13a4b21198f9b78c73984b21086..f1e5419c712296a3e5de5ae14b3d22527d266efd 100644 (file)
@@ -4,8 +4,8 @@ error[E0191]: the value of the associated type `A` (from the trait `Foo`) must b
 LL |     type A;
    |     ------- `A` defined here
 ...
-LL | fn bar(x: &Foo) {}
-   |            ^^^ associated type `A` must be specified
+LL | fn bar(x: &dyn Foo) {}
+   |            ^^^^^^^ associated type `A` must be specified
 
 error: aborting due to previous error
 
index 9f0b08d6c357cabc55d8084815444838a11cb830..7054ef41b1c829b989a2c20960c80ef15f1f871d 100644 (file)
@@ -14,7 +14,7 @@ impl Bar for Thing { }
 
 fn main() {
     let mut thing = Thing;
-    let test: &mut Bar = &mut thing;
+    let test: &mut dyn Bar = &mut thing;
     //~^ ERROR E0038
     //~| ERROR E0038
 }
index d0f05a41d4d3a57e5121a12e6823c3391c4744cc..e5da0a9b0dac38e2f92cd3dc8b3b6aa84610dcfb 100644 (file)
@@ -1,16 +1,16 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/issue-19538.rs:17:15
    |
-LL |     let test: &mut Bar = &mut thing;
-   |               ^^^^^^^^ the trait `Bar` cannot be made into an object
+LL |     let test: &mut dyn Bar = &mut thing;
+   |               ^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `foo` has generic type parameters
 
 error[E0038]: the trait `Bar` cannot be made into an object
-  --> $DIR/issue-19538.rs:17:26
+  --> $DIR/issue-19538.rs:17:30
    |
-LL |     let test: &mut Bar = &mut thing;
-   |                          ^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL |     let test: &mut dyn Bar = &mut thing;
+   |                              ^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `foo` has generic type parameters
    = note: required because of the requirements on the impl of `std::ops::CoerceUnsized<&mut dyn Bar>` for `&mut Thing`
index b6dfffbd69ebb6db40e7be53ff230e9ff4e3b31f..0e69b7f3d1e0c57892f32ecc8e94940557d72793 100644 (file)
@@ -10,7 +10,7 @@ trait Foo<T> {
 enum Bar<T> { Bla(T) }
 
 struct Baz<'a> {
-    inner: for<'b> Foo<Bar<&'b ()>> + 'a,
+    inner: dyn for<'b> Foo<Bar<&'b ()>> + 'a,
 }
 
 fn main() {}
index 11a2a573ea6776dd2bdedb1457fede91437ae410..17b7d32ebf59b95e47fd19df991b0d92838b2fad 100644 (file)
@@ -1,4 +1,4 @@
-fn changer<'a>(mut things: Box<Iterator<Item=&'a mut u8>>) {
+fn changer<'a>(mut things: Box<dyn Iterator<Item=&'a mut u8>>) {
     for item in *things { *item = 0 }
 //~^ ERROR the size for values of type
 }
index ea89bca78d07649c444650a6c1d0496c75cbcb4b..2a05bba7b163214b6ca06037be8acd1c5a024dbf 100644 (file)
@@ -4,7 +4,7 @@ fn f<T: Array>(x: &T) {
     let _ = x
     //~^ ERROR `Array` cannot be made into an object
     as
-    &Array;
+    &dyn Array;
     //~^ ERROR `Array` cannot be made into an object
 }
 
index acc223c0b2dfced9e5f52f5a4cf321165356e584..66309394a426d6c5efd12a3f03124d50a4f975f7 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Array` cannot be made into an object
   --> $DIR/issue-20692.rs:7:5
    |
-LL |     &Array;
-   |     ^^^^^^ the trait `Array` cannot be made into an object
+LL |     &dyn Array;
+   |     ^^^^^^^^^^ the trait `Array` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
 
index 6d3c7331a45798971ee3d52af25b9fb8823da5ce..ef4b1581fd874f900d31bdfbe4ce82c8e9f6d09e 100644 (file)
@@ -12,7 +12,7 @@ pub trait Subscriber {
 
 pub trait Publisher<'a> {
     type Output;
-    fn subscribe(&mut self, _: Box<Subscriber<Input=Self::Output> + 'a>);
+    fn subscribe(&mut self, _: Box<dyn Subscriber<Input=Self::Output> + 'a>);
 }
 
 pub trait Processor<'a> : Subscriber + Publisher<'a> { }
@@ -20,12 +20,12 @@ pub trait Processor<'a> : Subscriber + Publisher<'a> { }
 impl<'a, P> Processor<'a> for P where P : Subscriber + Publisher<'a> { }
 
 struct MyStruct<'a> {
-    sub: Box<Subscriber<Input=u64> + 'a>
+    sub: Box<dyn Subscriber<Input=u64> + 'a>
 }
 
 impl<'a> Publisher<'a> for MyStruct<'a> {
     type Output = u64;
-    fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+    fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
         // Not obvious, but there is an implicit lifetime here -------^
         //~^^ ERROR cannot infer
         //~| ERROR mismatched types
index 70a395d0b89eb987d01c41ae8a223970665e53c4..64e3cdc64c1127d3522a1283fbd3ac3c6e069d55 100644 (file)
@@ -1,7 +1,7 @@
 error[E0308]: mismatched types
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
@@ -15,7 +15,7 @@ LL | |     }
 note: the anonymous lifetime #2 defined on the method body at 28:5...
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
@@ -32,7 +32,7 @@ LL | impl<'a> Publisher<'a> for MyStruct<'a> {
 error[E0308]: mismatched types
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
@@ -51,7 +51,7 @@ LL | impl<'a> Publisher<'a> for MyStruct<'a> {
 note: ...does not necessarily outlive the anonymous lifetime #2 defined on the method body at 28:5
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
@@ -63,7 +63,7 @@ LL | |     }
 error[E0495]: cannot infer an appropriate lifetime for lifetime parameter `'a` due to conflicting requirements
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
@@ -75,7 +75,7 @@ LL | |     }
 note: first, the lifetime cannot outlive the anonymous lifetime #2 defined on the method body at 28:5...
   --> $DIR/issue-20831-debruijn.rs:28:5
    |
-LL | /     fn subscribe(&mut self, t : Box<Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
+LL | /     fn subscribe(&mut self, t : Box<dyn Subscriber<Input=<Self as Publisher>::Output> + 'a>) {
 LL | |         // Not obvious, but there is an implicit lifetime here -------^
 LL | |
 LL | |
index 259fff2e6c2f8531169cfe5a98591759e4dc9eb0..c0c222978970d51d36a34a93e7a465d3e2833333 100644 (file)
@@ -1,6 +1,6 @@
 trait Foo {}
 
-impl<'a> Foo for Foo+'a {}
+impl<'a> Foo for dyn Foo + 'a {}
 //~^ ERROR the object type `(dyn Foo + 'a)` automatically implements the trait `Foo`
 
 fn main() {}
index d15a5196667f392258439ab68b4fc0dfb201be87..3819a21a2cfff25a5c604fe9f5597fd3960db2b8 100644 (file)
@@ -1,8 +1,8 @@
 error[E0371]: the object type `(dyn Foo + 'a)` automatically implements the trait `Foo`
   --> $DIR/issue-20939.rs:3:1
    |
-LL | impl<'a> Foo for Foo+'a {}
-   | ^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Foo + 'a)` automatically implements trait `Foo`
+LL | impl<'a> Foo for dyn Foo + 'a {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Foo + 'a)` automatically implements trait `Foo`
 
 error: aborting due to previous error
 
index 5e30db17c6d18a53664f9554d8657b6a2aff28b9..12efce9496efa2af5df7bbf9c9f27b33bccf51fa 100644 (file)
@@ -8,7 +8,7 @@ trait Iterator {
     fn dummy(&self) { }
 }
 
-impl<'a, T> Iterator for &'a mut (Iterator<Item=T> + 'a) {
+impl<'a, T> Iterator for &'a mut (dyn Iterator<Item=T> + 'a) {
     type Item = T;
 }
 
index b902893bf822438bfcf7d4302ae4cfd22527ea9e..0bc87824ccec32bab96080c6dc8fdcce1f0c7301 100644 (file)
@@ -2,7 +2,7 @@
 
 fn main() {
     let x = &10 as
-            &Add;
+            &dyn Add;
             //~^ ERROR E0393
             //~| ERROR E0191
 }
index 7655e0811e066b4f0cd5b7b11d8e0fc06d33e783..9be7b052da31cf3fa4c71353dcd951c81d6b69bb 100644 (file)
@@ -1,16 +1,16 @@
 error[E0393]: the type parameter `Rhs` must be explicitly specified
-  --> $DIR/issue-21950.rs:5:14
+  --> $DIR/issue-21950.rs:5:18
    |
-LL |             &Add;
-   |              ^^^ missing reference to `Rhs`
+LL |             &dyn Add;
+   |                  ^^^ missing reference to `Rhs`
    |
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
 error[E0191]: the value of the associated type `Output` (from the trait `std::ops::Add`) must be specified
   --> $DIR/issue-21950.rs:5:14
    |
-LL |             &Add;
-   |              ^^^ associated type `Output` must be specified
+LL |             &dyn Add;
+   |              ^^^^^^^ associated type `Output` must be specified
 
 error: aborting due to 2 previous errors
 
index 75ac78ad24fea71ab3af0feb9599539df443c6dd..508c9c91b04e5f989fed2ddf659f07f7da876163 100644 (file)
@@ -4,8 +4,8 @@
 
 fn main() {
     let ptr: *mut () = 0 as *mut _;
-    let _: &mut Fn() = unsafe {
-        &mut *(ptr as *mut Fn())
+    let _: &mut dyn Fn() = unsafe {
+        &mut *(ptr as *mut dyn Fn())
         //~^ ERROR expected a `std::ops::Fn<()>` closure, found `()`
     };
 }
index de2d315ff5c68d6fd1eb82c4c5cd5df6f26b1f41..19fb080154a4a3bf0a9db0b24ebce5c565a030e4 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: expected a `std::ops::Fn<()>` closure, found `()`
   --> $DIR/issue-22034.rs:8:16
    |
-LL |         &mut *(ptr as *mut Fn())
+LL |         &mut *(ptr as *mut dyn Fn())
    |                ^^^ expected an `Fn<()>` closure, found `()`
    |
    = help: the trait `std::ops::Fn<()>` is not implemented for `()`
index b683834de441bf4dc88931609a11135a2a4cad56..e1b3dfe5b61bd39d66522943f610d12ac5d43c58 100644 (file)
@@ -1,3 +1,3 @@
 fn main() {
-    0 as &std::any::Any; //~ ERROR non-primitive cast
+    0 as &dyn std::any::Any; //~ ERROR non-primitive cast
 }
index e9846b848f43181764c4f7ff0cade0d052ba4fd2..cc7ace30cabef108eff333f1c6b428fa847a885c 100644 (file)
@@ -1,8 +1,8 @@
 error[E0605]: non-primitive cast: `i32` as `&(dyn std::any::Any + 'static)`
   --> $DIR/issue-22289.rs:2:5
    |
-LL |     0 as &std::any::Any;
-   |     ^^^^^^^^^^^^^^^^^^^
+LL |     0 as &dyn std::any::Any;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: an `as` expression can only be used to convert between primitive types. Consider using the `From` trait
 
index f7ebdb0372ad8b6685ae037020ae01954c9c0094..250fec2588702c0e94ec3155b40e36e2a86f2202 100644 (file)
@@ -8,7 +8,7 @@ fn get<'a>(&'a self, y: usize, x: usize) -> Option<&'a <Self as Index<usize>>::O
             return None;
         }
         let i = y * self.columns() + x;
-        let indexer = &(*self as &Index<usize, Output = <Self as Index<usize>>::Output>);
+        let indexer = &(*self as &dyn Index<usize, Output = <Self as Index<usize>>::Output>);
         //~^ERROR non-primitive cast
         Some(indexer.index(i))
     }
index 6a012b214c504a6a0ccfa183092dd9c582717a3e..fc32fd376b75a9eb023d3fc8b5e54dc184bc19fc 100644 (file)
@@ -1,8 +1,8 @@
 error[E0605]: non-primitive cast: `Self` as `&dyn std::ops::Index<usize, Output = <Self as std::ops::Index<usize>>::Output>`
   --> $DIR/issue-22312.rs:11:24
    |
-LL |         let indexer = &(*self as &Index<usize, Output = <Self as Index<usize>>::Output>);
-   |                        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         let indexer = &(*self as &dyn Index<usize, Output = <Self as Index<usize>>::Output>);
+   |                        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: an `as` expression can only be used to convert between primitive types. Consider using the `From` trait
 
index 90912cfda0d4e78a005f860d21aee35d66c0f80b..bab0469c011934b27a3330b21531e9d0540fb4f8 100644 (file)
@@ -1,6 +1,6 @@
 trait A<T=Self> {}
 
-fn f(a: &A) {}
+fn f(a: &dyn A) {}
 //~^ ERROR E0393
 
 fn main() {}
index f21551a55bc9a0732d6681fe28e141cfcf9d8f71..3ce164e9548b4e71370b1fccab866b0df7114f5d 100644 (file)
@@ -1,8 +1,8 @@
 error[E0393]: the type parameter `T` must be explicitly specified
-  --> $DIR/issue-22370.rs:3:10
+  --> $DIR/issue-22370.rs:3:14
    |
-LL | fn f(a: &A) {}
-   |          ^ missing reference to `T`
+LL | fn f(a: &dyn A) {}
+   |              ^ missing reference to `T`
    |
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
index 0d7d67cbc1bc26aa81fea3a21cb164e7590b315f..3e800a2b61db94edcfcc18cef26e8a84a44876b9 100644 (file)
@@ -2,7 +2,7 @@ pub trait Foo {
     type A;
 }
 
-type I<'a> = &'a (Foo + 'a);
+type I<'a> = &'a (dyn Foo + 'a);
 //~^ ERROR the value of the associated type `A` (from the trait `Foo`) must be specified
 
 fn main() {}
index bbdbeb6ae98049dfba92a1b698b706767dc4d5e0..eb78c4fc311fc3d751a145a597fbf739204d5f31 100644 (file)
@@ -4,8 +4,8 @@ error[E0191]: the value of the associated type `A` (from the trait `Foo`) must b
 LL |     type A;
    |     ------- `A` defined here
 ...
-LL | type I<'a> = &'a (Foo + 'a);
-   |                   ^^^^^^^^ associated type `A` must be specified
+LL | type I<'a> = &'a (dyn Foo + 'a);
+   |                   ^^^^^^^^^^^^ associated type `A` must be specified
 
 error: aborting due to previous error
 
index 4b8e3aa9eb3e10afdcc68e1279c4d7a832f62751..acee99dbedcc4bd6a2b18b81826601b193974384 100644 (file)
@@ -1,6 +1,6 @@
 use std::ops::{Add, Sub};
 
-type Test = Add +
+type Test = dyn Add +
             //~^ ERROR E0393
             //~| ERROR E0191
             Sub;
index 322136d35cad156b37ed86fbd5b1040676dc8da9..5b58adb197c6903c6fcd103e74e720c2d3111b1a 100644 (file)
@@ -7,21 +7,21 @@ LL |             Sub;
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
 error[E0393]: the type parameter `Rhs` must be explicitly specified
-  --> $DIR/issue-22560.rs:3:13
+  --> $DIR/issue-22560.rs:3:17
    |
-LL | type Test = Add +
-   |             ^^^ missing reference to `Rhs`
+LL | type Test = dyn Add +
+   |                 ^^^ missing reference to `Rhs`
    |
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
 error[E0225]: only auto traits can be used as additional traits in a trait object
   --> $DIR/issue-22560.rs:6:13
    |
-LL | type Test = Add +
-   |             ---
-   |             |
-   |             first non-auto trait
-   |             trait alias used in trait object type (first use)
+LL | type Test = dyn Add +
+   |                 ---
+   |                 |
+   |                 first non-auto trait
+   |                 trait alias used in trait object type (first use)
 ...
 LL |             Sub;
    |             ^^^
@@ -32,7 +32,7 @@ LL |             Sub;
 error[E0191]: the value of the associated types `Output` (from the trait `std::ops::Add`), `Output` (from the trait `std::ops::Sub`) must be specified
   --> $DIR/issue-22560.rs:3:13
    |
-LL |   type Test = Add +
+LL |   type Test = dyn Add +
    |  _____________^
    | |_____________|
    | |
index 5df3d88b168fabb25ae56a5463c8ede1bda00022..a7b94c106a4c8a7680b9b132beff7ff4f089788a 100644 (file)
@@ -4,7 +4,7 @@
 use std::collections::hash_map::Entry::Vacant;
 
 pub fn foo() {
-    type F = Box<Fn(&()) + 'static>;
+    type F = Box<dyn Fn(&()) + 'static>;
     let mut map: HashMap<(), F> = HashMap::new();
     let x: &mut F = match map.entry(()) {
         Vacant(_) => unimplemented!(),
index 8ef4af15bd462b957ae1313e422f93bb8c1c153f..5db2891e65e753efffcfeb9d78a37d7bf4f709e4 100644 (file)
@@ -17,7 +17,7 @@ pub trait Process<'a> {
 }
 
 fn push_process<P>(process: P) where P: Process<'static> {
-    let _: Box<for<'b> Wrap<'b>> = Box::new(Wrapper(process));
+    let _: Box<dyn for<'b> Wrap<'b>> = Box::new(Wrapper(process));
 //~^ ERROR is not an iterator
 }
 
index ebd096f1dde5ac98a2e29620a724251033b5dcaa..fc5de23752b3e7e85ab8bdfe69690dee8b20c948 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: `<P as Process<'_>>::Item` is not an iterator
-  --> $DIR/issue-22872.rs:20:36
+  --> $DIR/issue-22872.rs:20:40
    |
-LL |     let _: Box<for<'b> Wrap<'b>> = Box::new(Wrapper(process));
-   |                                    ^^^^^^^^^^^^^^^^^^^^^^^^^^ `<P as Process<'_>>::Item` is not an iterator
+LL |     let _: Box<dyn for<'b> Wrap<'b>> = Box::new(Wrapper(process));
+   |                                        ^^^^^^^^^^^^^^^^^^^^^^^^^^ `<P as Process<'_>>::Item` is not an iterator
    |
    = help: the trait `std::iter::Iterator` is not implemented for `<P as Process<'_>>::Item`
    = help: consider adding a `where <P as Process<'_>>::Item: std::iter::Iterator` bound
index 0639ce30aa0e8178c7287f8590fb75bbaf86f3f1..2638e15f0eae501e4763211f600a14955d43c59c 100644 (file)
@@ -4,9 +4,9 @@
 fn main()
 {
     fn h(x:i32) -> i32 {3*x}
-    let mut vfnfer:Vec<Box<Any>> = vec![];
+    let mut vfnfer:Vec<Box<dyn Any>> = vec![];
     vfnfer.push(box h);
-    println!("{:?}",(vfnfer[0] as Fn)(3));
+    println!("{:?}",(vfnfer[0] as dyn Fn)(3));
     //~^ ERROR the precise format of `Fn`-family traits'
     //~| ERROR wrong number of type arguments: expected 1, found 0 [E0107]
     //~| ERROR the value of the associated type `Output` (from the trait `std::ops::FnOnce`)
index fbefbe4f56e688725d08e7e2a23e92955ed47d19..e99854539de88f6f915e599cd4c5843717ed858b 100644 (file)
@@ -1,23 +1,23 @@
 error[E0658]: the precise format of `Fn`-family traits' type parameters is subject to change. Use parenthetical notation (Fn(Foo, Bar) -> Baz) instead
-  --> $DIR/issue-23024.rs:9:35
+  --> $DIR/issue-23024.rs:9:39
    |
-LL |     println!("{:?}",(vfnfer[0] as Fn)(3));
-   |                                   ^^
+LL |     println!("{:?}",(vfnfer[0] as dyn Fn)(3));
+   |                                       ^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29625
    = help: add #![feature(unboxed_closures)] to the crate attributes to enable
 
 error[E0107]: wrong number of type arguments: expected 1, found 0
-  --> $DIR/issue-23024.rs:9:35
+  --> $DIR/issue-23024.rs:9:39
    |
-LL |     println!("{:?}",(vfnfer[0] as Fn)(3));
-   |                                   ^^ expected 1 type argument
+LL |     println!("{:?}",(vfnfer[0] as dyn Fn)(3));
+   |                                       ^^ expected 1 type argument
 
 error[E0191]: the value of the associated type `Output` (from the trait `std::ops::FnOnce`) must be specified
   --> $DIR/issue-23024.rs:9:35
    |
-LL |     println!("{:?}",(vfnfer[0] as Fn)(3));
-   |                                   ^^ associated type `Output` must be specified
+LL |     println!("{:?}",(vfnfer[0] as dyn Fn)(3));
+   |                                   ^^^^^^ associated type `Output` must be specified
 
 error: aborting due to 3 previous errors
 
index a18e85806d918a5922ee593b98282a05ad8318f4..a1371521a0aa03c346e0fc5d704e7cf22a0328b6 100644 (file)
@@ -2,6 +2,6 @@
 fn main()
 {
     fn bar(x:i32) ->i32 { 3*x };
-    let b:Box<Any> = Box::new(bar as fn(_)->_);
+    let b:Box<dyn Any> = Box::new(bar as fn(_)->_);
     b.downcast_ref::<fn(_)->_>(); //~ ERROR E0282
 }
index 898654b7b5967a329cbc80e91f0f7397cf7681e1..a68369616d8b62a32b84bfc9a0e5b2994eae5bc8 100644 (file)
@@ -1,6 +1,6 @@
 pub enum Expr<'var, VAR> {
     Let(Box<Expr<'var, VAR>>,
-        Box<for<'v> Fn(Expr<'v, VAR>) -> Expr<'v, VAR> + 'var>)
+        Box<dyn for<'v> Fn(Expr<'v, VAR>) -> Expr<'v, VAR> + 'var>)
 }
 
 pub fn add<'var, VAR>
index 2b457a57d3ede06f54e2839a3abb8ce02bbc392c..d5f747288627323b0127f557df0c85c05790f5fc 100644 (file)
@@ -1,7 +1,7 @@
 pub struct Struct;
 
 impl Struct {
-    pub fn function(funs: Vec<Fn() -> ()>) {}
+    pub fn function(funs: Vec<dyn Fn() -> ()>) {}
     //~^ ERROR the size for values of type
 }
 
index e540d4e8192428ad76842dba27b045a4539898ca..f1def4745836822a0fa217087e3e932286fc10db 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the size for values of type `(dyn std::ops::Fn() + 'static)` cannot be known at compilation time
   --> $DIR/issue-23281.rs:4:5
    |
-LL |     pub fn function(funs: Vec<Fn() -> ()>) {}
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
+LL |     pub fn function(funs: Vec<dyn Fn() -> ()>) {}
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::ops::Fn() + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index c5e1b49e5ed1cb9245f5e5aa534f9cf8009f1f23..ffd6dfabc2890a1cb7f905485e1812780b86b903 100644 (file)
@@ -1,5 +1,5 @@
 fn main() {
-    static foo: Fn() -> u32 = || -> u32 {
+    static foo: dyn Fn() -> u32 = || -> u32 {
         //~^ ERROR the size for values of type
         0
     };
index ffec73b1ab4a818fea10bc84198e0027a1597607..344443e783038171bfdc1a71a8b6db9ac186a997 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the size for values of type `(dyn std::ops::Fn() -> u32 + 'static)` cannot be known at compilation time
   --> $DIR/issue-24446.rs:2:17
    |
-LL |     static foo: Fn() -> u32 = || -> u32 {
-   |                 ^^^^^^^^^^^ doesn't have a size known at compile-time
+LL |     static foo: dyn Fn() -> u32 = || -> u32 {
+   |                 ^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::ops::Fn() -> u32 + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index 739d571d7275f9d93b384fecfce543f1c59149a6..297f403c05ee7353d21e8d863735ad3bfc250cb1 100644 (file)
@@ -2,6 +2,6 @@
 #![allow(dead_code)]
 #![allow(non_upper_case_globals)]
 
-const x: &'static Fn() = &|| println!("ICE here");
+const x: &'static dyn Fn() = &|| println!("ICE here");
 
 fn main() {}
index 0d9973b45484304fcb27f6acf8bad97a86552fa9..99d43ec792b3c80990a1669eee533b647aeee432 100644 (file)
@@ -17,6 +17,6 @@ impl<K> Map for K {
 
 fn main() {
     let _ = &()
-        as &Map<Key=u32,MapValue=u32>;
+        as &dyn Map<Key=u32,MapValue=u32>;
     //~^ ERROR E0038
 }
index 44fabd0db195aaaaa7cca337a0b844292c8f7696..9c4cf0b18acfe2eccc7302de74d5b14f03fce6b7 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Map` cannot be made into an object
   --> $DIR/issue-26056.rs:20:13
    |
-LL |         as &Map<Key=u32,MapValue=u32>;
-   |             ^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Map` cannot be made into an object
+LL |         as &dyn Map<Key=u32,MapValue=u32>;
+   |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Map` cannot be made into an object
    |
    = note: the trait cannot use `Self` as a type parameter in the supertraits or where-clauses
 
index 0f5ed5caa74cb0a0300a820aba5b98a2bab05022..72fe4286a06b332ff6f4b23e25ff435886bb15bc 100644 (file)
@@ -1,4 +1,4 @@
-fn parse_type(iter: Box<Iterator<Item=&str>+'static>) -> &str { iter.next() }
+fn parse_type(iter: Box<dyn Iterator<Item=&str>+'static>) -> &str { iter.next() }
 //~^ ERROR missing lifetime specifier [E0106]
 
 fn parse_type_2(iter: fn(&u8)->&u8) -> &str { iter() }
index 64c2cd43264d0c83deab5a20161d834ea84ab970..6d7c1b0c43fceb09b4a1e0c6c2b4cc3a924c715d 100644 (file)
@@ -1,8 +1,8 @@
 error[E0106]: missing lifetime specifier
-  --> $DIR/issue-26638.rs:1:58
+  --> $DIR/issue-26638.rs:1:62
    |
-LL | fn parse_type(iter: Box<Iterator<Item=&str>+'static>) -> &str { iter.next() }
-   |                                                          ^ expected lifetime parameter
+LL | fn parse_type(iter: Box<dyn Iterator<Item=&str>+'static>) -> &str { iter.next() }
+   |                                                              ^ expected lifetime parameter
    |
    = help: this function's return type contains a borrowed value, but the signature does not say which one of `iter`'s 2 lifetimes it is borrowed from
 
index efd06219c3decaa3cd2013ee370935973ed060c7..4c5c67d58bc3d6936501578b9cef736713d17209 100644 (file)
@@ -19,5 +19,5 @@ fn main() {
     let data = [1, 2, 3];
     let iter = data.iter();
     let x = MyRc { _ptr: &iter, _boo: NotPhantomData(PhantomData) };
-    let _y: MyRc<Iterator<Item=&u32>> = x;
+    let _y: MyRc<dyn Iterator<Item=&u32>> = x;
 }
index 5f0dff12aec9271dca47e986b4610b084e8eb874..1aafa11768fd36468935bbdd830549c6df77fc3b 100644 (file)
@@ -3,7 +3,7 @@
 use std::rc::Rc;
 
 pub struct Callbacks {
-    callbacks: Vec<Rc<RefCell<FnMut(i32)>>>,
+    callbacks: Vec<Rc<RefCell<dyn FnMut(i32)>>>,
 }
 
 impl Callbacks {
index c770c509859593522b70f626347f0b0f38f66842..fab91160a88be84ee5e0ca2170462b90df94d867 100644 (file)
@@ -2,7 +2,7 @@
 #![allow(dead_code)]
 use std::rc::Rc;
 
-fn test1() -> Rc<for<'a> Fn(&'a usize) + 'static> {
+fn test1() -> Rc<dyn for<'a> Fn(&'a usize) + 'static> {
     if let Some(_) = Some(1) {
         loop{}
     } else {
@@ -10,7 +10,7 @@ fn test1() -> Rc<for<'a> Fn(&'a usize) + 'static> {
     }
 }
 
-fn test2() -> *mut (for<'a> Fn(&'a usize) + 'static) {
+fn test2() -> *mut (dyn for<'a> Fn(&'a usize) + 'static) {
     if let Some(_) = Some(1) {
         loop{}
     } else {
index de665d5aa1680e9aab1563a385891f247b92fdbe..972c839b648032a8f5cdd483e0836f78c0a6a5a8 100644 (file)
@@ -4,7 +4,7 @@ pub trait Foo<RHS=Self> {
 
 pub trait Bar: Foo<Assoc=()> {
     fn new(&self, b: &
-           Bar //~ ERROR the trait `Bar` cannot be made into an object
+           dyn Bar //~ ERROR the trait `Bar` cannot be made into an object
               <Assoc=()>
     );
 }
index cf6174ba857bed80d00eca65db8f5c1fc85412bb..3249d76e69b57d36c6d468d611e46a7851b1e6ce 100644 (file)
@@ -1,7 +1,7 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/issue-28576.rs:7:12
    |
-LL | /            Bar
+LL | /            dyn Bar
 LL | |               <Assoc=()>
    | |________________________^ the trait `Bar` cannot be made into an object
    |
index 7755b7ecee3070f7c0261fee7dcc329355c2f65c..42f71a1b096153d8b0774d81e537f187fe5e45ff 100644 (file)
@@ -55,7 +55,7 @@ fn square_from_char(c: char) -> square {
 
 fn read_board_grid<rdr:'static + Read>(mut input: rdr)
                    -> Vec<Vec<square>> {
-    let mut input: &mut Read = &mut input;
+    let mut input: &mut dyn Read = &mut input;
     let mut grid = Vec::new();
     let mut line = [0; 10];
     input.read(&mut line);
index be59d3522b865d228580f1c92eee6785d3b835db..ee099069f02414152b8ddfb3654ef6d80a3ebd08 100644 (file)
@@ -5,7 +5,7 @@ trait Misc {}
 fn size_of_copy<T: Copy+?Sized>() -> usize { mem::size_of::<T>() }
 
 fn main() {
-    size_of_copy::<Misc+Copy>();
+    size_of_copy::<dyn Misc + Copy>();
     //~^ ERROR only auto traits can be used as additional traits in a trait object
     //~| ERROR the trait bound `dyn Misc: std::marker::Copy` is not satisfied
 }
index cde4123dc3f40a462cd3b5b35d751803e99313cc..a31a74a07f46e56241c3da905c2f326e233f8a88 100644 (file)
@@ -1,19 +1,19 @@
 error[E0225]: only auto traits can be used as additional traits in a trait object
-  --> $DIR/issue-32963.rs:8:25
+  --> $DIR/issue-32963.rs:8:31
    |
-LL |     size_of_copy::<Misc+Copy>();
-   |                    ---- ^^^^
-   |                    |    |
-   |                    |    additional non-auto trait
-   |                    |    trait alias used in trait object type (additional use)
-   |                    first non-auto trait
-   |                    trait alias used in trait object type (first use)
+LL |     size_of_copy::<dyn Misc + Copy>();
+   |                        ----   ^^^^
+   |                        |      |
+   |                        |      additional non-auto trait
+   |                        |      trait alias used in trait object type (additional use)
+   |                        first non-auto trait
+   |                        trait alias used in trait object type (first use)
 
 error[E0277]: the trait bound `dyn Misc: std::marker::Copy` is not satisfied
   --> $DIR/issue-32963.rs:8:5
    |
-LL |     size_of_copy::<Misc+Copy>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `dyn Misc`
+LL |     size_of_copy::<dyn Misc + Copy>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `dyn Misc`
    |
 note: required by `size_of_copy`
   --> $DIR/issue-32963.rs:5:1
index c32fb63f1e5845a9c0ca18815f3516668ca58fe1..3526deffc79ab075dbecc1a2c7ba00f6b3806eb0 100644 (file)
@@ -17,11 +17,11 @@ fn main() {
     //~^ ERROR parenthesized type parameters may only be used with a `Fn` trait
     //~| WARN previously accepted
 
-    let o : Box<::std::marker()::Send> = Box::new(1);
+    let o : Box<dyn (::std::marker()::Send)> = Box::new(1);
     //~^ ERROR parenthesized type parameters may only be used with a `Fn` trait
     //~| WARN previously accepted
 
-    let o : Box<Send + ::std::marker()::Sync> = Box::new(1);
+    let o : Box<dyn Send + ::std::marker()::Sync> = Box::new(1);
     //~^ ERROR parenthesized type parameters may only be used with a `Fn` trait
     //~| WARN previously accepted
 }
index 97b4b7fa76ca81354b7e6c6b89ce02923501a68a..f97d86f6522abeeca8d0ea6ab103ee6a8c547257 100644 (file)
@@ -36,19 +36,19 @@ LL |     let p = ::std::str::from_utf8::()(b"foo").unwrap();
    = note: for more information, see issue #42238 <https://github.com/rust-lang/rust/issues/42238>
 
 error: parenthesized type parameters may only be used with a `Fn` trait
-  --> $DIR/issue-32995.rs:20:30
+  --> $DIR/issue-32995.rs:20:35
    |
-LL |     let o : Box<::std::marker()::Send> = Box::new(1);
-   |                              ^^
+LL |     let o : Box<dyn (::std::marker()::Send)> = Box::new(1);
+   |                                   ^^
    |
    = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
    = note: for more information, see issue #42238 <https://github.com/rust-lang/rust/issues/42238>
 
 error: parenthesized type parameters may only be used with a `Fn` trait
-  --> $DIR/issue-32995.rs:24:37
+  --> $DIR/issue-32995.rs:24:41
    |
-LL |     let o : Box<Send + ::std::marker()::Sync> = Box::new(1);
-   |                                     ^^
+LL |     let o : Box<dyn Send + ::std::marker()::Sync> = Box::new(1);
+   |                                         ^^
    |
    = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
    = note: for more information, see issue #42238 <https://github.com/rust-lang/rust/issues/42238>
index 2b644817df1158272ad890c6a34bf0c2fc3664d6..078f3f3dd2cd22aa9e0703363e37d46c00c0bf4c 100644 (file)
 /// Implementations for all traits in std are provided.
 pub unsafe trait Trait {}
 
-unsafe impl Trait for ::std::any::Any + Send { }
-unsafe impl Trait for ::std::any::Any + Sync { }
-unsafe impl Trait for ::std::any::Any + Send + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::Borrow<T> + Send { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::Borrow<T> + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::Borrow<T> + Send + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::BorrowMut<T> + Send { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::BorrowMut<T> + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::borrow::BorrowMut<T> + Send + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsMut<T> + Send { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsMut<T> + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsMut<T> + Send + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsRef<T> + Send { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsRef<T> + Sync { }
-unsafe impl<T: ?Sized> Trait for ::std::convert::AsRef<T> + Send + Sync { }
-unsafe impl Trait for ::std::error::Error + Send { }
-unsafe impl Trait for ::std::error::Error + Sync { }
-unsafe impl Trait for ::std::error::Error + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Binary + Send { }
-unsafe impl Trait for ::std::fmt::Binary + Sync { }
-unsafe impl Trait for ::std::fmt::Binary + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Debug + Send { }
-unsafe impl Trait for ::std::fmt::Debug + Sync { }
-unsafe impl Trait for ::std::fmt::Debug + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Display + Send { }
-unsafe impl Trait for ::std::fmt::Display + Sync { }
-unsafe impl Trait for ::std::fmt::Display + Send + Sync { }
-unsafe impl Trait for ::std::fmt::LowerExp + Send { }
-unsafe impl Trait for ::std::fmt::LowerExp + Sync { }
-unsafe impl Trait for ::std::fmt::LowerExp + Send + Sync { }
-unsafe impl Trait for ::std::fmt::LowerHex + Send { }
-unsafe impl Trait for ::std::fmt::LowerHex + Sync { }
-unsafe impl Trait for ::std::fmt::LowerHex + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Octal + Send { }
-unsafe impl Trait for ::std::fmt::Octal + Sync { }
-unsafe impl Trait for ::std::fmt::Octal + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Pointer + Send { }
-unsafe impl Trait for ::std::fmt::Pointer + Sync { }
-unsafe impl Trait for ::std::fmt::Pointer + Send + Sync { }
-unsafe impl Trait for ::std::fmt::UpperExp + Send { }
-unsafe impl Trait for ::std::fmt::UpperExp + Sync { }
-unsafe impl Trait for ::std::fmt::UpperExp + Send + Sync { }
-unsafe impl Trait for ::std::fmt::UpperHex + Send { }
-unsafe impl Trait for ::std::fmt::UpperHex + Sync { }
-unsafe impl Trait for ::std::fmt::UpperHex + Send + Sync { }
-unsafe impl Trait for ::std::fmt::Write + Send { }
-unsafe impl Trait for ::std::fmt::Write + Sync { }
-unsafe impl Trait for ::std::fmt::Write + Send + Sync { }
-unsafe impl Trait for ::std::hash::Hasher + Send { }
-unsafe impl Trait for ::std::hash::Hasher + Sync { }
-unsafe impl Trait for ::std::hash::Hasher + Send + Sync { }
-unsafe impl Trait for ::std::io::BufRead + Send { }
-unsafe impl Trait for ::std::io::BufRead + Sync { }
-unsafe impl Trait for ::std::io::BufRead + Send + Sync { }
-unsafe impl Trait for ::std::io::Read + Send { }
-unsafe impl Trait for ::std::io::Read + Sync { }
-unsafe impl Trait for ::std::io::Read + Send + Sync { }
-unsafe impl Trait for ::std::io::Seek + Send { }
-unsafe impl Trait for ::std::io::Seek + Sync { }
-unsafe impl Trait for ::std::io::Seek + Send + Sync { }
-unsafe impl Trait for ::std::io::Write + Send { }
-unsafe impl Trait for ::std::io::Write + Sync { }
-unsafe impl Trait for ::std::io::Write + Send + Sync { }
-unsafe impl<T, I> Trait for ::std::iter::IntoIterator<IntoIter=I, Item=T> { }
-unsafe impl<T> Trait for ::std::iter::Iterator<Item=T> + Send { }
-unsafe impl<T> Trait for ::std::iter::Iterator<Item=T> + Sync { }
-unsafe impl<T> Trait for ::std::iter::Iterator<Item=T> + Send + Sync { }
-unsafe impl Trait for ::std::marker::Send + Send { }
-unsafe impl Trait for ::std::marker::Send + Sync { }
-unsafe impl Trait for ::std::marker::Send + Send + Sync { }
-unsafe impl Trait for ::std::marker::Sync + Send { }
-unsafe impl Trait for ::std::marker::Sync + Sync { }
-unsafe impl Trait for ::std::marker::Sync + Send + Sync { }
-unsafe impl Trait for ::std::ops::Drop + Send { }
-unsafe impl Trait for ::std::ops::Drop + Sync { }
-unsafe impl Trait for ::std::ops::Drop + Send + Sync { }
-unsafe impl Trait for ::std::string::ToString + Send { }
-unsafe impl Trait for ::std::string::ToString + Sync { }
-unsafe impl Trait for ::std::string::ToString + Send + Sync { }
+unsafe impl Trait for dyn (::std::any::Any) + Send { }
+unsafe impl Trait for dyn (::std::any::Any) + Sync { }
+unsafe impl Trait for dyn (::std::any::Any) + Send + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::Borrow<T>) + Send { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::Borrow<T>) + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::Borrow<T>) + Send + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::BorrowMut<T>) + Send { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::BorrowMut<T>) + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::borrow::BorrowMut<T>) + Send + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsMut<T>) + Send { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsMut<T>) + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsMut<T>) + Send + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsRef<T>) + Send { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsRef<T>) + Sync { }
+unsafe impl<T: ?Sized> Trait for dyn (::std::convert::AsRef<T>) + Send + Sync { }
+unsafe impl Trait for dyn (::std::error::Error) + Send { }
+unsafe impl Trait for dyn (::std::error::Error) + Sync { }
+unsafe impl Trait for dyn (::std::error::Error) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Binary) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Binary) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Binary) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Debug) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Debug) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Debug) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Display) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Display) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Display) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::LowerExp) + Send { }
+unsafe impl Trait for dyn (::std::fmt::LowerExp) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::LowerExp) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::LowerHex) + Send { }
+unsafe impl Trait for dyn (::std::fmt::LowerHex) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::LowerHex) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Octal) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Octal) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Octal) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Pointer) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Pointer) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Pointer) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::UpperExp) + Send { }
+unsafe impl Trait for dyn (::std::fmt::UpperExp) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::UpperExp) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::UpperHex) + Send { }
+unsafe impl Trait for dyn (::std::fmt::UpperHex) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::UpperHex) + Send + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Write) + Send { }
+unsafe impl Trait for dyn (::std::fmt::Write) + Sync { }
+unsafe impl Trait for dyn (::std::fmt::Write) + Send + Sync { }
+unsafe impl Trait for dyn (::std::hash::Hasher) + Send { }
+unsafe impl Trait for dyn (::std::hash::Hasher) + Sync { }
+unsafe impl Trait for dyn (::std::hash::Hasher) + Send + Sync { }
+unsafe impl Trait for dyn (::std::io::BufRead) + Send { }
+unsafe impl Trait for dyn (::std::io::BufRead) + Sync { }
+unsafe impl Trait for dyn (::std::io::BufRead) + Send + Sync { }
+unsafe impl Trait for dyn (::std::io::Read) + Send { }
+unsafe impl Trait for dyn (::std::io::Read) + Sync { }
+unsafe impl Trait for dyn (::std::io::Read) + Send + Sync { }
+unsafe impl Trait for dyn (::std::io::Seek) + Send { }
+unsafe impl Trait for dyn (::std::io::Seek) + Sync { }
+unsafe impl Trait for dyn (::std::io::Seek) + Send + Sync { }
+unsafe impl Trait for dyn (::std::io::Write) + Send { }
+unsafe impl Trait for dyn (::std::io::Write) + Sync { }
+unsafe impl Trait for dyn (::std::io::Write) + Send + Sync { }
+unsafe impl<T, I> Trait for dyn (::std::iter::IntoIterator<IntoIter=I, Item=T>) { }
+unsafe impl<T> Trait for dyn (::std::iter::Iterator<Item=T>) + Send { }
+unsafe impl<T> Trait for dyn (::std::iter::Iterator<Item=T>) + Sync { }
+unsafe impl<T> Trait for dyn (::std::iter::Iterator<Item=T>) + Send + Sync { }
+unsafe impl Trait for dyn (::std::marker::Send) + Send { }
+unsafe impl Trait for dyn (::std::marker::Send) + Sync { }
+unsafe impl Trait for dyn (::std::marker::Send) + Send + Sync { }
+unsafe impl Trait for dyn (::std::marker::Sync) + Send { }
+unsafe impl Trait for dyn (::std::marker::Sync) + Sync { }
+unsafe impl Trait for dyn (::std::marker::Sync) + Send + Sync { }
+unsafe impl Trait for dyn (::std::ops::Drop) + Send { }
+unsafe impl Trait for dyn (::std::ops::Drop) + Sync { }
+unsafe impl Trait for dyn (::std::ops::Drop) + Send + Sync { }
+unsafe impl Trait for dyn (::std::string::ToString) + Send { }
+unsafe impl Trait for dyn (::std::string::ToString) + Sync { }
+unsafe impl Trait for dyn (::std::string::ToString) + Send + Sync { }
 fn assert_trait<T: Trait + ?Sized>() {}
 
 fn main() {
index 6f71e79d0ee7a69595ef5a6102f76a56d9b49300..76db98aa38bb437a3523eacb664c17ac93b7c391 100644 (file)
@@ -1,10 +1,10 @@
 warning: conflicting implementations of trait `Trait` for type `(dyn std::marker::Send + std::marker::Sync + 'static)`: (E0119)
   --> $DIR/issue-33140-traitobject-crate.rs:85:1
    |
-LL | unsafe impl Trait for ::std::marker::Send + Sync { }
-   | ------------------------------------------------ first implementation here
-LL | unsafe impl Trait for ::std::marker::Send + Send + Sync { }
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
+LL | unsafe impl Trait for dyn (::std::marker::Send) + Sync { }
+   | ------------------------------------------------------ first implementation here
+LL | unsafe impl Trait for dyn (::std::marker::Send) + Send + Sync { }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
    |
 note: lint level defined here
   --> $DIR/issue-33140-traitobject-crate.rs:3:9
@@ -17,10 +17,10 @@ LL | #![warn(order_dependent_trait_objects)]
 warning: conflicting implementations of trait `Trait` for type `(dyn std::marker::Send + std::marker::Sync + 'static)`: (E0119)
   --> $DIR/issue-33140-traitobject-crate.rs:86:1
    |
-LL | unsafe impl Trait for ::std::marker::Send + Send + Sync { }
-   | ------------------------------------------------------- first implementation here
-LL | unsafe impl Trait for ::std::marker::Sync + Send { }
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
+LL | unsafe impl Trait for dyn (::std::marker::Send) + Send + Sync { }
+   | ------------------------------------------------------------- first implementation here
+LL | unsafe impl Trait for dyn (::std::marker::Sync) + Send { }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
    |
    = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
    = note: for more information, see issue #56484 <https://github.com/rust-lang/rust/issues/56484>
@@ -28,11 +28,11 @@ LL | unsafe impl Trait for ::std::marker::Sync + Send { }
 warning: conflicting implementations of trait `Trait` for type `(dyn std::marker::Send + std::marker::Sync + 'static)`: (E0119)
   --> $DIR/issue-33140-traitobject-crate.rs:88:1
    |
-LL | unsafe impl Trait for ::std::marker::Sync + Send { }
-   | ------------------------------------------------ first implementation here
-LL | unsafe impl Trait for ::std::marker::Sync + Sync { }
-LL | unsafe impl Trait for ::std::marker::Sync + Send + Sync { }
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
+LL | unsafe impl Trait for dyn (::std::marker::Sync) + Send { }
+   | ------------------------------------------------------ first implementation here
+LL | unsafe impl Trait for dyn (::std::marker::Sync) + Sync { }
+LL | unsafe impl Trait for dyn (::std::marker::Sync) + Send + Sync { }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(dyn std::marker::Send + std::marker::Sync + 'static)`
    |
    = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
    = note: for more information, see issue #56484 <https://github.com/rust-lang/rust/issues/56484>
index 930e24218ac72a49319065d5ac344c6be2f05363..9bdac4b8375c265bdcb41f1b3c5f9a1a2fdbdeb9 100644 (file)
@@ -38,10 +38,10 @@ fn abc() -> bool {
 }
 
 fn main() {
-    assert_eq!(<Send+Sync>::xyz(), false);
-    assert_eq!(<Sync+Send>::xyz(), true);
-    assert_eq!(<Send+Sync>::uvw(), false);
-    assert_eq!(<Sync+Send+Sync>::uvw(), true);
-    assert_eq!(<Foo<Send+Sync>>::abc(), false);
-    assert_eq!(<Foo<Sync+Send>>::abc(), true);
+    assert_eq!(<dyn Send + Sync>::xyz(), false);
+    assert_eq!(<dyn Sync + Send>::xyz(), true);
+    assert_eq!(<dyn Send + Sync>::uvw(), false);
+    assert_eq!(<dyn Sync + Send+ Sync>::uvw(), true);
+    assert_eq!(<Foo<dyn Send + Sync>>::abc(), false);
+    assert_eq!(<Foo<dyn Sync + Send>>::abc(), true);
 }
index 4c5052a60d3f38d5871597f2ecaca4e696805c93..4d6204cb28832e88a5fd96b8c1fcce8c2763d3bb 100644 (file)
@@ -9,6 +9,6 @@ fn any<T>() -> T { unreachable!() }
 
 
 fn main() {
-    let t: &(u8, fmt::Debug) = any();
+    let t: &(u8, dyn fmt::Debug) = any();
     println!("{:?}", &t.1);
 }
index a9ba5f5408bdb1a0ac3d03684c60d4c8df41c1dd..19f9f13e14416af5fe32b1ea16e5a30ca49403d0 100644 (file)
@@ -5,7 +5,7 @@
 
 pub struct Path;
 
-type rsrc_loader = Box<FnMut(&Path) -> Result<String, String>>;
+type rsrc_loader = Box<dyn FnMut(&Path) -> Result<String, String>>;
 
 fn tester()
 {
index 1ee00fc7ec2d94049a298395418a186bccd5c3f9..e462f3543735805893e1a1aa680a4bc91ccac45e 100644 (file)
@@ -7,14 +7,14 @@ pub trait MethodType {
 pub struct MTFn;
 
 impl<'a> MethodType for MTFn { //~ ERROR E0207
-    type GetProp = fmt::Debug + 'a;
+    type GetProp = dyn fmt::Debug + 'a;
 }
 
-fn bad(a: Box<<MTFn as MethodType>::GetProp>) -> Box<fmt::Debug+'static> {
+fn bad(a: Box<<MTFn as MethodType>::GetProp>) -> Box<dyn fmt::Debug+'static> {
     a
 }
 
-fn dangling(a: &str) -> Box<fmt::Debug> {
+fn dangling(a: &str) -> Box<dyn fmt::Debug> {
     bad(Box::new(a))
 }
 
index 19c0491e4bc2981a4e7dfb403f6f19af38c3b28c..500ba48e0b71c3103c7ce76d51ad02fad940e7e4 100644 (file)
@@ -6,11 +6,11 @@
 // `value` field of `Node<Send>`).
 
 struct Node<T: ?Sized + Send> {
-    next: Option<Box<Node<Send>>>,
+    next: Option<Box<Node<dyn Send>>>,
     value: T,
 }
 
-fn clear(head: &mut Option<Box<Node<Send>>>) {
+fn clear(head: &mut Option<Box<Node<dyn Send>>>) {
     match head.take() {
         Some(node) => *head = node.next,
         None => (),
index e809b46bcdca5975693c3291f16d0b1614a72c01..9bb9db63951c36506dbbc32f3d14f3506ef7e3e7 100644 (file)
@@ -8,7 +8,7 @@ trait Trait2<'a> {
   type Ty;
 }
 
-fn _ice(param: Box<for <'a> Trait1<<() as Trait2<'a>>::Ty>>) {
+fn _ice(param: Box<dyn for <'a> Trait1<<() as Trait2<'a>>::Ty>>) {
     let _e: (usize, usize) = unsafe{mem::transmute(param)};
 }
 
index 95c0cc95bb2baa5e85c6f17478303e449c236d19..d075794d9946fe40da855c4234695fbb230c95fd 100644 (file)
@@ -3,14 +3,14 @@ pub trait Future {
         fn wait(&self) where Self: Sized;
     }
 
-    impl Future for Box<Future> {
+    impl Future for Box<dyn Future> {
         fn wait(&self) { }
     }
 }
 
 //use private::Future;
 
-fn bar(arg: Box<private::Future>) {
+fn bar(arg: Box<dyn private::Future>) {
     arg.wait();
     //~^ ERROR the `wait` method cannot be invoked on a trait object
 }
index c76c183821e522c64614c6e10d54876d65a112ef..9bccb2a21e33c3ac700cd22e5ae2016f41847bb3 100644 (file)
@@ -6,7 +6,7 @@
 use std::sync::mpsc::Sender;
 
 type RingBuffer = Vec<f64> ;
-type SamplesFn = Box<FnMut(&RingBuffer) + Send>;
+type SamplesFn = Box<dyn FnMut(&RingBuffer) + Send>;
 
 enum Msg
 {
index 0944d07896e570828b42ed3efa4a31f62551302c..a660368f40153ef3036ab72e81ffdbc4e17f60aa 100644 (file)
@@ -19,5 +19,5 @@ fn broken(&self) where Self::Assoc: Foo {
 
 
 fn main() {
-    let _m: &Broken<Assoc=()> = &();
+    let _m: &dyn Broken<Assoc=()> = &();
 }
index c3a92a23cef50dc087694e66578c162340013e33..d47f6d248f708772140b76491316fbd44b02f124 100644 (file)
@@ -7,12 +7,12 @@ impl ToPrimitive for isize {}
 
 trait Add {
     fn to_int(&self) -> isize;
-    fn add_dynamic(&self, other: &Add) -> isize;
+    fn add_dynamic(&self, other: &dyn Add) -> isize;
 }
 
 impl Add for isize {
     fn to_int(&self) -> isize { *self }
-    fn add_dynamic(&self, other: &Add) -> isize {
+    fn add_dynamic(&self, other: &dyn Add) -> isize {
         self.to_int() + other.to_int() //~ ERROR multiple applicable items in scope
     }
 }
index 090b9bbf1ec49f13d642c0166601e031380f79e2..cc07bd1d91509bba0c914685eca7218cfbeba34b 100644 (file)
@@ -2,7 +2,7 @@
 // compile-pass
 #![warn(unused)]
 
-type Z = for<'x> Send;
+type Z = dyn for<'x> Send;
 //~^ WARN type alias is never used
 
 
index 1b4965594848b40f48eaa5fc00b2dc0a78d8ac47..1476d17cdc6424b9ebfb184774ba374b6b5e5721 100644 (file)
@@ -1,8 +1,8 @@
 warning: type alias is never used: `Z`
   --> $DIR/issue-37515.rs:5:1
    |
-LL | type Z = for<'x> Send;
-   | ^^^^^^^^^^^^^^^^^^^^^^
+LL | type Z = dyn for<'x> Send;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: lint level defined here
   --> $DIR/issue-37515.rs:3:9
index cddd75e267c42b96e1f2cd6a358e4b38c58b03c7..1a92acc34042b0f8f9f0b3f440a0e81ede2dfe78 100644 (file)
@@ -1,6 +1,6 @@
 trait A<T>: std::ops::Add<Self> + Sized {}
 trait B<T>: A<T> {}
-trait C<T>: A<B<T, Output=usize>> {}
+trait C<T>: A<dyn B<T, Output=usize>> {}
 //~^ ERROR the trait `B` cannot be made into an object
 
 fn main() {}
index 06bcf220f18366b453f67745e8d1c0f52bd8007e..d18a26b3a76382ca55fc0eb58590dc62404a3e18 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `B` cannot be made into an object
   --> $DIR/issue-38404.rs:3:15
    |
-LL | trait C<T>: A<B<T, Output=usize>> {}
-   |               ^^^^^^^^^^^^^^^^^^ the trait `B` cannot be made into an object
+LL | trait C<T>: A<dyn B<T, Output=usize>> {}
+   |               ^^^^^^^^^^^^^^^^^^^^^^ the trait `B` cannot be made into an object
    |
    = note: the trait cannot use `Self` as a type parameter in the supertraits or where-clauses
 
index c172595a245cd0ce960f50876141264413c05e92..002a3c43fcba6a7ce51f061ea72f8a87e2c68915 100644 (file)
@@ -11,6 +11,6 @@ fn foo(&self) {
 }
 
 fn main() {
-    let _f: Box<Foo> = //~ ERROR `Foo` cannot be made into an object
+    let _f: Box<dyn Foo> = //~ ERROR `Foo` cannot be made into an object
         Box::new(()); //~ ERROR `Foo` cannot be made into an object
 }
index 77b42b80613c3e569c5b5b0e36c9505fc20e2237..8ef7d346cb3318623db57c3a714ab119b4828156 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/issue-38604.rs:14:13
    |
-LL |     let _f: Box<Foo> =
-   |             ^^^^^^^^ the trait `Foo` cannot be made into an object
+LL |     let _f: Box<dyn Foo> =
+   |             ^^^^^^^^^^^^ the trait `Foo` cannot be made into an object
    |
    = note: the trait cannot use `Self` as a type parameter in the supertraits or where-clauses
 
index 320992c0764cfd4a3a87200e1c8e970b62c2d5b3..9d5ef481afc37cce1fec1105e9e9845fb6a2bb76 100644 (file)
@@ -1,7 +1,7 @@
 fn main() {
     let bar: fn(&mut u32) = |_| {};
 
-    fn foo(x: Box<Fn(&i32)>) {}
-    let bar = Box::new(|x: &i32| {}) as Box<Fn(_)>;
+    fn foo(x: Box<dyn Fn(&i32)>) {}
+    let bar = Box::new(|x: &i32| {}) as Box<dyn Fn(_)>;
     foo(bar); //~ ERROR E0308
 }
index f3e6c44ecb921e457b68f0fc40c6cc4ae6b7af9e..4814232607cf8d16a7d1f98554bd39641506aa18 100644 (file)
@@ -1,8 +1,8 @@
 trait Trait {}
 
-fn get_function<'a>() -> &'a Fn() -> Trait { panic!("") }
+fn get_function<'a>() -> &'a dyn Fn() -> dyn Trait { panic!("") }
 
 fn main() {
-    let t : &Trait = &get_function()();
+    let t : &dyn Trait = &get_function()();
     //~^ ERROR cannot move a value of type dyn Trait
 }
index 4dd017b0a919149655fc96323907e84168f46edb..829d0cfa72ca704d77af2279230d67993ea7448f 100644 (file)
@@ -1,8 +1,8 @@
 error[E0161]: cannot move a value of type dyn Trait: the size of dyn Trait cannot be statically determined
-  --> $DIR/issue-41139.rs:6:23
+  --> $DIR/issue-41139.rs:6:27
    |
-LL |     let t : &Trait = &get_function()();
-   |                       ^^^^^^^^^^^^^^^^
+LL |     let t : &dyn Trait = &get_function()();
+   |                           ^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index b1c651f665b72005b54f8b3e9934cb36a1e17c5e..426efcbf9b16f8292cdf6c82d1044f9147127f97 100644 (file)
@@ -5,7 +5,7 @@ fn baz(_: Self::Target) where Self: Deref {}
     //~^ ERROR the size for values of type
 }
 
-pub fn f(_: ToString) {}
+pub fn f(_: dyn ToString) {}
 //~^ ERROR the size for values of type
 
 fn main() { }
index 20c8d085cbc62f375edf8848316bb7c53ca5a928..bfdc4272fb3089d1550ca3459f5b16bf524a72f2 100644 (file)
@@ -11,10 +11,10 @@ LL |     fn baz(_: Self::Target) where Self: Deref {}
    = help: unsized locals are gated as an unstable feature
 
 error[E0277]: the size for values of type `(dyn std::string::ToString + 'static)` cannot be known at compilation time
-  --> $DIR/issue-42312.rs:8:23
+  --> $DIR/issue-42312.rs:8:27
    |
-LL | pub fn f(_: ToString) {}
-   |                       ^ doesn't have a size known at compile-time
+LL | pub fn f(_: dyn ToString) {}
+   |                           ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn std::string::ToString + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index d3c9954cdb05161afc57c808c723ac6cb5e590fe..a10ae9a1243a211256faaf09132a2aa74a45444c 100644 (file)
@@ -2,7 +2,7 @@
 
 fn id<T>(t: T) -> T { t }
 
-fn f<'r, T>(v: &'r T) -> Box<FnMut() -> T + 'r> {
+fn f<'r, T>(v: &'r T) -> Box<dyn FnMut() -> T + 'r> {
     id(Box::new(|| *v))
         //~^ ERROR E0373
         //~| ERROR E0507
index 1b5cab249291b5d05451c73a645dc01046e00e5e..f1b6e475949dc8224ed122ca039392850a5d5079 100644 (file)
@@ -1,7 +1,7 @@
 error[E0507]: cannot move out of captured variable in an `FnMut` closure
   --> $DIR/issue-4335.rs:6:20
    |
-LL | fn f<'r, T>(v: &'r T) -> Box<FnMut() -> T + 'r> {
+LL | fn f<'r, T>(v: &'r T) -> Box<dyn FnMut() -> T + 'r> {
    |             - captured outer variable
 LL |     id(Box::new(|| *v))
    |                    ^^ cannot move out of captured variable in an `FnMut` closure
index 5709125e5f01b3300197850bb621b46579c6dbdc..3776759fe07a5967c142572642a574e09415ae8e 100644 (file)
@@ -3,7 +3,7 @@ fn main() {
     let x: *const _ = 0 as _; //~ ERROR cannot cast
 
     let x: *const _ = 0 as *const _; //~ ERROR cannot cast
-    let y: Option<*const fmt::Debug> = Some(x) as _;
+    let y: Option<*const dyn fmt::Debug> = Some(x) as _;
 
     let x = 0 as *const i32 as *const _ as *mut _; //~ ERROR cannot cast
 }
index 9c95a9794766bd18f5101b817d4a134bbdb2ebfc..fab258f137e68c66f683a3d6b34a7ca002ec4aa8 100644 (file)
@@ -6,10 +6,10 @@ fn dummy(&self) {}
 }
 
 pub enum TraitWrapper {
-    A(Box<MyTrait+'static>),
+    A(Box<dyn MyTrait + 'static>),
 }
 
-fn get_tw_map(tw: &TraitWrapper) -> &MyTrait {
+fn get_tw_map(tw: &TraitWrapper) -> &dyn MyTrait {
     match *tw {
         TraitWrapper::A(box ref map) => map, //~ ERROR cannot be dereferenced
     }
index bcf3ebcd60a5e201a848bd7a3df865134b4b82e1..70b4bc8b755aac7b31cb97c2de2655c354ac2736 100644 (file)
@@ -14,7 +14,7 @@ pub fn new() -> Builder {
     }
 
     impl Builder {
-        pub fn with_a(&mut self, _a: fn() -> ::a::A) {}
+        pub fn with_a(&mut self, _a: fn() -> dyn (::a::A)) {}
     }
 }
 
index edf8d82b48050b94aeed931a5b761f2a2331c2ff..3c5e5a9f69af0a61bb32c76994efba55b7f31168 100644 (file)
@@ -15,5 +15,5 @@ impl Trait for dyn X {}
 
 pub fn main() {
     // Check that this does not segfault.
-    <X as X>::foo(&());
+    <dyn X as X>::foo(&());
 }
index 551880ae009fb3f762b0aadec7097bfda1cd3787..e6737662088f2081e569a6f595aaa16886cc4186 100644 (file)
@@ -7,6 +7,6 @@ fn foo(self: Box<isize>) { }
 }
 
 fn main() {
-    (&5isize as &Foo).foo();
+    (&5isize as &dyn Foo).foo();
     //~^ ERROR: no method named `foo` found for type `&dyn Foo` in the current scope
 }
index 48adfee0dec0352f81251e33839ec328286e78a4..97214fbdc52d404b82c958b6ece9700e5902fe71 100644 (file)
@@ -1,8 +1,8 @@
 error[E0599]: no method named `foo` found for type `&dyn Foo` in the current scope
-  --> $DIR/issue-5153.rs:10:23
+  --> $DIR/issue-5153.rs:10:27
    |
-LL |     (&5isize as &Foo).foo();
-   |                       ^^^
+LL |     (&5isize as &dyn Foo).foo();
+   |                           ^^^
    |
    = help: items from traits can only be used if the trait is implemented and in scope
    = note: the following trait defines an item `foo`, perhaps you need to implement it:
index fd490884fa1fcf2e16aa9df947e49b6d1a59e701..35b343edfbdbe870c23a63f1828936983106b212 100644 (file)
@@ -1,10 +1,10 @@
 fn f() { }
-struct S(Box<FnMut()>);
+struct S(Box<dyn FnMut()>);
 pub static C: S = S(f); //~ ERROR mismatched types
 
 
 fn g() { }
-type T = Box<FnMut()>;
+type T = Box<dyn FnMut()>;
 pub static D: T = g; //~ ERROR mismatched types
 
 fn main() {}
index 52149cf486dc9b394b55fbb154ad9328d13508b8..bf6791734d4e23179e253f4093795fff8a1ffa4d 100644 (file)
@@ -1,7 +1,7 @@
 //compile-pass
 
 struct Foo {
-    bar: for<'r> Fn(usize, &'r FnMut())
+    bar: dyn for<'r> Fn(usize, &'r dyn FnMut())
 }
 
 fn main() {
index c2dbf361911b5826c6045705ba4abfba561f7d0e..8c50cac67f8fc4a347435b2363d382c0ce0bcdc5 100644 (file)
@@ -9,7 +9,7 @@ pub enum Enum {
 
 impl Stage for Enum {}
 
-pub static ARRAY: [(&Stage, &str); 1] = [
+pub static ARRAY: [(&dyn Stage, &str); 1] = [
     (&Enum::A, ""),
 ];
 
index efdea5c9b1e16e44c2cd536a99f12ab4f641aa78..088d4301c51b1acf8eaeb5575c8a51a12eee0d0b 100644 (file)
@@ -12,12 +12,12 @@ pub trait Graph<'a> {
     fn out_edges(&'a self, u: &Self::Node) -> Self::EdgesIter;
     fn in_edges(&'a self, u: &Self::Node) -> Self::EdgesIter;
 
-    fn out_neighbors(&'a self, u: &Self::Node) -> Box<Iterator<Item = Self::Node>> {
+    fn out_neighbors(&'a self, u: &Self::Node) -> Box<dyn Iterator<Item = Self::Node>> {
         Box::new(self.out_edges(u).map(|e| e.target()))
 //~^ ERROR cannot infer
     }
 
-    fn in_neighbors(&'a self, u: &Self::Node) -> Box<Iterator<Item = Self::Node>> {
+    fn in_neighbors(&'a self, u: &Self::Node) -> Box<dyn Iterator<Item = Self::Node>> {
         Box::new(self.in_edges(u).map(|e| e.target()))
 //~^ ERROR cannot infer
     }
index b4a73ba99c5744673e7ec277007bbd35223a384a..0de535023972e0d80869bc0c07e93a127f497618 100644 (file)
@@ -1,10 +1,10 @@
 trait A {}
 
 struct Struct {
-    r: A+'static
+    r: dyn A + 'static
 }
 
-fn new_struct(r: A+'static)
+fn new_struct(r: dyn A + 'static)
     -> Struct { //~^ ERROR the size for values of type
     //~^ ERROR the size for values of type
     Struct { r: r }
index 7753881f73684e06dc57f982c712149c1622822d..c2de1d095505a462765725ca9a118f481204d953 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: the size for values of type `(dyn A + 'static)` cannot be known at compilation time
   --> $DIR/issue-5883.rs:7:15
    |
-LL | fn new_struct(r: A+'static)
+LL | fn new_struct(r: dyn A + 'static)
    |               ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn A + 'static)`
index 930e98bedce8a08b53399f3c4c72c5d0ab3ce2a2..6dae1e1347b7a402263dff8570ac2bdc31e0061d 100644 (file)
@@ -13,6 +13,6 @@ fn main() {
     //~^ ERROR type arguments are not allowed for this type
 
     let c1 = A {};
-    c1::<Into<B>>;
+    c1::<dyn Into<B>>;
     //~^ ERROR type arguments are not allowed for this type
 }
index 55a0b9626df752c0ba561e42d2f6d6179c564d04..5d2d9e83c9b9c2d5f5b628df0f495e15922bd0d9 100644 (file)
@@ -7,8 +7,8 @@ LL |     c1::<()>;
 error[E0109]: type arguments are not allowed for this type
   --> $DIR/issue-60989.rs:16:10
    |
-LL |     c1::<Into<B>>;
-   |          ^^^^^^^ type argument not allowed
+LL |     c1::<dyn Into<B>>;
+   |          ^^^^^^^^^^^ type argument not allowed
 
 error: aborting due to 2 previous errors
 
index ee68aa8623b376592e3e11d90413762f33f8cedd..3d72b67e391c9674fa5a49fbbc956c72e51c8938 100644 (file)
@@ -19,10 +19,10 @@ fn set(&mut self, v: Rc<RefCell<A>>)
 }
 
 struct A {
-    v: Box<Foo + Send>,
+    v: Box<dyn Foo + Send>,
 }
 
 fn main() {
-    let a = A {v: box B{v: None} as Box<Foo+Send>};
+    let a = A {v: box B{v: None} as Box<dyn Foo + Send>};
     //~^ ERROR `std::rc::Rc<std::cell::RefCell<A>>` cannot be sent between threads safely
 }
index 22185c7da344b1efbfce268c31c9b2fd92270ad2..f2668d3312289f37385d0f064f0c885529831bf5 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: `std::rc::Rc<std::cell::RefCell<A>>` cannot be sent between threads safely
   --> $DIR/issue-7013.rs:26:19
    |
-LL |     let a = A {v: box B{v: None} as Box<Foo+Send>};
+LL |     let a = A {v: box B{v: None} as Box<dyn Foo + Send>};
    |                   ^^^^^^^^^^^^^^ `std::rc::Rc<std::cell::RefCell<A>>` cannot be sent between threads safely
    |
    = help: within `B`, the trait `std::marker::Send` is not implemented for `std::rc::Rc<std::cell::RefCell<A>>`
index 7dd6b07177f933aa410cfb033b8a6695863142bd..619256c7871936069c35e245903f5999ecddfd0a 100644 (file)
@@ -18,5 +18,5 @@ fn dummy(&self) { }
 
 impl<T: 'static> A for T {}
 
-fn owned2<T: 'static>(a: Box<T>) { a as Box<A>; }
-fn owned3<T: 'static>(a: Box<T>) { box a as Box<A>; }
+fn owned2<T: 'static>(a: Box<T>) { a as Box<dyn A>; }
+fn owned3<T: 'static>(a: Box<T>) { box a as Box<dyn A>; }
index bd37b8582b204b60d0a0ac11ee56eb1f25da4fc9..a65c667b08e45f3b1d44544fcb13502c507abae5 100644 (file)
@@ -6,7 +6,7 @@ pub trait Writer {
     fn write(&mut self, b: &[u8]) -> Result<(), ()>;
 }
 
-fn foo(a: &mut Writer) {
+fn foo(a: &mut dyn Writer) {
     a.write(&[]).unwrap();
 }
 
index 96865344e7464deec94b588c2c91e3db882a4017..1e38ab9c6c2a4e4d4b3a3dab10a5c650695208d9 100644 (file)
@@ -12,8 +12,8 @@ fn dummy(&self) { }
     }
     impl X for isize {}
 
-    pub struct Z<'a>(Enum<&'a (X+'a)>);
-    fn foo() { let x: isize = 42; let z = Z(Enum::A(&x as &X)); let _ = z; }
+    pub struct Z<'a>(Enum<&'a (dyn X + 'a)>);
+    fn foo() { let x: isize = 42; let z = Z(Enum::A(&x as &dyn X)); let _ = z; }
 }
 
 mod b {
@@ -22,20 +22,20 @@ fn dummy(&self) { }
     }
     impl X for isize {}
     struct Y<'a>{
-        x:Option<&'a (X+'a)>,
+        x:Option<&'a (dyn X + 'a)>,
     }
 
     fn bar() {
         let x: isize = 42;
-        let _y = Y { x: Some(&x as &X) };
+        let _y = Y { x: Some(&x as &dyn X) };
     }
 }
 
 mod c {
     pub trait X { fn f(&self); }
     impl X for isize { fn f(&self) {} }
-    pub struct Z<'a>(Option<&'a (X+'a)>);
-    fn main() { let x: isize = 42; let z = Z(Some(&x as &X)); let _ = z; }
+    pub struct Z<'a>(Option<&'a (dyn X + 'a)>);
+    fn main() { let x: isize = 42; let z = Z(Some(&x as &dyn X)); let _ = z; }
 }
 
 pub fn main() {}
index dadeb9569644c608ffd8159da25097dbf56752d6..eb18613682f65fa844a9f6fba2e6ff231d25847d 100644 (file)
@@ -34,16 +34,16 @@ fn test<'a,T,U:Copy>(_: &'a isize) {
     assert_copy::<Box<&'a mut isize>>(); //~ ERROR : std::marker::Copy` is not satisfied
 
     // borrowed object types are generally ok
-    assert_copy::<&'a Dummy>();
-    assert_copy::<&'a (Dummy+Send)>();
-    assert_copy::<&'static (Dummy+Send)>();
+    assert_copy::<&'a dyn Dummy>();
+    assert_copy::<&'a (dyn Dummy + Send)>();
+    assert_copy::<&'static (dyn Dummy + Send)>();
 
     // owned object types are not ok
-    assert_copy::<Box<Dummy>>(); //~ ERROR : std::marker::Copy` is not satisfied
-    assert_copy::<Box<Dummy+Send>>(); //~ ERROR : std::marker::Copy` is not satisfied
+    assert_copy::<Box<dyn Dummy>>(); //~ ERROR : std::marker::Copy` is not satisfied
+    assert_copy::<Box<dyn Dummy + Send>>(); //~ ERROR : std::marker::Copy` is not satisfied
 
     // mutable object types are not ok
-    assert_copy::<&'a mut (Dummy+Send)>();  //~ ERROR : std::marker::Copy` is not satisfied
+    assert_copy::<&'a mut (dyn Dummy + Send)>();  //~ ERROR : std::marker::Copy` is not satisfied
 
     // unsafe ptrs are ok
     assert_copy::<*const isize>();
index 2680cb7c012f1b2b9dd80a7e70625d8eb10d94ed..929a8076562099a323bdb6fefa489ce3e0ce0621 100644 (file)
@@ -77,8 +77,8 @@ LL | fn assert_copy<T:Copy>() { }
 error[E0277]: the trait bound `std::boxed::Box<dyn Dummy>: std::marker::Copy` is not satisfied
   --> $DIR/kindck-copy.rs:42:5
    |
-LL |     assert_copy::<Box<Dummy>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `std::boxed::Box<dyn Dummy>`
+LL |     assert_copy::<Box<dyn Dummy>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `std::boxed::Box<dyn Dummy>`
    |
 note: required by `assert_copy`
   --> $DIR/kindck-copy.rs:5:1
@@ -89,8 +89,8 @@ LL | fn assert_copy<T:Copy>() { }
 error[E0277]: the trait bound `std::boxed::Box<dyn Dummy + std::marker::Send>: std::marker::Copy` is not satisfied
   --> $DIR/kindck-copy.rs:43:5
    |
-LL |     assert_copy::<Box<Dummy+Send>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `std::boxed::Box<dyn Dummy + std::marker::Send>`
+LL |     assert_copy::<Box<dyn Dummy + Send>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `std::boxed::Box<dyn Dummy + std::marker::Send>`
    |
 note: required by `assert_copy`
   --> $DIR/kindck-copy.rs:5:1
@@ -101,8 +101,8 @@ LL | fn assert_copy<T:Copy>() { }
 error[E0277]: the trait bound `&'a mut (dyn Dummy + std::marker::Send + 'a): std::marker::Copy` is not satisfied
   --> $DIR/kindck-copy.rs:46:5
    |
-LL |     assert_copy::<&'a mut (Dummy+Send)>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `&'a mut (dyn Dummy + std::marker::Send + 'a)`
+LL |     assert_copy::<&'a mut (dyn Dummy + Send)>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `&'a mut (dyn Dummy + std::marker::Send + 'a)`
    |
 note: required by `assert_copy`
   --> $DIR/kindck-copy.rs:5:1
index c1f662fda610b41fcee81e8a9532361bd6e56331..25d0e74187f75f68e2e25bef6b7582259685daca 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: `T` cannot be sent between threads safely
   --> $DIR/kindck-impl-type-params.rs:18:13
    |
-LL |     let a = &t as &Gettable<T>;
+LL |     let a = &t as &dyn Gettable<T>;
    |             ^^ `T` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `T`
@@ -12,7 +12,7 @@ LL |     let a = &t as &Gettable<T>;
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
   --> $DIR/kindck-impl-type-params.rs:18:13
    |
-LL |     let a = &t as &Gettable<T>;
+LL |     let a = &t as &dyn Gettable<T>;
    |             ^^ the trait `std::marker::Copy` is not implemented for `T`
    |
    = help: consider adding a `where T: std::marker::Copy` bound
@@ -20,10 +20,10 @@ LL |     let a = &t as &Gettable<T>;
    = note: required for the cast to the object type `dyn Gettable<T>`
 
 error[E0277]: `T` cannot be sent between threads safely
-  --> $DIR/kindck-impl-type-params.rs:25:27
+  --> $DIR/kindck-impl-type-params.rs:25:31
    |
-LL |     let a: &Gettable<T> = &t;
-   |                           ^^ `T` cannot be sent between threads safely
+LL |     let a: &dyn Gettable<T> = &t;
+   |                               ^^ `T` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `T`
    = help: consider adding a `where T: std::marker::Send` bound
@@ -31,10 +31,10 @@ LL |     let a: &Gettable<T> = &t;
    = note: required for the cast to the object type `dyn Gettable<T>`
 
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
-  --> $DIR/kindck-impl-type-params.rs:25:27
+  --> $DIR/kindck-impl-type-params.rs:25:31
    |
-LL |     let a: &Gettable<T> = &t;
-   |                           ^^ the trait `std::marker::Copy` is not implemented for `T`
+LL |     let a: &dyn Gettable<T> = &t;
+   |                               ^^ the trait `std::marker::Copy` is not implemented for `T`
    |
    = help: consider adding a `where T: std::marker::Copy` bound
    = note: required because of the requirements on the impl of `Gettable<T>` for `S<T>`
@@ -43,17 +43,17 @@ LL |     let a: &Gettable<T> = &t;
 error[E0277]: the trait bound `std::string::String: std::marker::Copy` is not satisfied
   --> $DIR/kindck-impl-type-params.rs:38:13
    |
-LL |     let a = t as Box<Gettable<String>>;
+LL |     let a = t as Box<dyn Gettable<String>>;
    |             ^ the trait `std::marker::Copy` is not implemented for `std::string::String`
    |
    = note: required because of the requirements on the impl of `Gettable<std::string::String>` for `S<std::string::String>`
    = note: required for the cast to the object type `dyn Gettable<std::string::String>`
 
 error[E0277]: the trait bound `foo3::Foo: std::marker::Copy` is not satisfied
-  --> $DIR/kindck-impl-type-params.rs:46:33
+  --> $DIR/kindck-impl-type-params.rs:46:37
    |
-LL |     let a: Box<Gettable<Foo>> = t;
-   |                                 ^ the trait `std::marker::Copy` is not implemented for `foo3::Foo`
+LL |     let a: Box<dyn Gettable<Foo>> = t;
+   |                                     ^ the trait `std::marker::Copy` is not implemented for `foo3::Foo`
    |
    = note: required because of the requirements on the impl of `Gettable<foo3::Foo>` for `S<foo3::Foo>`
    = note: required for the cast to the object type `dyn Gettable<foo3::Foo>`
index a47e418709dcd9ad2bfa9330d6b0cd9d3d871983..c4f90f36acfc25f6759cf88edb0a44630d1cf3de 100644 (file)
@@ -15,27 +15,27 @@ impl<T: Send + Copy + 'static> Gettable<T> for S<T> {}
 
 fn f<T>(val: T) {
     let t: S<T> = S(marker::PhantomData);
-    let a = &t as &Gettable<T>;
+    let a = &t as &dyn Gettable<T>;
     //~^ ERROR `T` cannot be sent between threads safely
     //~| ERROR : std::marker::Copy` is not satisfied
 }
 
 fn g<T>(val: T) {
     let t: S<T> = S(marker::PhantomData);
-    let a: &Gettable<T> = &t;
+    let a: &dyn Gettable<T> = &t;
     //~^ ERROR `T` cannot be sent between threads safely
     //~| ERROR : std::marker::Copy` is not satisfied
 }
 
 fn foo<'a>() {
     let t: S<&'a isize> = S(marker::PhantomData);
-    let a = &t as &Gettable<&'a isize>;
+    let a = &t as &dyn Gettable<&'a isize>;
     //~^ ERROR does not fulfill
 }
 
 fn foo2<'a>() {
     let t: Box<S<String>> = box S(marker::PhantomData);
-    let a = t as Box<Gettable<String>>;
+    let a = t as Box<dyn Gettable<String>>;
     //~^ ERROR : std::marker::Copy` is not satisfied
 }
 
@@ -43,7 +43,7 @@ fn foo3<'a>() {
     struct Foo; // does not impl Copy
 
     let t: Box<S<Foo>> = box S(marker::PhantomData);
-    let a: Box<Gettable<Foo>> = t;
+    let a: Box<dyn Gettable<Foo>> = t;
     //~^ ERROR : std::marker::Copy` is not satisfied
 }
 
index 8580e6812b41c6371133866bbeed5063515c2f55..e6f7088bd46355b0b17fc73fb9e657a159de59ad 100644 (file)
@@ -1,7 +1,7 @@
 error[E0277]: `T` cannot be sent between threads safely
   --> $DIR/kindck-impl-type-params.rs:18:13
    |
-LL |     let a = &t as &Gettable<T>;
+LL |     let a = &t as &dyn Gettable<T>;
    |             ^^ `T` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `T`
@@ -12,7 +12,7 @@ LL |     let a = &t as &Gettable<T>;
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
   --> $DIR/kindck-impl-type-params.rs:18:13
    |
-LL |     let a = &t as &Gettable<T>;
+LL |     let a = &t as &dyn Gettable<T>;
    |             ^^ the trait `std::marker::Copy` is not implemented for `T`
    |
    = help: consider adding a `where T: std::marker::Copy` bound
@@ -20,10 +20,10 @@ LL |     let a = &t as &Gettable<T>;
    = note: required for the cast to the object type `dyn Gettable<T>`
 
 error[E0277]: `T` cannot be sent between threads safely
-  --> $DIR/kindck-impl-type-params.rs:25:27
+  --> $DIR/kindck-impl-type-params.rs:25:31
    |
-LL |     let a: &Gettable<T> = &t;
-   |                           ^^ `T` cannot be sent between threads safely
+LL |     let a: &dyn Gettable<T> = &t;
+   |                               ^^ `T` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `T`
    = help: consider adding a `where T: std::marker::Send` bound
@@ -31,10 +31,10 @@ LL |     let a: &Gettable<T> = &t;
    = note: required for the cast to the object type `dyn Gettable<T>`
 
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
-  --> $DIR/kindck-impl-type-params.rs:25:27
+  --> $DIR/kindck-impl-type-params.rs:25:31
    |
-LL |     let a: &Gettable<T> = &t;
-   |                           ^^ the trait `std::marker::Copy` is not implemented for `T`
+LL |     let a: &dyn Gettable<T> = &t;
+   |                               ^^ the trait `std::marker::Copy` is not implemented for `T`
    |
    = help: consider adding a `where T: std::marker::Copy` bound
    = note: required because of the requirements on the impl of `Gettable<T>` for `S<T>`
@@ -43,7 +43,7 @@ LL |     let a: &Gettable<T> = &t;
 error[E0477]: the type `&'a isize` does not fulfill the required lifetime
   --> $DIR/kindck-impl-type-params.rs:32:13
    |
-LL |     let a = &t as &Gettable<&'a isize>;
+LL |     let a = &t as &dyn Gettable<&'a isize>;
    |             ^^
    |
    = note: type must satisfy the static lifetime
@@ -51,17 +51,17 @@ LL |     let a = &t as &Gettable<&'a isize>;
 error[E0277]: the trait bound `std::string::String: std::marker::Copy` is not satisfied
   --> $DIR/kindck-impl-type-params.rs:38:13
    |
-LL |     let a = t as Box<Gettable<String>>;
+LL |     let a = t as Box<dyn Gettable<String>>;
    |             ^ the trait `std::marker::Copy` is not implemented for `std::string::String`
    |
    = note: required because of the requirements on the impl of `Gettable<std::string::String>` for `S<std::string::String>`
    = note: required for the cast to the object type `dyn Gettable<std::string::String>`
 
 error[E0277]: the trait bound `foo3::Foo: std::marker::Copy` is not satisfied
-  --> $DIR/kindck-impl-type-params.rs:46:33
+  --> $DIR/kindck-impl-type-params.rs:46:37
    |
-LL |     let a: Box<Gettable<Foo>> = t;
-   |                                 ^ the trait `std::marker::Copy` is not implemented for `foo3::Foo`
+LL |     let a: Box<dyn Gettable<Foo>> = t;
+   |                                     ^ the trait `std::marker::Copy` is not implemented for `foo3::Foo`
    |
    = note: required because of the requirements on the impl of `Gettable<foo3::Foo>` for `S<foo3::Foo>`
    = note: required for the cast to the object type `dyn Gettable<foo3::Foo>`
index 0134636fa0d3c48b1b2e4d1bfbb6cb405cdb2632..61e72908248dff11c89f469bf4a7f6d7b14a596b 100644 (file)
@@ -21,7 +21,7 @@ fn a() {
 fn b() {
     let x: Box<_> = box 3;
     let y = &x;
-    let z = &x as &Foo;
+    let z = &x as &dyn Foo;
     //~^ ERROR E0038
     //~| ERROR E0038
 }
index 0ed2da46fbaea1c3b135b6b546452e5c8ab4bc27..1e719e2608425446c5e93bd73577c2e533f2939b 100644 (file)
@@ -14,15 +14,15 @@ LL | fn take_param<T:Foo>(foo: &T) { }
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/kindck-inherited-copy-bound.rs:24:19
    |
-LL |     let z = &x as &Foo;
-   |                   ^^^^ the trait `Foo` cannot be made into an object
+LL |     let z = &x as &dyn Foo;
+   |                   ^^^^^^^^ the trait `Foo` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
 
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/kindck-inherited-copy-bound.rs:24:13
    |
-LL |     let z = &x as &Foo;
+LL |     let z = &x as &dyn Foo;
    |             ^^ the trait `Foo` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
index 97f46c3953d51081e8db943f9a7a10f5c2ff390e..6411e688b4aa6dcf6b2a33028b6d833168560abe 100644 (file)
@@ -9,18 +9,18 @@ trait Message : Send { }
 // careful with object types, who knows what they close over...
 
 fn object_ref_with_static_bound_not_ok() {
-    assert_send::<&'static (Dummy+'static)>();
+    assert_send::<&'static (dyn Dummy + 'static)>();
     //~^ ERROR `(dyn Dummy + 'static)` cannot be shared between threads safely [E0277]
 }
 
 fn box_object_with_no_bound_not_ok<'a>() {
-    assert_send::<Box<Dummy>>();
+    assert_send::<Box<dyn Dummy>>();
     //~^ ERROR `dyn Dummy` cannot be sent between threads safely
 }
 
 fn object_with_send_bound_ok() {
-    assert_send::<&'static (Dummy+Sync)>();
-    assert_send::<Box<Dummy+Send>>();
+    assert_send::<&'static (dyn Dummy + Sync)>();
+    assert_send::<Box<dyn Dummy + Send>>();
 }
 
 fn main() { }
index 8d9935660292f35299cdc21f912409a0f2fed36e..c9aadd85a53f28cd0cddeee92ec7f9864a8ea5a4 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: `(dyn Dummy + 'static)` cannot be shared between threads safely
   --> $DIR/kindck-send-object.rs:12:5
    |
-LL |     assert_send::<&'static (Dummy+'static)>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'static)` cannot be shared between threads safely
+LL |     assert_send::<&'static (dyn Dummy + 'static)>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'static)` cannot be shared between threads safely
    |
    = help: the trait `std::marker::Sync` is not implemented for `(dyn Dummy + 'static)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `&'static (dyn Dummy + 'static)`
@@ -15,8 +15,8 @@ LL | fn assert_send<T:Send>() { }
 error[E0277]: `dyn Dummy` cannot be sent between threads safely
   --> $DIR/kindck-send-object.rs:17:5
    |
-LL |     assert_send::<Box<Dummy>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Dummy` cannot be sent between threads safely
+LL |     assert_send::<Box<dyn Dummy>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Dummy` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `dyn Dummy`
    = note: required because of the requirements on the impl of `std::marker::Send` for `std::ptr::Unique<dyn Dummy>`
index 1df7412132bd9fa6b787c8d95a16c8e80927a2db..998dc90456f143283ee002bdb2d3d624fa8556dc 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: `(dyn Dummy + 'a)` cannot be shared between threads safely
   --> $DIR/kindck-send-object1.rs:10:5
    |
-LL |     assert_send::<&'a Dummy>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be shared between threads safely
+LL |     assert_send::<&'a dyn Dummy>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be shared between threads safely
    |
    = help: the trait `std::marker::Sync` is not implemented for `(dyn Dummy + 'a)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `&'a (dyn Dummy + 'a)`
@@ -15,8 +15,8 @@ LL | fn assert_send<T:Send+'static>() { }
 error[E0277]: `(dyn Dummy + 'a)` cannot be sent between threads safely
   --> $DIR/kindck-send-object1.rs:29:5
    |
-LL |     assert_send::<Box<Dummy+'a>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be sent between threads safely
+LL |     assert_send::<Box<dyn Dummy + 'a>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `(dyn Dummy + 'a)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `std::ptr::Unique<(dyn Dummy + 'a)>`
index 341985467de6c8036a13647d2f20bd76b6cb8d09..0e198395c26fbfd53116fa2c674f5bbe7f317bf5 100644 (file)
@@ -7,26 +7,26 @@ trait Dummy { }
 
 // careful with object types, who knows what they close over...
 fn test51<'a>() {
-    assert_send::<&'a Dummy>();
+    assert_send::<&'a dyn Dummy>();
     //~^ ERROR `(dyn Dummy + 'a)` cannot be shared between threads safely [E0277]
 }
 fn test52<'a>() {
-    assert_send::<&'a (Dummy+Sync)>();
+    assert_send::<&'a (dyn Dummy + Sync)>();
     //~^ ERROR does not fulfill the required lifetime
 }
 
 // ...unless they are properly bounded
 fn test60() {
-    assert_send::<&'static (Dummy+Sync)>();
+    assert_send::<&'static (dyn Dummy + Sync)>();
 }
 fn test61() {
-    assert_send::<Box<Dummy+Send>>();
+    assert_send::<Box<dyn Dummy + Send>>();
 }
 
 // closure and object types can have lifetime bounds which make
 // them not ok
 fn test_71<'a>() {
-    assert_send::<Box<Dummy+'a>>();
+    assert_send::<Box<dyn Dummy + 'a>>();
     //~^ ERROR `(dyn Dummy + 'a)` cannot be sent between threads safely
 }
 
index a4b908e4101ff6a1cfc7918ee81ddc7b2436bc29..757b41ab6cb7e44dadbc4fe3a54f39e52a66140f 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: `(dyn Dummy + 'a)` cannot be shared between threads safely
   --> $DIR/kindck-send-object1.rs:10:5
    |
-LL |     assert_send::<&'a Dummy>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be shared between threads safely
+LL |     assert_send::<&'a dyn Dummy>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be shared between threads safely
    |
    = help: the trait `std::marker::Sync` is not implemented for `(dyn Dummy + 'a)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `&'a (dyn Dummy + 'a)`
@@ -15,16 +15,16 @@ LL | fn assert_send<T:Send+'static>() { }
 error[E0477]: the type `&'a (dyn Dummy + std::marker::Sync + 'a)` does not fulfill the required lifetime
   --> $DIR/kindck-send-object1.rs:14:5
    |
-LL |     assert_send::<&'a (Dummy+Sync)>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     assert_send::<&'a (dyn Dummy + Sync)>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: type must satisfy the static lifetime
 
 error[E0277]: `(dyn Dummy + 'a)` cannot be sent between threads safely
   --> $DIR/kindck-send-object1.rs:29:5
    |
-LL |     assert_send::<Box<Dummy+'a>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be sent between threads safely
+LL |     assert_send::<Box<dyn Dummy + 'a>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'a)` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `(dyn Dummy + 'a)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `std::ptr::Unique<(dyn Dummy + 'a)>`
index 911ad988081f5bfaba489cd3ed88db4a24923e3c..b797588e446d635f17d4b3e18f62f8680b014f52 100644 (file)
@@ -4,21 +4,21 @@ fn assert_send<T:Send>() { }
 trait Dummy { }
 
 fn test50() {
-    assert_send::<&'static Dummy>();
+    assert_send::<&'static dyn Dummy>();
     //~^ ERROR `(dyn Dummy + 'static)` cannot be shared between threads safely [E0277]
 }
 
 fn test53() {
-    assert_send::<Box<Dummy>>();
+    assert_send::<Box<dyn Dummy>>();
     //~^ ERROR `dyn Dummy` cannot be sent between threads safely
 }
 
 // ...unless they are properly bounded
 fn test60() {
-    assert_send::<&'static (Dummy+Sync)>();
+    assert_send::<&'static (dyn Dummy + Sync)>();
 }
 fn test61() {
-    assert_send::<Box<Dummy+Send>>();
+    assert_send::<Box<dyn Dummy + Send>>();
 }
 
 fn main() { }
index db79989dc5f6cea7922ab051917b305211078b11..c1c9db9da839ab541ed544fb5e4ed9095bd82658 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: `(dyn Dummy + 'static)` cannot be shared between threads safely
   --> $DIR/kindck-send-object2.rs:7:5
    |
-LL |     assert_send::<&'static Dummy>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'static)` cannot be shared between threads safely
+LL |     assert_send::<&'static dyn Dummy>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Dummy + 'static)` cannot be shared between threads safely
    |
    = help: the trait `std::marker::Sync` is not implemented for `(dyn Dummy + 'static)`
    = note: required because of the requirements on the impl of `std::marker::Send` for `&'static (dyn Dummy + 'static)`
@@ -15,8 +15,8 @@ LL | fn assert_send<T:Send>() { }
 error[E0277]: `dyn Dummy` cannot be sent between threads safely
   --> $DIR/kindck-send-object2.rs:12:5
    |
-LL |     assert_send::<Box<Dummy>>();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Dummy` cannot be sent between threads safely
+LL |     assert_send::<Box<dyn Dummy>>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Dummy` cannot be sent between threads safely
    |
    = help: the trait `std::marker::Send` is not implemented for `dyn Dummy`
    = note: required because of the requirements on the impl of `std::marker::Send` for `std::ptr::Unique<dyn Dummy>`
index 8b24563e920041d1c05668cf0779b4a5a3bf38df..f2cf19abdac31a6a92e573288920905df59b0d8e 100644 (file)
@@ -1,7 +1,7 @@
 error[E0521]: borrowed data escapes outside of function
   --> $DIR/lifetime-bound-will-change-warning.rs:34:5
    |
-LL | fn test2<'a>(x: &'a Box<Fn()+'a>) {
+LL | fn test2<'a>(x: &'a Box<dyn Fn() + 'a>) {
    |              - `x` is a reference that is only valid in the function body
 LL |     // but ref_obj will not, so warn.
 LL |     ref_obj(x)
@@ -10,7 +10,7 @@ LL |     ref_obj(x)
 error[E0521]: borrowed data escapes outside of function
   --> $DIR/lifetime-bound-will-change-warning.rs:39:5
    |
-LL | fn test2cc<'a>(x: &'a Box<Fn()+'a>) {
+LL | fn test2cc<'a>(x: &'a Box<dyn Fn() + 'a>) {
    |                - `x` is a reference that is only valid in the function body
 LL |     // same as test2, but cross crate
 LL |     lib::ref_obj(x)
index 5461f875af6c548d28bbce106b802bb5c832f34f..3c6d92234c4fa7e40906297b919e8361905bfcba 100644 (file)
@@ -9,42 +9,42 @@
 
 extern crate lifetime_bound_will_change_warning_lib as lib;
 
-fn just_ref(x: &Fn()) {
+fn just_ref(x: &dyn Fn()) {
 }
 
-fn ref_obj(x: &Box<Fn()>) {
+fn ref_obj(x: &Box<dyn Fn()>) {
     // this will change to &Box<Fn()+'static>...
 
     // Note: no warning is issued here, because the type of `x` will change to 'static
     if false { ref_obj(x); }
 }
 
-fn test1<'a>(x: &'a Box<Fn()+'a>) {
+fn test1<'a>(x: &'a Box<dyn Fn() + 'a>) {
     // just_ref will stay the same.
     just_ref(&**x)
 }
 
-fn test1cc<'a>(x: &'a Box<Fn()+'a>) {
+fn test1cc<'a>(x: &'a Box<dyn Fn() + 'a>) {
     // same as test1, but cross-crate
     lib::just_ref(&**x)
 }
 
-fn test2<'a>(x: &'a Box<Fn()+'a>) {
+fn test2<'a>(x: &'a Box<dyn Fn() + 'a>) {
     // but ref_obj will not, so warn.
     ref_obj(x) //~ ERROR mismatched types
 }
 
-fn test2cc<'a>(x: &'a Box<Fn()+'a>) {
+fn test2cc<'a>(x: &'a Box<dyn Fn() + 'a>) {
     // same as test2, but cross crate
     lib::ref_obj(x) //~ ERROR mismatched types
 }
 
-fn test3<'a>(x: &'a Box<Fn()+'static>) {
+fn test3<'a>(x: &'a Box<dyn Fn() + 'static>) {
     // here, we have a 'static bound, so even when ref_obj changes, no error results
     ref_obj(x)
 }
 
-fn test3cc<'a>(x: &'a Box<Fn()+'static>) {
+fn test3cc<'a>(x: &'a Box<dyn Fn() + 'static>) {
     // same as test3, but cross crate
     lib::ref_obj(x)
 }
index 1af4bd501ba49f69d168b9f3cf300f41eef95195..35d63c172765112e11dc5578d9e559bc4d45269b 100644 (file)
@@ -9,7 +9,7 @@ LL |     ref_obj(x)
 note: the lifetime 'a as defined on the function body at 32:10...
   --> $DIR/lifetime-bound-will-change-warning.rs:32:10
    |
-LL | fn test2<'a>(x: &'a Box<Fn()+'a>) {
+LL | fn test2<'a>(x: &'a Box<dyn Fn() + 'a>) {
    |          ^^
    = note: ...does not necessarily outlive the static lifetime
 
@@ -24,7 +24,7 @@ LL |     lib::ref_obj(x)
 note: the lifetime 'a as defined on the function body at 37:12...
   --> $DIR/lifetime-bound-will-change-warning.rs:37:12
    |
-LL | fn test2cc<'a>(x: &'a Box<Fn()+'a>) {
+LL | fn test2cc<'a>(x: &'a Box<dyn Fn() + 'a>) {
    |            ^^
    = note: ...does not necessarily outlive the static lifetime
 
index 1c288a7e44f37a563f7e2feadf38e4997d29f8e1..2370084b072c7c070b3667901d2e819fb004a5e6 100644 (file)
@@ -5,7 +5,7 @@ trait Future {
 
 use std::error::Error;
 
-fn foo() -> impl Future<Item=(), Error=Box<Error>> {
+fn foo() -> impl Future<Item=(), Error=Box<dyn Error>> {
 //~^ ERROR missing lifetime
     Ok(())
 }
index b2a3d9a94361fdfb73f767c29248ddd8989c8ef7..06b317ce95278fabf218a9e5a0fda986da1c6720 100644 (file)
@@ -1,8 +1,8 @@
 error[E0106]: missing lifetime specifier
   --> $DIR/lifetime-elision-return-type-trait.rs:8:44
    |
-LL | fn foo() -> impl Future<Item=(), Error=Box<Error>> {
-   |                                            ^^^^^ help: consider giving it a 'static lifetime: `Error + 'static`
+LL | fn foo() -> impl Future<Item=(), Error=Box<dyn Error>> {
+   |                                            ^^^^^^^^^ help: consider giving it a 'static lifetime: `dyn Error + 'static`
    |
    = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from
 
index c4e7ff90069db0b8a180df1ac2a907c44c92a768..3c95be95db0801c7c8cbe91e7f39e762e189fe62 100644 (file)
@@ -1,18 +1,18 @@
 error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable
   --> $DIR/ex3-both-anon-regions-using-trait-objects.rs:2:3
    |
-LL | fn foo(x:Box<Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
-   |                              - help: consider changing this to be mutable: `mut y`
+LL | fn foo(x:Box<dyn Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
+   |                                  - help: consider changing this to be mutable: `mut y`
 LL |   y.push(z);
    |   ^ cannot borrow as mutable
 
 error: lifetime may not live long enough
   --> $DIR/ex3-both-anon-regions-using-trait-objects.rs:2:3
    |
-LL | fn foo(x:Box<Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
-   |                                     -        - let's call the lifetime of this reference `'1`
-   |                                     |
-   |                                     let's call the lifetime of this reference `'2`
+LL | fn foo(x:Box<dyn Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
+   |                                         -        - let's call the lifetime of this reference `'1`
+   |                                         |
+   |                                         let's call the lifetime of this reference `'2`
 LL |   y.push(z);
    |   ^^^^^^^^^ argument requires that `'1` must outlive `'2`
 
index 324a5846c94ae4ee836c69ace1c498950a0f9e79..6625d41c7de2a7d78d6a0bb247071fd1069ce2f3 100644 (file)
@@ -1,4 +1,4 @@
-fn foo(x:Box<Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
+fn foo(x:Box<dyn Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
   y.push(z); //~ ERROR lifetime mismatch
 }
 
index 6cd175b8a617b767eee806ab2bd797f57611be83..bfecb4d33931b4bd2cecd6bb6afdc56e54cb6199 100644 (file)
@@ -1,8 +1,8 @@
 error[E0623]: lifetime mismatch
   --> $DIR/ex3-both-anon-regions-using-trait-objects.rs:2:10
    |
-LL | fn foo(x:Box<Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
-   |                 ---  --- these two types are declared with different lifetimes...
+LL | fn foo(x:Box<dyn Fn(&u8, &u8)> , y: Vec<&u8>, z: &u8) {
+   |                     ---  --- these two types are declared with different lifetimes...
 LL |   y.push(z);
    |          ^ ...but data from `z` flows into `y` here
 
diff --git a/src/test/ui/linkage-attr/auxiliary/def_colliding_external.rs b/src/test/ui/linkage-attr/auxiliary/def_colliding_external.rs
new file mode 100644 (file)
index 0000000..bbbfc48
--- /dev/null
@@ -0,0 +1,7 @@
+#![feature(linkage)]
+#![crate_type = "lib"]
+
+extern {
+    #[linkage="external"]
+    pub static collision: *const i32;
+}
diff --git a/src/test/ui/linkage-attr/auxiliary/def_illtyped_external.rs b/src/test/ui/linkage-attr/auxiliary/def_illtyped_external.rs
new file mode 100644 (file)
index 0000000..2300930
--- /dev/null
@@ -0,0 +1,5 @@
+#![feature(linkage)]
+#![crate_type = "lib"]
+
+#[linkage="external"]
+pub static EXTERN: u32 = 0;
diff --git a/src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.rs b/src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.rs
new file mode 100644 (file)
index 0000000..85a9a33
--- /dev/null
@@ -0,0 +1,21 @@
+// rust-lang/rust#61232: We used to ICE when trying to detect a
+// collision on the symbol generated for the external linkage item in
+// an extern crate.
+
+// aux-build:def_colliding_external.rs
+
+extern crate def_colliding_external as dep1;
+
+#[no_mangle]
+pub static _rust_extern_with_linkage_collision: i32 = 0;
+
+mod dep2 {
+    #[no_mangle]
+    pub static collision: usize = 0;
+}
+
+fn main() {
+    unsafe {
+       println!("{:p}", &dep1::collision);
+    }
+}
diff --git a/src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.stderr b/src/test/ui/linkage-attr/linkage-detect-extern-generated-name-collision.stderr
new file mode 100644 (file)
index 0000000..dcb954a
--- /dev/null
@@ -0,0 +1,8 @@
+error: symbol `collision` is already defined
+  --> $DIR/auxiliary/def_colliding_external.rs:6:5
+   |
+LL |     pub static collision: *const i32;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.rs b/src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.rs
new file mode 100644 (file)
index 0000000..dc15798
--- /dev/null
@@ -0,0 +1,23 @@
+#![feature(linkage)]
+
+mod dep1 {
+    extern {
+        #[linkage="external"]
+        #[no_mangle]
+        pub static collision: *const i32; //~ ERROR symbol `collision` is already defined
+    }
+}
+
+#[no_mangle]
+pub static _rust_extern_with_linkage_collision: i32 = 0;
+
+mod dep2 {
+    #[no_mangle]
+    pub static collision: usize = 0;
+}
+
+fn main() {
+    unsafe {
+       println!("{:p}", &dep1::collision);
+    }
+}
diff --git a/src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.stderr b/src/test/ui/linkage-attr/linkage-detect-local-generated-name-collision.stderr
new file mode 100644 (file)
index 0000000..117c76f
--- /dev/null
@@ -0,0 +1,8 @@
+error: symbol `collision` is already defined
+  --> $DIR/linkage-detect-local-generated-name-collision.rs:7:9
+   |
+LL |         pub static collision: *const i32;
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/linkage-attr/linkage-requires-raw-ptr.rs b/src/test/ui/linkage-attr/linkage-requires-raw-ptr.rs
new file mode 100644 (file)
index 0000000..014c715
--- /dev/null
@@ -0,0 +1,10 @@
+// rust-lang/rust#59548: We used to ICE when trying to use a static
+// with a type that violated its own `#[linkage]`.
+
+// aux-build:def_illtyped_external.rs
+
+extern crate def_illtyped_external as dep;
+
+fn main() {
+    println!("{:p}", &dep::EXTERN);
+}
diff --git a/src/test/ui/linkage-attr/linkage-requires-raw-ptr.stderr b/src/test/ui/linkage-attr/linkage-requires-raw-ptr.stderr
new file mode 100644 (file)
index 0000000..a80b495
--- /dev/null
@@ -0,0 +1,8 @@
+error: must have type `*const T` or `*mut T` due to `#[linkage]` attribute
+  --> $DIR/auxiliary/def_illtyped_external.rs:5:1
+   |
+LL | pub static EXTERN: u32 = 0;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/linkage-attr/linkage2.rs b/src/test/ui/linkage-attr/linkage2.rs
new file mode 100644 (file)
index 0000000..c8af1a6
--- /dev/null
@@ -0,0 +1,15 @@
+// FIXME https://github.com/rust-lang/rust/issues/59774
+// normalize-stderr-test "thread.*panicked.*Metadata module not compiled.*\n" -> ""
+// normalize-stderr-test "note:.*RUST_BACKTRACE=1.*\n" -> ""
+// ignore-sgx no weak linkages permitted
+
+#![feature(linkage)]
+
+extern {
+    #[linkage = "extern_weak"] static foo: i32;
+    //~^ ERROR: must have type `*const T` or `*mut T` due to `#[linkage]` attribute
+}
+
+fn main() {
+    println!("{}", unsafe { foo });
+}
diff --git a/src/test/ui/linkage-attr/linkage2.stderr b/src/test/ui/linkage-attr/linkage2.stderr
new file mode 100644 (file)
index 0000000..2654ffd
--- /dev/null
@@ -0,0 +1,8 @@
+error: must have type `*const T` or `*mut T` due to `#[linkage]` attribute
+  --> $DIR/linkage2.rs:9:32
+   |
+LL |     #[linkage = "extern_weak"] static foo: i32;
+   |                                ^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/linkage-attr/linkage3.rs b/src/test/ui/linkage-attr/linkage3.rs
new file mode 100644 (file)
index 0000000..1462079
--- /dev/null
@@ -0,0 +1,14 @@
+// FIXME https://github.com/rust-lang/rust/issues/59774
+// normalize-stderr-test "thread.*panicked.*Metadata module not compiled.*\n" -> ""
+// normalize-stderr-test "note:.*RUST_BACKTRACE=1.*\n" -> ""
+
+#![feature(linkage)]
+
+extern {
+    #[linkage = "foo"] static foo: *const i32;
+    //~^ ERROR: invalid linkage specified
+}
+
+fn main() {
+    println!("{:?}", unsafe { foo });
+}
diff --git a/src/test/ui/linkage-attr/linkage3.stderr b/src/test/ui/linkage-attr/linkage3.stderr
new file mode 100644 (file)
index 0000000..b74fdc9
--- /dev/null
@@ -0,0 +1,8 @@
+error: invalid linkage specified
+  --> $DIR/linkage3.rs:8:24
+   |
+LL |     #[linkage = "foo"] static foo: *const i32;
+   |                        ^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/linkage-attr/linkage4.rs b/src/test/ui/linkage-attr/linkage4.rs
new file mode 100644 (file)
index 0000000..3b935f9
--- /dev/null
@@ -0,0 +1,5 @@
+#[linkage = "external"]
+static foo: isize = 0;
+//~^^ ERROR: the `linkage` attribute is experimental and not portable
+
+fn main() {}
diff --git a/src/test/ui/linkage-attr/linkage4.stderr b/src/test/ui/linkage-attr/linkage4.stderr
new file mode 100644 (file)
index 0000000..f2aab16
--- /dev/null
@@ -0,0 +1,12 @@
+error[E0658]: the `linkage` attribute is experimental and not portable across platforms
+  --> $DIR/linkage4.rs:1:1
+   |
+LL | #[linkage = "external"]
+   | ^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: for more information, see https://github.com/rust-lang/rust/issues/29603
+   = help: add #![feature(linkage)] to the crate attributes to enable
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/src/test/ui/linkage2.rs b/src/test/ui/linkage2.rs
deleted file mode 100644 (file)
index f9ea531..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-// FIXME https://github.com/rust-lang/rust/issues/59774
-// normalize-stderr-test "thread.*panicked.*Metadata module not compiled.*\n" -> ""
-// normalize-stderr-test "note:.*RUST_BACKTRACE=1.*\n" -> ""
-// ignore-sgx no weak linkages permitted
-
-#![feature(linkage)]
-
-extern {
-    #[linkage = "extern_weak"] static foo: i32;
-    //~^ ERROR: must have type `*const T` or `*mut T`
-}
-
-fn main() {
-    println!("{}", unsafe { foo });
-}
diff --git a/src/test/ui/linkage2.stderr b/src/test/ui/linkage2.stderr
deleted file mode 100644 (file)
index 8326c0b..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-error: must have type `*const T` or `*mut T`
-  --> $DIR/linkage2.rs:9:32
-   |
-LL |     #[linkage = "extern_weak"] static foo: i32;
-   |                                ^^^^^^^^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/linkage3.rs b/src/test/ui/linkage3.rs
deleted file mode 100644 (file)
index 1462079..0000000
+++ /dev/null
@@ -1,14 +0,0 @@
-// FIXME https://github.com/rust-lang/rust/issues/59774
-// normalize-stderr-test "thread.*panicked.*Metadata module not compiled.*\n" -> ""
-// normalize-stderr-test "note:.*RUST_BACKTRACE=1.*\n" -> ""
-
-#![feature(linkage)]
-
-extern {
-    #[linkage = "foo"] static foo: *const i32;
-    //~^ ERROR: invalid linkage specified
-}
-
-fn main() {
-    println!("{:?}", unsafe { foo });
-}
diff --git a/src/test/ui/linkage3.stderr b/src/test/ui/linkage3.stderr
deleted file mode 100644 (file)
index b74fdc9..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-error: invalid linkage specified
-  --> $DIR/linkage3.rs:8:24
-   |
-LL |     #[linkage = "foo"] static foo: *const i32;
-   |                        ^^^^^^^^^^^^^^^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/linkage4.rs b/src/test/ui/linkage4.rs
deleted file mode 100644 (file)
index 3b935f9..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-#[linkage = "external"]
-static foo: isize = 0;
-//~^^ ERROR: the `linkage` attribute is experimental and not portable
-
-fn main() {}
diff --git a/src/test/ui/linkage4.stderr b/src/test/ui/linkage4.stderr
deleted file mode 100644 (file)
index f2aab16..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-error[E0658]: the `linkage` attribute is experimental and not portable across platforms
-  --> $DIR/linkage4.rs:1:1
-   |
-LL | #[linkage = "external"]
-   | ^^^^^^^^^^^^^^^^^^^^^^^
-   |
-   = note: for more information, see https://github.com/rust-lang/rust/issues/29603
-   = help: add #![feature(linkage)] to the crate attributes to enable
-
-error: aborting due to previous error
-
-For more information about this error, try `rustc --explain E0658`.
index 816177abdeaf1e840e3d437b6b2b2fba20376ff7..a3d9b6febdbb73601ab9831b870a3229fa3698de 100644 (file)
@@ -51,7 +51,7 @@ pub struct StructWithProjectionAndLifetime<'a>(
     pub fn char_type(p: char); //~ ERROR uses type `char`
     pub fn i128_type(p: i128); //~ ERROR uses type `i128`
     pub fn u128_type(p: u128); //~ ERROR uses type `u128`
-    pub fn trait_type(p: &Clone); //~ ERROR uses type `dyn std::clone::Clone`
+    pub fn trait_type(p: &dyn Clone); //~ ERROR uses type `dyn std::clone::Clone`
     pub fn tuple_type(p: (i32, i32)); //~ ERROR uses type `(i32, i32)`
     pub fn tuple_type2(p: I32Pair); //~ ERROR uses type `(i32, i32)`
     pub fn zero_size(p: ZeroSize); //~ ERROR struct has no fields
index 67ba30a81c50272aab86521c1be2dd9a8d2496bf..03c18e4530b82dea2d588784fd916caefa5cb931 100644 (file)
@@ -76,8 +76,8 @@ LL |     pub fn u128_type(p: u128);
 error: `extern` block uses type `dyn std::clone::Clone` which is not FFI-safe: trait objects have no C equivalent
   --> $DIR/lint-ctypes.rs:54:26
    |
-LL |     pub fn trait_type(p: &Clone);
-   |                          ^^^^^^
+LL |     pub fn trait_type(p: &dyn Clone);
+   |                          ^^^^^^^^^^
 
 error: `extern` block uses type `(i32, i32)` which is not FFI-safe: tuples have unspecified layout
   --> $DIR/lint-ctypes.rs:55:26
index 00b250f83dd6f312531237bb283f201f34b0dbba..4397522f3f32fd8274b1f223c057a7c0c848a5cb 100644 (file)
@@ -73,6 +73,6 @@ fn f() {}
 }
 
 pub fn foo() {
-    let a: &inner::Trait = &1_isize;
+    let a: &dyn inner::Trait = &1_isize;
     a.f();
 }
index 12e7b086d35d10fc5f3bbea1e4deb2118fe55a58..53eee35a9ca24759cf67d6bde1b65ad530d37487 100644 (file)
@@ -148,7 +148,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated();
         foo.trait_deprecated_text();
         foo.trait_deprecated_unstable();
@@ -373,7 +373,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated();
         foo.trait_deprecated_text();
         foo.trait_unstable();
index bf574d7144d06310cbc26d2d654b0eae98980f1a..a2031c2189ae14c41237c3d07598fd485947d445 100644 (file)
@@ -98,7 +98,7 @@ fn test() {
         struct S1<T: TraitWithAssociatedTypes>(T::TypeUnstable);
         struct S2<T: TraitWithAssociatedTypes>(T::TypeDeprecated);
         //~^ WARN use of deprecated item 'lint_stability::TraitWithAssociatedTypes::TypeDeprecated': text
-        type A = TraitWithAssociatedTypes<
+        type A = dyn TraitWithAssociatedTypes<
             TypeUnstable = u8,
             TypeDeprecated = u16,
             //~^ WARN use of deprecated item 'lint_stability::TraitWithAssociatedTypes::TypeDeprecated'
@@ -170,7 +170,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated(); //~ WARN use of deprecated item 'lint_stability::Trait::trait_deprecated'
         foo.trait_deprecated_text(); //~ WARN use of deprecated item 'lint_stability::Trait::trait_deprecated_text': text
         foo.trait_deprecated_unstable(); //~ WARN use of deprecated item 'lint_stability::Trait::trait_deprecated_unstable'
@@ -423,7 +423,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated(); //~ WARN use of deprecated item 'this_crate::Trait::trait_deprecated'
         foo.trait_deprecated_text(); //~ WARN use of deprecated item 'this_crate::Trait::trait_deprecated_text': text
         foo.trait_unstable();
index 3e4a3874d2c4a074698a3ea717aac6d1aa756f3c..fde27eec7d3e882f87eba4965cdb9236e60c62d2 100644 (file)
@@ -88,7 +88,7 @@ fn test() {
         struct S1<T: TraitWithAssociatedTypes>(T::TypeUnstable);
         //~^ ERROR use of unstable library feature
         struct S2<T: TraitWithAssociatedTypes>(T::TypeDeprecated);
-        type A = TraitWithAssociatedTypes<
+        type A = dyn TraitWithAssociatedTypes<
             TypeUnstable = u8, //~ ERROR use of unstable library feature
             TypeDeprecated = u16,
         >;
@@ -161,7 +161,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated();
         foo.trait_deprecated_text();
         foo.trait_stable();
@@ -414,7 +414,7 @@ fn test_method_param<Foo: Trait>(foo: Foo) {
         <Foo as Trait>::trait_stable(&foo);
     }
 
-    fn test_method_object(foo: &Trait) {
+    fn test_method_object(foo: &dyn Trait) {
         foo.trait_deprecated();
         foo.trait_deprecated_text();
         foo.trait_unstable();
index 44af1179097ede2bed8f3b42cfb5576304e60e65..ab60a326cd220808ba2d69bc15b1fbbdb2673118 100644 (file)
@@ -39,7 +39,7 @@ fn bar(&self) { //~ ERROR function cannot return without recursing
     }
 }
 
-impl Foo for Box<Foo+'static> {
+impl Foo for Box<dyn Foo + 'static> {
     fn bar(&self) { //~ ERROR function cannot return without recursing
         loop {
             self.bar()
@@ -67,7 +67,7 @@ fn bar(&self) { //~ ERROR function cannot return without recursing
     }
 }
 
-impl Foo2 for Box<Foo2+'static> {
+impl Foo2 for Box<dyn Foo2 + 'static> {
     fn bar(&self) { //~ ERROR function cannot return without recursing
         loop {
             Foo2::bar(self)
index f48e9848456657b3633c8e08e336ca95061be7a0..656ed6576e269855a60c48b05735b1c06cd892ee 100644 (file)
@@ -18,7 +18,7 @@ struct S1<'a> { x: &'a i8 } impl<'a> S1<'a> { fn m(&self) {} }
     let z = 3_i8;
 
     'a: loop {
-        let b = Box::new(|x: &i8| *x) as Box<for <'a> Fn(&'a i8) -> i8>;
+        let b = Box::new(|x: &i8| *x) as Box<dyn for <'a> Fn(&'a i8) -> i8>;
         //~^ WARN lifetime name `'a` shadows a label name that is already in scope
         assert_eq!((*b)(&z), z);
         break 'a;
index 4c4d9218ec9e9549734f23a5de57a93da5f83df3..e5d376675c62abaffa4803df26e6f33191e24eba 100644 (file)
@@ -1,8 +1,8 @@
 warning: lifetime name `'a` shadows a label name that is already in scope
-  --> $DIR/loops-reject-lifetime-shadowing-label.rs:21:51
+  --> $DIR/loops-reject-lifetime-shadowing-label.rs:21:55
    |
 LL |     'a: loop {
    |     -- first declared here
-LL |         let b = Box::new(|x: &i8| *x) as Box<for <'a> Fn(&'a i8) -> i8>;
-   |                                                   ^^ lifetime 'a already in scope
+LL |         let b = Box::new(|x: &i8| *x) as Box<dyn for <'a> Fn(&'a i8) -> i8>;
+   |                                                       ^^ lifetime 'a already in scope
 
index dcd604a5157e26b39d35cfa9ea4541cafeae79bc..f303c07e6d79c339194979923bc42740938a71c5 100644 (file)
@@ -4,8 +4,8 @@
 trait Foo<T, U> { }
 
 fn foo(
-    x: &for<'a, 'b> Foo<&'a u8, &'b u8>,
-    y: &for<'a> Foo<&'a u8, &'a u8>,
+    x: &dyn for<'a, 'b> Foo<&'a u8, &'b u8>,
+    y: &dyn for<'a> Foo<&'a u8, &'a u8>,
 ) {
     let z = match 22 {
         0 => x,
@@ -14,12 +14,12 @@ fn foo(
 }
 
 fn bar(
-    x: &for<'a, 'b> Foo<&'a u8, &'b u8>,
-    y: &for<'a> Foo<&'a u8, &'a u8>,
+    x: &dyn for<'a, 'b> Foo<&'a u8, &'b u8>,
+    y: &dyn for<'a> Foo<&'a u8, &'a u8>,
 ) {
     // Accepted with explicit case:
     let z = match 22 {
-        0 => x as &for<'a> Foo<&'a u8, &'a u8>,
+        0 => x as &dyn for<'a> Foo<&'a u8, &'a u8>,
         _ => y,
     };
 }
index dab7863415f6ed3d8bacc91be9597b57a791b810..c355a0e420f8feaf98cf728acc95d1309a861a73 100644 (file)
@@ -13,7 +13,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::new(x);
+    let x: Box<dyn Map<isize, isize>> = x;
+    let y: Box<dyn Map<usize, isize>> = Box::new(x);
     //~^ ERROR `std::boxed::Box<dyn Map<isize, isize>>: Map<usize, isize>` is not satisfied
 }
index 9aa9804424214d08eb0caa1a6f084e798d781c58..21dac1ab1edfb0a7ce6acccd3893842192b41cab 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the trait bound `std::boxed::Box<dyn Map<isize, isize>>: Map<usize, isize>` is not satisfied
-  --> $DIR/map-types.rs:17:37
+  --> $DIR/map-types.rs:17:41
    |
-LL |     let y: Box<Map<usize, isize>> = Box::new(x);
-   |                                     ^^^^^^^^^^^ the trait `Map<usize, isize>` is not implemented for `std::boxed::Box<dyn Map<isize, isize>>`
+LL |     let y: Box<dyn Map<usize, isize>> = Box::new(x);
+   |                                         ^^^^^^^^^^^ the trait `Map<usize, isize>` is not implemented for `std::boxed::Box<dyn Map<isize, isize>>`
    |
    = note: required for the cast to the object type `dyn Map<usize, isize>`
 
index 36a1a2fda69958023d0aecfc3c535e762a18bfff..23893911eabd901b871114158f5b4082416e2ba3 100644 (file)
@@ -11,10 +11,10 @@ fn late_implicit_early<'b>(self, _: &u8) -> &'b u8 { loop {} }
 
     // 'late lifetimes here belong to nested types not to the tested functions.
     fn early_tricky_explicit<'a>(_: for<'late> fn(&'late u8),
-                                 _: Box<for<'late> Fn(&'late u8)>)
+                                 _: Box<dyn for<'late> Fn(&'late u8)>)
                                  -> &'a u8 { loop {} }
     fn early_tricky_implicit<'a>(_: fn(&u8),
-                                 _: Box<Fn(&u8)>)
+                                 _: Box<dyn Fn(&u8)>)
                                  -> &'a u8 { loop {} }
 }
 
index a5e03a18e6af2468065439e4979624bce681d413..2f88c6496c4206f21c690959f31837d6efa2fdef 100644 (file)
@@ -24,7 +24,7 @@ fn main()
     let v = 0 as *const u8;
     let fat_v : *const [u8] = unsafe { &*(0 as *const [u8; 1])};
     let fat_sv : *const [i8] = unsafe { &*(0 as *const [i8; 1])};
-    let foo: &Foo = &f;
+    let foo: &dyn Foo = &f;
 
     let _ = v as &u8; //~ ERROR non-primitive cast
     let _ = v as E; //~ ERROR non-primitive cast
@@ -50,7 +50,7 @@ fn main()
 
     let _ = 42usize as *const [u8]; //~ ERROR is invalid
     let _ = v as *const [u8]; //~ ERROR cannot cast
-    let _ = fat_v as *const Foo; //~ ERROR the size for values of type
+    let _ = fat_v as *const dyn Foo; //~ ERROR the size for values of type
     let _ = foo as *const str; //~ ERROR is invalid
     let _ = foo as *mut str; //~ ERROR is invalid
     let _ = main as *mut str; //~ ERROR is invalid
@@ -59,14 +59,14 @@ fn main()
     let _ = fat_sv as usize; //~ ERROR is invalid
 
     let a : *const str = "hello";
-    let _ = a as *const Foo; //~ ERROR the size for values of type
+    let _ = a as *const dyn Foo; //~ ERROR the size for values of type
 
     // check no error cascade
     let _ = main.f as *const u32; //~ ERROR no field
 
-    let cf: *const Foo = &0;
+    let cf: *const dyn Foo = &0;
     let _ = cf as *const [u16]; //~ ERROR is invalid
-    let _ = cf as *const Bar; //~ ERROR is invalid
+    let _ = cf as *const dyn Bar; //~ ERROR is invalid
 
     vec![0.0].iter().map(|s| s as f32).collect::<Vec<f32>>(); //~ ERROR is invalid
 }
index 0e0bb8da81e4333fef877dc656fc36225f345a13..f94dfd100a6f4dff17580d211659a5e2ee014fd3 100644 (file)
@@ -207,15 +207,15 @@ LL |     let _ = cf as *const [u16];
 error[E0606]: casting `*const dyn Foo` as `*const dyn Bar` is invalid
   --> $DIR/cast-rfc0401.rs:69:13
    |
-LL |     let _ = cf as *const Bar;
-   |             ^^^^^^^^^^^^^^^^
+LL |     let _ = cf as *const dyn Bar;
+   |             ^^^^^^^^^^^^^^^^^^^^
    |
    = note: vtable kinds may not match
 
 error[E0277]: the size for values of type `[u8]` cannot be known at compilation time
   --> $DIR/cast-rfc0401.rs:53:13
    |
-LL |     let _ = fat_v as *const Foo;
+LL |     let _ = fat_v as *const dyn Foo;
    |             ^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `[u8]`
@@ -225,7 +225,7 @@ LL |     let _ = fat_v as *const Foo;
 error[E0277]: the size for values of type `str` cannot be known at compilation time
   --> $DIR/cast-rfc0401.rs:62:13
    |
-LL |     let _ = a as *const Foo;
+LL |     let _ = a as *const dyn Foo;
    |             ^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `str`
index 030b7a40ca6fed0a6b032ba0d2b386ce8cb81a57..eae6a87905b33de42ec814cdcc35a87f7f5e23df 100644 (file)
@@ -1,7 +1,7 @@
 trait Trait { }
 
-fn function(t: &mut Trait) {
-    t as *mut Trait
+fn function(t: &mut dyn Trait) {
+    t as *mut dyn Trait
  //~^ ERROR: mismatched types
 }
 
index db2d484edff0710bf81a5757eca058fa0efafac5..b826ca66c683a409756422ca860f96114dd979f8 100644 (file)
@@ -1,10 +1,10 @@
 error[E0308]: mismatched types
   --> $DIR/issue-19109.rs:4:5
    |
-LL | fn function(t: &mut Trait) {
-   |                            - help: try adding a return type: `-> *mut dyn Trait`
-LL |     t as *mut Trait
-   |     ^^^^^^^^^^^^^^^ expected (), found *-ptr
+LL | fn function(t: &mut dyn Trait) {
+   |                                - help: try adding a return type: `-> *mut dyn Trait`
+LL |     t as *mut dyn Trait
+   |     ^^^^^^^^^^^^^^^^^^^ expected (), found *-ptr
    |
    = note: expected type `()`
               found type `*mut dyn Trait`
index be5fab871b42f2be89956cf33d900a1c380b04c6..882533992bd3c82b37b7f0152d2c55cb08008968 100644 (file)
@@ -2,14 +2,14 @@ trait Foo {
     fn dummy(&self) { }
 }
 
-fn a(_x: Box<Foo+Send>) {
+fn a(_x: Box<dyn Foo + Send>) {
 }
 
-fn c(x: Box<Foo+Sync+Send>) {
+fn c(x: Box<dyn Foo + Sync + Send>) {
     a(x);
 }
 
-fn d(x: Box<Foo>) {
+fn d(x: Box<dyn Foo>) {
     a(x); //~ ERROR mismatched types [E0308]
 }
 
index 3fa11878629c32079a1901196ddccedca8807947..0385a120ce21314996a1859ee31aea166360d965 100644 (file)
@@ -6,7 +6,7 @@ struct R<'a> {
     // This struct is needed to create the
     // otherwise infinite type of a fn that
     // accepts itself as argument:
-    c: Box<FnMut(&mut R, bool) + 'a>
+    c: Box<dyn FnMut(&mut R, bool) + 'a>
 }
 
 fn innocent_looking_victim() {
index e8e571aadc3680de679abe85fe1dc0319fd81427..a7be365bde4bdf78c9c4da1d8b0d9a45b25e4454 100644 (file)
@@ -10,7 +10,7 @@ fn main() {
     let _ = {
         let tmp0 = 3;
         let tmp1 = &tmp0;
-        box tmp1 as Box<Foo + '_>
+        box tmp1 as Box<dyn Foo + '_>
     };
     //~^^^ ERROR `tmp0` does not live long enough
 }
index 9262117f397553efdae9e8d3539dcc52fd5fecff..b71893de7f8bdca925bcf391dac445e1908dd97a 100644 (file)
@@ -3,8 +3,8 @@ error[E0597]: `tmp0` does not live long enough
    |
 LL |         let tmp1 = &tmp0;
    |                    ^^^^^ borrowed value does not live long enough
-LL |         box tmp1 as Box<Foo + '_>
-   |         ------------------------- borrow later captured here by trait object
+LL |         box tmp1 as Box<dyn Foo + '_>
+   |         ----------------------------- borrow later captured here by trait object
 LL |     };
    |     - `tmp0` dropped here while still borrowed
 
index cea458dcb65b92460b2ece1f38f46d9728a87600..81c50edfed1a4e3fd21ea5fba04733e9b0617127 100644 (file)
@@ -14,11 +14,11 @@ trait AnyVec<'a> {
 }
 
 trait GenericVec<T> {
-    fn unwrap<'a, 'b>(vec: &'b AnyVec<'a>) -> &'b [T] where T: 'a;
+    fn unwrap<'a, 'b>(vec: &'b dyn AnyVec<'a>) -> &'b [T] where T: 'a;
 }
 
 struct Scratchpad<'a> {
-    buffers: RefCell<Box<AnyVec<'a>>>,
+    buffers: RefCell<Box<dyn AnyVec<'a>>>,
 }
 
 impl<'a> Scratchpad<'a> {
index 2d72b4588f754e5218c18f006a889cebaa660770..104e7b2e2155914af4dd743482693cadc8570eda 100644 (file)
@@ -3,6 +3,6 @@
 
 trait Foo {}
 fn take_foo<F:Foo>(f: F) {}
-fn take_object(f: Box<Foo>) { take_foo(f); }
+fn take_object(f: Box<dyn Foo>) { take_foo(f); }
 //~^ ERROR `std::boxed::Box<dyn Foo>: Foo` is not satisfied
 fn main() {}
index 0e28875ced63aee5fe359a3582300a46e766895a..288ce9682c2097d8d1956cbf3c239e905258a0d2 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the trait bound `std::boxed::Box<dyn Foo>: Foo` is not satisfied
-  --> $DIR/object-does-not-impl-trait.rs:6:31
+  --> $DIR/object-does-not-impl-trait.rs:6:35
    |
-LL | fn take_object(f: Box<Foo>) { take_foo(f); }
-   |                               ^^^^^^^^ the trait `Foo` is not implemented for `std::boxed::Box<dyn Foo>`
+LL | fn take_object(f: Box<dyn Foo>) { take_foo(f); }
+   |                                   ^^^^^^^^ the trait `Foo` is not implemented for `std::boxed::Box<dyn Foo>`
    |
 note: required by `take_foo`
   --> $DIR/object-does-not-impl-trait.rs:5:1
index d14351aef9a48684810574158e529dfd67bd984f..5dae92fee5f90762fb21291e3c9f2e48fec899a2 100644 (file)
@@ -20,27 +20,27 @@ struct Ref2<'a,'b:'a,T:'a+'b+?Sized> {
     r: &'a &'b T
 }
 
-fn a<'a,'b>(t: Ref2<'a,'b,Test>) {
+fn a<'a,'b>(t: Ref2<'a,'b, dyn Test>) {
     //~^ ERROR lifetime bound for this object type cannot be deduced from context
 }
 
-fn b(t: Ref2<Test>) {
+fn b(t: Ref2<dyn Test>) {
     //~^ ERROR lifetime bound for this object type cannot be deduced from context
 }
 
-fn c(t: Ref2<&Test>) {
+fn c(t: Ref2<&dyn Test>) {
     // In this case, the &'a overrides.
 }
 
-fn d(t: Ref2<Ref1<Test>>) {
+fn d(t: Ref2<Ref1<dyn Test>>) {
     // In this case, the lifetime parameter from the Ref1 overrides.
 }
 
-fn e(t: Ref2<Ref0<Test>>) {
+fn e(t: Ref2<Ref0<dyn Test>>) {
     // In this case, Ref2 is ambiguous, but Ref0 overrides with 'static.
 }
 
-fn f(t: &Ref2<Test>) {
+fn f(t: &Ref2<dyn Test>) {
     //~^ ERROR lifetime bound for this object type cannot be deduced from context
 }
 
index 0319c7bfbe27233079cde514e44f22367f56b5ee..0c3dbffeea638ab119a05bd8b3f3dd05460ee1aa 100644 (file)
@@ -1,20 +1,20 @@
 error[E0228]: the lifetime bound for this object type cannot be deduced from context; please supply an explicit bound
-  --> $DIR/object-lifetime-default-ambiguous.rs:23:27
+  --> $DIR/object-lifetime-default-ambiguous.rs:23:28
    |
-LL | fn a<'a,'b>(t: Ref2<'a,'b,Test>) {
-   |                           ^^^^
+LL | fn a<'a,'b>(t: Ref2<'a,'b, dyn Test>) {
+   |                            ^^^^^^^^
 
 error[E0228]: the lifetime bound for this object type cannot be deduced from context; please supply an explicit bound
   --> $DIR/object-lifetime-default-ambiguous.rs:27:14
    |
-LL | fn b(t: Ref2<Test>) {
-   |              ^^^^
+LL | fn b(t: Ref2<dyn Test>) {
+   |              ^^^^^^^^
 
 error[E0228]: the lifetime bound for this object type cannot be deduced from context; please supply an explicit bound
   --> $DIR/object-lifetime-default-ambiguous.rs:43:15
    |
-LL | fn f(t: &Ref2<Test>) {
-   |               ^^^^
+LL | fn f(t: &Ref2<dyn Test>) {
+   |               ^^^^^^^^
 
 error: aborting due to 3 previous errors
 
index 19cdd66ef759c2ea1bf9bf211c7135b2d83c036b..e94f2a92125cd8a5cdb0b70fdb8fcf4df5e76eba 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/object-lifetime-default-elision.rs:71:5
    |
-LL | fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+LL | fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
    |          -- -- lifetime `'b` defined here
    |          |
    |          lifetime `'a` defined here
index cf15a4e8676bd6540d1f106a4f0fed955fe27cc5..dc42edfba2cc19e71775bbcb80af5586e1c8d2bb 100644 (file)
@@ -8,7 +8,7 @@ fn dummy(&self) { }
 }
 
 struct SomeStruct<'a> {
-    r: Box<SomeTrait+'a>
+    r: Box<dyn SomeTrait+'a>
 }
 
 fn deref<T>(ss: &T) -> T {
@@ -17,7 +17,7 @@ fn deref<T>(ss: &T) -> T {
     loop { }
 }
 
-fn load0<'a>(ss: &'a Box<SomeTrait>) -> Box<SomeTrait> {
+fn load0<'a>(ss: &'a Box<dyn SomeTrait>) -> Box<dyn SomeTrait> {
     // Under old rules, the fully elaborated types of input/output were:
     //
     // for<'a,'b> fn(&'a Box<SomeTrait+'b>) -> Box<SomeTrait+'a>
@@ -31,7 +31,7 @@ fn load0<'a>(ss: &'a Box<SomeTrait>) -> Box<SomeTrait> {
     deref(ss)
 }
 
-fn load1(ss: &SomeTrait) -> &SomeTrait {
+fn load1(ss: &dyn SomeTrait) -> &dyn SomeTrait {
     // Under old rules, the fully elaborated types of input/output were:
     //
     // for<'a,'b> fn(&'a (SomeTrait+'b)) -> &'a (SomeTrait+'a)
@@ -45,13 +45,13 @@ fn load1(ss: &SomeTrait) -> &SomeTrait {
     ss
 }
 
-fn load2<'a>(ss: &'a SomeTrait) -> &SomeTrait {
+fn load2<'a>(ss: &'a dyn SomeTrait) -> &dyn SomeTrait {
     // Same as `load1` but with an explicit name thrown in for fun.
 
     ss
 }
 
-fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
     // Under old rules, the fully elaborated types of input/output were:
     //
     // for<'a,'b,'c>fn(&'a (SomeTrait+'c)) -> &'b (SomeTrait+'a)
index dcb07a1706f35825d10f1db7c16eae5cd71c47d5..2cdd6c5d890f2721ffa94bd6f70e351867e80a8c 100644 (file)
@@ -7,7 +7,7 @@ LL |     ss
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 54:10...
   --> $DIR/object-lifetime-default-elision.rs:54:10
    |
-LL | fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+LL | fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
    |          ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/object-lifetime-default-elision.rs:71:5
@@ -17,7 +17,7 @@ LL |     ss
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 54:13...
   --> $DIR/object-lifetime-default-elision.rs:54:13
    |
-LL | fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+LL | fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
    |             ^^
    = note: ...so that the expression is assignable:
            expected &'b (dyn SomeTrait + 'b)
@@ -32,7 +32,7 @@ LL |     ss
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 54:10...
   --> $DIR/object-lifetime-default-elision.rs:54:10
    |
-LL | fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+LL | fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
    |          ^^
 note: ...so that the declared lifetime parameter bounds are satisfied
   --> $DIR/object-lifetime-default-elision.rs:71:5
@@ -42,7 +42,7 @@ LL |     ss
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 54:13...
   --> $DIR/object-lifetime-default-elision.rs:54:13
    |
-LL | fn load3<'a,'b>(ss: &'a SomeTrait) -> &'b SomeTrait {
+LL | fn load3<'a,'b>(ss: &'a dyn SomeTrait) -> &'b dyn SomeTrait {
    |             ^^
    = note: ...so that the expression is assignable:
            expected &'b (dyn SomeTrait + 'b)
index 9e68647214c277e939417ea3ba34235c32596155..17fb7c4acdffdac4d471158be880cd4c96feeb85 100644 (file)
@@ -1,7 +1,7 @@
 error[E0621]: explicit lifetime required in the type of `ss`
   --> $DIR/object-lifetime-default-from-box-error.rs:18:5
    |
-LL | fn load(ss: &mut SomeStruct) -> Box<SomeTrait> {
+LL | fn load(ss: &mut SomeStruct) -> Box<dyn SomeTrait> {
    |             --------------- help: add explicit lifetime `'static` to the type of `ss`: `&mut SomeStruct<'static>`
 ...
 LL |     ss.r
@@ -16,7 +16,7 @@ LL |     ss.r
 error[E0621]: explicit lifetime required in the type of `ss`
   --> $DIR/object-lifetime-default-from-box-error.rs:31:5
    |
-LL | fn store1<'b>(ss: &mut SomeStruct, b: Box<SomeTrait+'b>) {
+LL | fn store1<'b>(ss: &mut SomeStruct, b: Box<dyn SomeTrait+'b>) {
    |                   --------------- help: add explicit lifetime `'b` to the type of `ss`: `&mut SomeStruct<'b>`
 ...
 LL |     ss.r = b;
index b6d72f1fce3ffe671854e021da914ba5f82a4cb2..587aab1edce385f9ac305532bb77e93d613ff216 100644 (file)
@@ -8,24 +8,24 @@ fn dummy(&self) { }
 }
 
 struct SomeStruct<'a> {
-    r: Box<SomeTrait+'a>
+    r: Box<dyn SomeTrait+'a>
 }
 
-fn load(ss: &mut SomeStruct) -> Box<SomeTrait> {
+fn load(ss: &mut SomeStruct) -> Box<dyn SomeTrait> {
     // `Box<SomeTrait>` defaults to a `'static` bound, so this return
     // is illegal.
 
     ss.r //~ ERROR explicit lifetime required in the type of `ss` [E0621]
 }
 
-fn store(ss: &mut SomeStruct, b: Box<SomeTrait>) {
+fn store(ss: &mut SomeStruct, b: Box<dyn SomeTrait>) {
     // No error: b is bounded by 'static which outlives the
     // (anonymous) lifetime on the struct.
 
     ss.r = b;
 }
 
-fn store1<'b>(ss: &mut SomeStruct, b: Box<SomeTrait+'b>) {
+fn store1<'b>(ss: &mut SomeStruct, b: Box<dyn SomeTrait+'b>) {
     // Here we override the lifetimes explicitly, and so naturally we get an error.
 
     ss.r = b; //~ ERROR explicit lifetime required in the type of `ss` [E0621]
index 0077c95139f4b22938a52789386ffeba6f2b48ef..78e4bdd374da96b8cd379b0675bef12c2bf09c1e 100644 (file)
@@ -1,7 +1,7 @@
 error[E0621]: explicit lifetime required in the type of `ss`
   --> $DIR/object-lifetime-default-from-box-error.rs:18:5
    |
-LL | fn load(ss: &mut SomeStruct) -> Box<SomeTrait> {
+LL | fn load(ss: &mut SomeStruct) -> Box<dyn SomeTrait> {
    |             --------------- help: add explicit lifetime `'static` to the type of `ss`: `&mut SomeStruct<'static>`
 ...
 LL |     ss.r
@@ -10,7 +10,7 @@ LL |     ss.r
 error[E0621]: explicit lifetime required in the type of `ss`
   --> $DIR/object-lifetime-default-from-box-error.rs:31:12
    |
-LL | fn store1<'b>(ss: &mut SomeStruct, b: Box<SomeTrait+'b>) {
+LL | fn store1<'b>(ss: &mut SomeStruct, b: Box<dyn SomeTrait+'b>) {
    |                   --------------- help: add explicit lifetime `'b` to the type of `ss`: `&mut SomeStruct<'b>`
 ...
 LL |     ss.r = b;
index 6d183ddf22d19902e9d028cbbf49cdca23b33fe8..7d6f9f39d13ed278f4bbab199300d749fd7c5acd 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/object-lifetime-default-from-rptr-box-error.rs:15:5
    |
-LL | fn c<'a>(t: &'a Box<Test+'a>, mut ss: SomeStruct<'a>) {
+LL | fn c<'a>(t: &'a Box<dyn Test+'a>, mut ss: SomeStruct<'a>) {
    |      -- lifetime `'a` defined here
 LL |     ss.t = t;
    |     ^^^^^^^^ assignment requires that `'a` must outlive `'static`
index 91b384e00713b08d55f57bbc62bd314ec8ac4741..bf9e0beb57cdf8157393bc6646763520afd5800f 100644 (file)
@@ -8,10 +8,10 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a Box<Test>,
+    t: &'a Box<dyn Test>,
 }
 
-fn c<'a>(t: &'a Box<Test+'a>, mut ss: SomeStruct<'a>) {
+fn c<'a>(t: &'a Box<dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.t = t; //~ ERROR mismatched types
 }
 
index d7e3a171333ecf3dd3cbdcad2f28db1ca07f6288..4f9cef12c5ef29ae0e29a944b06a91df91a9ef10 100644 (file)
@@ -9,7 +9,7 @@ LL |     ss.t = t;
 note: the lifetime 'a as defined on the function body at 14:6...
   --> $DIR/object-lifetime-default-from-rptr-box-error.rs:14:6
    |
-LL | fn c<'a>(t: &'a Box<Test+'a>, mut ss: SomeStruct<'a>) {
+LL | fn c<'a>(t: &'a Box<dyn Test+'a>, mut ss: SomeStruct<'a>) {
    |      ^^
    = note: ...does not necessarily outlive the static lifetime
 
index fe3b21fa39c57381118da02fb55161840649eec2..6df54638ce00425262306af2cad2ea9af9538321 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/object-lifetime-default-from-rptr-struct-error.rs:21:5
    |
-LL | fn c<'a>(t: &'a MyBox<Test+'a>, mut ss: SomeStruct<'a>) {
+LL | fn c<'a>(t: &'a MyBox<dyn Test+'a>, mut ss: SomeStruct<'a>) {
    |      -- lifetime `'a` defined here
 LL |     ss.t = t;
    |     ^^^^^^^^ assignment requires that `'a` must outlive `'static`
index 6a84621f59e440044b57078b9c77402decab792d..ae2878539cfd1875d316219a73549e7ea161769d 100644 (file)
@@ -9,15 +9,15 @@ fn foo(&self) { }
 }
 
 struct SomeStruct<'a> {
-    t: &'a MyBox<Test>,
-    u: &'a MyBox<Test+'a>,
+    t: &'a MyBox<dyn Test>,
+    u: &'a MyBox<dyn Test + 'a>,
 }
 
 struct MyBox<T:?Sized> {
     b: Box<T>
 }
 
-fn c<'a>(t: &'a MyBox<Test+'a>, mut ss: SomeStruct<'a>) {
+fn c<'a>(t: &'a MyBox<dyn Test+'a>, mut ss: SomeStruct<'a>) {
     ss.t = t; //~ ERROR mismatched types
 }
 
index 4d082530dc528168b2dab437210a1a9e058f0ffe..3b7faee68aaba5a1fae9373e5014e5c26f8d6e1c 100644 (file)
@@ -9,7 +9,7 @@ LL |     ss.t = t;
 note: the lifetime 'a as defined on the function body at 20:6...
   --> $DIR/object-lifetime-default-from-rptr-struct-error.rs:20:6
    |
-LL | fn c<'a>(t: &'a MyBox<Test+'a>, mut ss: SomeStruct<'a>) {
+LL | fn c<'a>(t: &'a MyBox<dyn Test+'a>, mut ss: SomeStruct<'a>) {
    |      ^^
    = note: ...does not necessarily outlive the static lifetime
 
index 448fe9e55109c199d726f3d5175ae8fe9f5b6924..cdfbf0fc878cfdc5abd11fd78261c1961b640bdf 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/object-lifetime-default-mybox.rs:27:5
    |
-LL | fn load1<'a,'b>(a: &'a MyBox<SomeTrait>,
+LL | fn load1<'a,'b>(a: &'a MyBox<dyn SomeTrait>,
    |          -- -- lifetime `'b` defined here
    |          |
    |          lifetime `'a` defined here
@@ -12,7 +12,7 @@ LL |     a
 error[E0521]: borrowed data escapes outside of function
   --> $DIR/object-lifetime-default-mybox.rs:31:5
    |
-LL | fn load2<'a>(ss: &MyBox<SomeTrait+'a>) -> MyBox<SomeTrait+'a> {
+LL | fn load2<'a>(ss: &MyBox<dyn SomeTrait + 'a>) -> MyBox<dyn SomeTrait + 'a> {
    |              -- `ss` is a reference that is only valid in the function body
 LL |     load0(ss)
    |     ^^^^^^^^^ `ss` escapes the function body here
index c94df82a177599fd41adc049f68973cec9d2b38e..eb27fe90f47ce63c1310fbd5048f4ac5a9b0f24a 100644 (file)
@@ -16,18 +16,18 @@ fn deref<T>(ss: &T) -> T {
     loop { }
 }
 
-fn load0(ss: &MyBox<SomeTrait>) -> MyBox<SomeTrait> {
+fn load0(ss: &MyBox<dyn SomeTrait>) -> MyBox<dyn SomeTrait> {
     deref(ss)
 }
 
-fn load1<'a,'b>(a: &'a MyBox<SomeTrait>,
-                b: &'b MyBox<SomeTrait>)
-                -> &'b MyBox<SomeTrait>
+fn load1<'a,'b>(a: &'a MyBox<dyn SomeTrait>,
+                b: &'b MyBox<dyn SomeTrait>)
+                -> &'b MyBox<dyn SomeTrait>
 {
     a //~ ERROR lifetime mismatch
 }
 
-fn load2<'a>(ss: &MyBox<SomeTrait+'a>) -> MyBox<SomeTrait+'a> {
+fn load2<'a>(ss: &MyBox<dyn SomeTrait + 'a>) -> MyBox<dyn SomeTrait + 'a> {
     load0(ss) //~ ERROR mismatched types
 }
 
index 4c23f867be81d45bc6bb5187f7aed211aa2480dc..928b9201982325d40f99f17496fe02f24dba9805 100644 (file)
@@ -1,11 +1,11 @@
 error[E0623]: lifetime mismatch
   --> $DIR/object-lifetime-default-mybox.rs:27:5
    |
-LL | fn load1<'a,'b>(a: &'a MyBox<SomeTrait>,
-   |                    -------------------- this parameter and the return type are declared with different lifetimes...
-LL |                 b: &'b MyBox<SomeTrait>)
-LL |                 -> &'b MyBox<SomeTrait>
-   |                    --------------------
+LL | fn load1<'a,'b>(a: &'a MyBox<dyn SomeTrait>,
+   |                    ------------------------ this parameter and the return type are declared with different lifetimes...
+LL |                 b: &'b MyBox<dyn SomeTrait>)
+LL |                 -> &'b MyBox<dyn SomeTrait>
+   |                    ------------------------
 LL | {
 LL |     a
    |     ^ ...but data from `a` is returned here
@@ -21,7 +21,7 @@ LL |     load0(ss)
 note: the lifetime 'a as defined on the function body at 30:10...
   --> $DIR/object-lifetime-default-mybox.rs:30:10
    |
-LL | fn load2<'a>(ss: &MyBox<SomeTrait+'a>) -> MyBox<SomeTrait+'a> {
+LL | fn load2<'a>(ss: &MyBox<dyn SomeTrait + 'a>) -> MyBox<dyn SomeTrait + 'a> {
    |          ^^
    = note: ...does not necessarily outlive the static lifetime
 
index a8a482fb5a6c3bee1ce741a2ad34c4132ace5c63..760a50e5b79723df596230c9307b18b5050bf813 100644 (file)
@@ -5,19 +5,19 @@ trait Foo {
     fn owned(self: Box<Self>);
 }
 
-fn borrowed_receiver(x: &Foo) {
+fn borrowed_receiver(x: &dyn Foo) {
     x.borrowed();
     x.borrowed_mut(); // See [1]
     x.owned(); //~ ERROR no method named `owned` found
 }
 
-fn borrowed_mut_receiver(x: &mut Foo) {
+fn borrowed_mut_receiver(x: &mut dyn Foo) {
     x.borrowed();
     x.borrowed_mut();
     x.owned(); //~ ERROR no method named `owned` found
 }
 
-fn owned_receiver(x: Box<Foo>) {
+fn owned_receiver(x: Box<dyn Foo>) {
     x.borrowed();
     x.borrowed_mut(); // See [1]
     x.managed();  //~ ERROR no method named `managed` found
index 79b7e541af82ae6740b5c262921a2612913c43c1..5900019ea915ae298e285c29a7d636c5bb1b951f 100644 (file)
@@ -6,7 +6,7 @@ trait Bar {
     const X: usize;
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
     //~^ ERROR E0038
     t
 }
index 96962c10720a26e7e9903d5834176bb6c806fde1..55f9e3f9f138bd812f8dbe6d19fcdeec9a13ceb1 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-associated-consts.rs:9:1
    |
-LL | fn make_bar<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: the trait cannot contain associated consts like `X`
 
index 0b70c8ad45e7de831b79c126e21fccc185134fbb..f903f26c0901dbc7af648f026080d3ade319ec5b 100644 (file)
@@ -11,7 +11,7 @@ trait Baz {
     fn baz(self: Self);
 }
 
-fn use_bar(t: Box<Bar>) {
+fn use_bar(t: Box<dyn Bar>) {
     t.bar() //~ ERROR cannot move a value of type dyn Bar
 }
 
index dee31f6e370f9ad35c2ea2edd1552fee6810b834..a8b1ddfaba7f12075ff14e74f36376bba413deb0 100644 (file)
@@ -17,28 +17,28 @@ trait Quux {
     fn baz(self: Self) where Self : Sized;
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
     t // legal
 }
 
-fn make_bar_explicit<T:Bar>(t: &T) -> &Bar {
-    t as &Bar // legal
+fn make_bar_explicit<T:Bar>(t: &T) -> &dyn Bar {
+    t as &dyn Bar // legal
 }
 
-fn make_baz<T:Baz>(t: &T) -> &Baz {
+fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
     t // legal
 }
 
-fn make_baz_explicit<T:Baz>(t: &T) -> &Baz {
-    t as &Baz // legal
+fn make_baz_explicit<T:Baz>(t: &T) -> &dyn Baz {
+    t as &dyn Baz // legal
 }
 
-fn make_quux<T:Quux>(t: &T) -> &Quux {
+fn make_quux<T:Quux>(t: &T) -> &dyn Quux {
     t
 }
 
-fn make_quux_explicit<T:Quux>(t: &T) -> &Quux {
-    t as &Quux
+fn make_quux_explicit<T:Quux>(t: &T) -> &dyn Quux {
+    t as &dyn Quux
 }
 
 
index 5f4aabf5469cbb790424b9ab763d0d1ef9d98007..d63ea28c8f2275e17393ac877cd9f6b016872b99 100644 (file)
@@ -11,22 +11,22 @@ fn bar<T>(&self, t: T)
         where Self : Sized;
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
         //~^ ERROR E0038
     t
 }
 
-fn make_bar_explicit<T:Bar>(t: &T) -> &Bar {
+fn make_bar_explicit<T:Bar>(t: &T) -> &dyn Bar {
     //~^ ERROR E0038
-    t as &Bar
+    t as &dyn Bar
 }
 
-fn make_quux<T:Quux>(t: &T) -> &Quux {
+fn make_quux<T:Quux>(t: &T) -> &dyn Quux {
     t
 }
 
-fn make_quux_explicit<T:Quux>(t: &T) -> &Quux {
-    t as &Quux
+fn make_quux_explicit<T:Quux>(t: &T) -> &dyn Quux {
+    t as &dyn Quux
 }
 
 fn main() {
index 7ae44794ceba9bbd483a31f245a2e17e4f8e3eeb..d66cdb98448d4edddb36b7f04a72e90645705553 100644 (file)
@@ -1,16 +1,16 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-generics.rs:14:1
    |
-LL | fn make_bar<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `bar` has generic type parameters
 
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-generics.rs:19:1
    |
-LL | fn make_bar_explicit<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar_explicit<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `bar` has generic type parameters
 
index eb28fcf0d5af246ae50b9fc9c92193956cd8a461..1fc5c5442c21ba0120cefcbf198874f03d11bb24 100644 (file)
@@ -9,7 +9,7 @@ trait Expr: Debug + PartialEq {
 //#[derive(PartialEq)]
 #[derive(Debug)]
 struct SExpr<'x> {
-    elements: Vec<Box<Expr+ 'x>>,
+    elements: Vec<Box<dyn Expr + 'x>>,
     //~^ ERROR E0038
 }
 
@@ -35,8 +35,8 @@ fn print_element_count(&self) {
 }
 
 fn main() {
-    let a: Box<Expr> = Box::new(SExpr::new());
-    let b: Box<Expr> = Box::new(SExpr::new());
+    let a: Box<dyn Expr> = Box::new(SExpr::new());
+    let b: Box<dyn Expr> = Box::new(SExpr::new());
 
     // assert_eq!(a , b);
 }
index 85721f1a5f81c3e71a04ef30fa5f39a135d08309..1f5c472ddc25a8870c973ade873f3fafc557ec82 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Expr` cannot be made into an object
   --> $DIR/object-safety-issue-22040.rs:12:23
    |
-LL |     elements: Vec<Box<Expr+ 'x>>,
-   |                       ^^^^^^^^ the trait `Expr` cannot be made into an object
+LL |     elements: Vec<Box<dyn Expr + 'x>>,
+   |                       ^^^^^^^^^^^^^ the trait `Expr` cannot be made into an object
    |
    = note: the trait cannot use `Self` as a type parameter in the supertraits or where-clauses
 
index 8e1bd83cec00a37c032bf380d89ae0ea87c03fbf..f13ffe53626702a14903dc82717e66dc1f40e78e 100644 (file)
@@ -14,22 +14,22 @@ trait Quux {
     fn get(&self, s: &Self) -> Self where Self : Sized;
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
         //~^ ERROR E0038
     loop { }
 }
 
-fn make_baz<T:Baz>(t: &T) -> &Baz {
+fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
         //~^ ERROR E0038
     t
 }
 
-fn make_quux<T:Quux>(t: &T) -> &Quux {
+fn make_quux<T:Quux>(t: &T) -> &dyn Quux {
     t
 }
 
-fn make_quux_explicit<T:Quux>(t: &T) -> &Quux {
-    t as &Quux
+fn make_quux_explicit<T:Quux>(t: &T) -> &dyn Quux {
+    t as &dyn Quux
 }
 
 fn main() {
index ed3aed983cf7a55a0dbd1137651aa9b0ccddc6c2..c0c471c2b1e72893489503629c638005fc371d3e 100644 (file)
@@ -1,16 +1,16 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-mentions-Self.rs:17:1
    |
-LL | fn make_bar<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: method `bar` references the `Self` type in its arguments or return type
 
 error[E0038]: the trait `Baz` cannot be made into an object
   --> $DIR/object-safety-mentions-Self.rs:22:1
    |
-LL | fn make_baz<T:Baz>(t: &T) -> &Baz {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Baz` cannot be made into an object
+LL | fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Baz` cannot be made into an object
    |
    = note: method `bar` references the `Self` type in its arguments or return type
 
index 4faf9386f9a8b2f4172e9b7aac2f5af62bbeedff..55d31ce80876954ca50650ba7824a1dc4aabbee0 100644 (file)
@@ -5,7 +5,7 @@ trait Foo {
     fn foo();
 }
 
-fn foo_implicit<T:Foo+'static>(b: Box<T>) -> Box<Foo+'static> {
+fn foo_implicit<T:Foo+'static>(b: Box<T>) -> Box<dyn Foo + 'static> {
     //~^ ERROR E0038
     loop { }
 }
index 3b8ccb594c181ecd3aeb79851871f4fc48411bcb..da8dd657c2a9d926647329631bbcd0f368cca299 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/object-safety-no-static.rs:8:1
    |
-LL | fn foo_implicit<T:Foo+'static>(b: Box<T>) -> Box<Foo+'static> {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` cannot be made into an object
+LL | fn foo_implicit<T:Foo+'static>(b: Box<T>) -> Box<dyn Foo + 'static> {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` cannot be made into an object
    |
    = note: method `foo` has no receiver
 
index f8875e4995b445679cf636756638e1affe0e067c..59ed12c78f0268f859605d75a2a5fe4ba6323ad2 100644 (file)
@@ -9,11 +9,11 @@ trait Baz {
 trait Bar<T> {
 }
 
-fn make_bar<T:Bar<u32>>(t: &T) -> &Bar<u32> {
+fn make_bar<T:Bar<u32>>(t: &T) -> &dyn Bar<u32> {
     t
 }
 
-fn make_baz<T:Baz>(t: &T) -> &Baz {
+fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
     t
 }
 
index baeb3734677fb25711b1d4fd8c3139c52636e112..7235b22404e29108f7240ab5e178f2890bc85492 100644 (file)
@@ -7,7 +7,7 @@ trait Bar
     fn bar<T>(&self, t: T);
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
         //~^ ERROR E0038
     loop { }
 }
index 2b8bfa341d79693510ff4c6cba22f492a709573d..dcaf2ff0bc294be2390a908542f5ddd007139ef3 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-sized-2.rs:10:1
    |
-LL | fn make_bar<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
 
index 77dc7390aff015ed876ab868663b52fba9f5707b..1312bb34717ee87a85e992b64e73ba4e1134046a 100644 (file)
@@ -5,7 +5,7 @@ trait Bar : Sized {
     fn bar<T>(&self, t: T);
 }
 
-fn make_bar<T:Bar>(t: &T) -> &Bar {
+fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
         //~^ ERROR E0038
     t
 }
index ba98e2f1ef65520629dbcdd467fc922598c7e881..98bc73e38d4cc4fd9f969a4bce90f77b3e5f35bb 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Bar` cannot be made into an object
   --> $DIR/object-safety-sized.rs:8:1
    |
-LL | fn make_bar<T:Bar>(t: &T) -> &Bar {
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
+LL | fn make_bar<T:Bar>(t: &T) -> &dyn Bar {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Bar` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
 
index 9d0da4e327c7c0edcc7c9c7f1371459f91df0a20..2445b33c814472cba1924c81573ceb9edd7bc0f9 100644 (file)
@@ -8,11 +8,11 @@ trait Bar<T> {
 trait Baz : Bar<Self> {
 }
 
-fn make_bar<T:Bar<u32>>(t: &T) -> &Bar<u32> {
+fn make_bar<T:Bar<u32>>(t: &T) -> &dyn Bar<u32> {
     t
 }
 
-fn make_baz<T:Baz>(t: &T) -> &Baz {
+fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
     //~^ ERROR E0038
     t
 }
index 5db34a23fff64af227ce87bfe4e8ea9924b90a11..8ae89832703d1d9e3f6c6e509403fe93b7770503 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Baz` cannot be made into an object
   --> $DIR/object-safety-supertrait-mentions-Self.rs:15:31
    |
-LL | fn make_baz<T:Baz>(t: &T) -> &Baz {
-   |                               ^^^ the trait `Baz` cannot be made into an object
+LL | fn make_baz<T:Baz>(t: &T) -> &dyn Baz {
+   |                               ^^^^^^^ the trait `Baz` cannot be made into an object
    |
    = note: the trait cannot use `Self` as a type parameter in the supertraits or where-clauses
 
index cc86879bf461add49e3b7a84e2b43ce69d1ddbe9..1e0f9e40cdca67b6654079a59d4dad6b077e03a5 100644 (file)
@@ -1,5 +1,7 @@
 // compile-pass
 
+#![allow(bare_trait_objects)]
+
 type A = Box<(Fn(u8) -> u8) + 'static + Send + Sync>; // OK (but see #39318)
 
 fn main() {}
index 153f942b978a88d979c8d6e6ce4b94853dc1fa2d..89a2953ad0fd4a1721655a7e27f76f2812dbe924 100644 (file)
@@ -2,6 +2,7 @@
 // compile-flags: -Z continue-parse-after-error
 
 #![feature(box_syntax)]
+#![allow(bare_trait_objects)]
 
 use std::fmt::Debug;
 
index 0f1f49a521bd651f8e3f6429717abc9ebb889cae..e81b019b6468fa955758877e4db374129d288797 100644 (file)
@@ -1,6 +1,7 @@
 // compile-flags: -Z continue-parse-after-error
 
 #![feature(optin_builtin_traits)]
+#![allow(bare_trait_objects)]
 
 auto trait Auto {}
 
index 74e484eebee1fba6157ff8c06648c6a1df2ac8e9..a36727ffeaf103158e827766035c5730e3d4394a 100644 (file)
@@ -1,23 +1,23 @@
 error[E0178]: expected a path on the left-hand side of `+`, not `((Auto))`
-  --> $DIR/trait-object-bad-parens.rs:8:16
+  --> $DIR/trait-object-bad-parens.rs:9:16
    |
 LL |     let _: Box<((Auto)) + Auto>;
    |                ^^^^^^^^^^^^^^^ expected a path
 
 error[E0178]: expected a path on the left-hand side of `+`, not `(Auto + Auto)`
-  --> $DIR/trait-object-bad-parens.rs:10:16
+  --> $DIR/trait-object-bad-parens.rs:11:16
    |
 LL |     let _: Box<(Auto + Auto) + Auto>;
    |                ^^^^^^^^^^^^^^^^^^^^ expected a path
 
 error[E0178]: expected a path on the left-hand side of `+`, not `(Auto)`
-  --> $DIR/trait-object-bad-parens.rs:12:16
+  --> $DIR/trait-object-bad-parens.rs:13:16
    |
 LL |     let _: Box<(Auto +) + Auto>;
    |                ^^^^^^^^^^^^^^^ expected a path
 
 error[E0178]: expected a path on the left-hand side of `+`, not `(dyn Auto)`
-  --> $DIR/trait-object-bad-parens.rs:14:16
+  --> $DIR/trait-object-bad-parens.rs:15:16
    |
 LL |     let _: Box<(dyn Auto) + Auto>;
    |                ^^^^^^^^^^^^^^^^^ expected a path
index 43f6497f7e71cfa2b7c59e8e81aacadd2431e31d..d5598afd6f4fdffcfd2e757f7ea61ed0d8ffaf51 100644 (file)
@@ -1,5 +1,7 @@
 // compile-flags: -Z continue-parse-after-error
 
+#![allow(bare_trait_objects)]
+
 trait Trait {}
 
 fn f<'a, T: Trait + ('a)>() {} //~ ERROR parenthesized lifetime bounds are not supported
index a31b7aea8fee6f9d0117aece4e62e45dfa6e2462..55f14c978760f7e790cdf69df1ac463e10f01911 100644 (file)
@@ -1,23 +1,23 @@
 error: parenthesized lifetime bounds are not supported
-  --> $DIR/trait-object-lifetime-parens.rs:5:21
+  --> $DIR/trait-object-lifetime-parens.rs:7:21
    |
 LL | fn f<'a, T: Trait + ('a)>() {}
    |                     ^^^^ help: remove the parentheses
 
 error: parenthesized lifetime bounds are not supported
-  --> $DIR/trait-object-lifetime-parens.rs:8:24
+  --> $DIR/trait-object-lifetime-parens.rs:10:24
    |
 LL |     let _: Box<Trait + ('a)>;
    |                        ^^^^ help: remove the parentheses
 
 error: expected `:`, found `)`
-  --> $DIR/trait-object-lifetime-parens.rs:9:19
+  --> $DIR/trait-object-lifetime-parens.rs:11:19
    |
 LL |     let _: Box<('a) + Trait>;
    |                   ^ expected `:`
 
 error: chained comparison operators require parentheses
-  --> $DIR/trait-object-lifetime-parens.rs:9:15
+  --> $DIR/trait-object-lifetime-parens.rs:11:15
    |
 LL |     let _: Box<('a) + Trait>;
    |               ^^^^^^^^^^^^^^^
@@ -26,7 +26,7 @@ LL |     let _: Box<('a) + Trait>;
    = help: or use `(...)` if you meant to specify fn arguments
 
 error: expected type, found `'a`
-  --> $DIR/trait-object-lifetime-parens.rs:9:17
+  --> $DIR/trait-object-lifetime-parens.rs:11:17
    |
 LL |     let _: Box<('a) + Trait>;
    |         -       ^^
index 40d2ad52c3574f3ffbad6267e0742ceaed226405..63425f3e2018679091e4740dbf143e3b564f266a 100644 (file)
@@ -1,3 +1,5 @@
+#![allow(bare_trait_objects)]
+
 trait Trait<'a> {}
 
 fn main() {
index 5e2a35ea60cb014bee44082b69aef0efafc79d07..a6add6079cecef3e9c71b86f49cbfd8133bacca1 100644 (file)
@@ -1,5 +1,5 @@
 error[E0178]: expected a path on the left-hand side of `+`, not `&for<'a> Trait<'a>`
-  --> $DIR/trait-object-polytrait-priority.rs:4:12
+  --> $DIR/trait-object-polytrait-priority.rs:6:12
    |
 LL |     let _: &for<'a> Trait<'a> + 'static;
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try adding parentheses: `&(for<'a> Trait<'a> + 'static)`
index 9ac10cd13279b3152748fb6fb135f6104c17402d..a113de14b6fbc5db9a01e8c6c2c61a8ca67de123 100644 (file)
@@ -5,8 +5,11 @@ fn f<T: (Copy) + (?Sized) + (for<'a> Trait<'a>)>() {}
 fn main() {
     let _: Box<(Copy) + (?Sized) + (for<'a> Trait<'a>)>;
     //~^ ERROR `?Trait` is not permitted in trait object types
+    //~| WARN trait objects without an explicit `dyn` are deprecated
     let _: Box<(?Sized) + (for<'a> Trait<'a>) + (Copy)>;
+    //~^ WARN trait objects without an explicit `dyn` are deprecated
     let _: Box<(for<'a> Trait<'a>) + (Copy) + (?Sized)>;
     //~^ ERROR use of undeclared lifetime name `'a`
     //~| ERROR `?Trait` is not permitted in trait object types
+    //~| WARN trait objects without an explicit `dyn` are deprecated
 }
index 36494b765394c225b83e97089f69c77e4082e074..e3fb8a0113a66dadea9dd203bbdad33ee52ca86b 100644 (file)
@@ -5,13 +5,33 @@ LL |     let _: Box<(Copy) + (?Sized) + (for<'a> Trait<'a>)>;
    |                         ^^^^^^^^
 
 error: `?Trait` is not permitted in trait object types
-  --> $DIR/trait-object-trait-parens.rs:9:47
+  --> $DIR/trait-object-trait-parens.rs:11:47
    |
 LL |     let _: Box<(for<'a> Trait<'a>) + (Copy) + (?Sized)>;
    |                                               ^^^^^^^^
 
+warning: trait objects without an explicit `dyn` are deprecated
+  --> $DIR/trait-object-trait-parens.rs:6:16
+   |
+LL |     let _: Box<(Copy) + (?Sized) + (for<'a> Trait<'a>)>;
+   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `dyn`: `dyn (Copy) + (?Sized) + (for<'a> Trait<'a>)`
+   |
+   = note: #[warn(bare_trait_objects)] on by default
+
+warning: trait objects without an explicit `dyn` are deprecated
+  --> $DIR/trait-object-trait-parens.rs:9:16
+   |
+LL |     let _: Box<(?Sized) + (for<'a> Trait<'a>) + (Copy)>;
+   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `dyn`: `dyn (?Sized) + (for<'a> Trait<'a>) + (Copy)`
+
+warning: trait objects without an explicit `dyn` are deprecated
+  --> $DIR/trait-object-trait-parens.rs:11:16
+   |
+LL |     let _: Box<(for<'a> Trait<'a>) + (Copy) + (?Sized)>;
+   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `dyn`: `dyn (for<'a> Trait<'a>) + (Copy) + (?Sized)`
+
 error[E0261]: use of undeclared lifetime name `'a`
-  --> $DIR/trait-object-trait-parens.rs:9:31
+  --> $DIR/trait-object-trait-parens.rs:11:31
    |
 LL |     let _: Box<(for<'a> Trait<'a>) + (Copy) + (?Sized)>;
    |                               ^^ undeclared lifetime
index 02fd92aa7a4ef95573d8ba68605b0bb030bbc644..8a59073fa6c7e589df1e2f492c04ad96f45ebaed 100644 (file)
@@ -4,7 +4,7 @@
 mod m {
     pub trait PubPrincipal {}
     auto trait PrivNonPrincipal {}
-    pub fn leak_dyn_nonprincipal() -> Box<PubPrincipal + PrivNonPrincipal> { loop {} }
+    pub fn leak_dyn_nonprincipal() -> Box<dyn PubPrincipal + PrivNonPrincipal> { loop {} }
 }
 
 fn main() {
index 5de5a685208cde885035827d35f66bf92231836a..5d89d8105b119ae43a2365981b10b1ecb8e14385 100644 (file)
@@ -3,7 +3,7 @@
 pub trait PubPrincipal {}
 auto trait PrivNonPrincipal {}
 
-pub fn leak_dyn_nonprincipal() -> Box<PubPrincipal + PrivNonPrincipal> { loop {} }
+pub fn leak_dyn_nonprincipal() -> Box<dyn PubPrincipal + PrivNonPrincipal> { loop {} }
 //~^ WARN private trait `PrivNonPrincipal` in public interface
 //~| WARN this was previously accepted
 
index 729b94ed8926afb856ac6adda80758a82e0e9a31..578f4380b4225fce8073304358a676697d14da0c 100644 (file)
@@ -1,8 +1,8 @@
 warning: private trait `PrivNonPrincipal` in public interface (error E0445)
   --> $DIR/private-in-public-non-principal.rs:6:1
    |
-LL | pub fn leak_dyn_nonprincipal() -> Box<PubPrincipal + PrivNonPrincipal> { loop {} }
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | pub fn leak_dyn_nonprincipal() -> Box<dyn PubPrincipal + PrivNonPrincipal> { loop {} }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: #[warn(private_in_public)] on by default
    = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
index d9bb421b53f8c5ccf9d10b2a2741d0bd37492f00..dab440b2d9910e7a7f85bc5b259eb83f665f5bc8 100644 (file)
@@ -65,9 +65,9 @@ pub fn leak_anon1() -> impl Trait + 'static { 0 }
     pub fn leak_anon2() -> impl TraitWithTyParam<Alias> { 0 }
     pub fn leak_anon3() -> impl TraitWithAssocTy<AssocTy = Alias> { 0 }
 
-    pub fn leak_dyn1() -> Box<Trait + 'static> { Box::new(0) }
-    pub fn leak_dyn2() -> Box<TraitWithTyParam<Alias>> { Box::new(0) }
-    pub fn leak_dyn3() -> Box<TraitWithAssocTy<AssocTy = Alias>> { Box::new(0) }
+    pub fn leak_dyn1() -> Box<dyn Trait + 'static> { Box::new(0) }
+    pub fn leak_dyn2() -> Box<dyn TraitWithTyParam<Alias>> { Box::new(0) }
+    pub fn leak_dyn3() -> Box<dyn TraitWithAssocTy<AssocTy = Alias>> { Box::new(0) }
 }
 
 mod adjust {
index 7b1eecd1558659f4665d2978d9839febc9074710..a3d4d23450ca6f1e44c346c667e1ad97bfef83cf 100644 (file)
@@ -1,14 +1,14 @@
-// aux-build:attr_proc_macro.rs
+// aux-build:test-macros.rs
 
-extern crate attr_proc_macro;
-use attr_proc_macro::*;
+#[macro_use]
+extern crate test_macros;
 
-#[attr_proc_macro] // OK
+#[identity_attr] // OK
 #[derive(Clone)]
 struct Before;
 
 #[derive(Clone)]
-#[attr_proc_macro] //~ ERROR macro attributes must be placed before `#[derive]`
+#[identity_attr] //~ ERROR macro attributes must be placed before `#[derive]`
 struct After;
 
 fn main() {}
index 39db45cf569a775d5421c49dd7be6af516d2d2c3..9ca8a443e40fbb5cf1fcb8015e279b10b4954ac6 100644 (file)
@@ -1,8 +1,8 @@
 error: macro attributes must be placed before `#[derive]`
   --> $DIR/attribute-order-restricted.rs:11:1
    |
-LL | #[attr_proc_macro]
-   | ^^^^^^^^^^^^^^^^^^
+LL | #[identity_attr]
+   | ^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index 2cced40830a7414ba0d15438c634f0d58015a0f3..aaa6c07dddbbd402440a524a6cf102cb813bcd1a 100644 (file)
@@ -1,12 +1,11 @@
-// aux-build:attribute-with-error.rs
+// aux-build:test-macros.rs
 
 #![feature(custom_inner_attributes)]
 
-extern crate attribute_with_error;
+#[macro_use]
+extern crate test_macros;
 
-use attribute_with_error::foo;
-
-#[foo]
+#[recollect_attr]
 fn test1() {
     let a: i32 = "foo";
     //~^ ERROR: mismatched types
@@ -15,13 +14,13 @@ fn test1() {
 }
 
 fn test2() {
-    #![foo]
+    #![recollect_attr]
 
     // FIXME: should have a type error here and assert it works but it doesn't
 }
 
 trait A {
-    // FIXME: should have a #[foo] attribute here and assert that it works
+    // FIXME: should have a #[recollect_attr] attribute here and assert that it works
     fn foo(&self) {
         let a: i32 = "foo";
         //~^ ERROR: mismatched types
@@ -31,13 +30,13 @@ fn foo(&self) {
 struct B;
 
 impl A for B {
-    #[foo]
+    #[recollect_attr]
     fn foo(&self) {
         let a: i32 = "foo";
         //~^ ERROR: mismatched types
     }
 }
 
-#[foo]
+#[recollect_attr]
 fn main() {
 }
index c5970ab6baaf865b586b049668d9f686cf24908c..937d47ff089798e66f2d8be8e423cbf76ed7e08f 100644 (file)
@@ -1,5 +1,5 @@
 error[E0308]: mismatched types
-  --> $DIR/attribute-with-error.rs:11:18
+  --> $DIR/attribute-with-error.rs:10:18
    |
 LL |     let a: i32 = "foo";
    |                  ^^^^^ expected i32, found reference
@@ -8,7 +8,7 @@ LL |     let a: i32 = "foo";
               found type `&'static str`
 
 error[E0308]: mismatched types
-  --> $DIR/attribute-with-error.rs:13:18
+  --> $DIR/attribute-with-error.rs:12:18
    |
 LL |     let b: i32 = "f'oo";
    |                  ^^^^^^ expected i32, found reference
@@ -17,7 +17,7 @@ LL |     let b: i32 = "f'oo";
               found type `&'static str`
 
 error[E0308]: mismatched types
-  --> $DIR/attribute-with-error.rs:26:22
+  --> $DIR/attribute-with-error.rs:25:22
    |
 LL |         let a: i32 = "foo";
    |                      ^^^^^ expected i32, found reference
@@ -26,7 +26,7 @@ LL |         let a: i32 = "foo";
               found type `&'static str`
 
 error[E0308]: mismatched types
-  --> $DIR/attribute-with-error.rs:36:22
+  --> $DIR/attribute-with-error.rs:35:22
    |
 LL |         let a: i32 = "foo";
    |                      ^^^^^ expected i32, found reference
diff --git a/src/test/ui/proc-macro/auxiliary/attr_proc_macro.rs b/src/test/ui/proc-macro/auxiliary/attr_proc_macro.rs
deleted file mode 100644 (file)
index b1f54be..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_attribute]
-pub fn attr_proc_macro(_: TokenStream, input: TokenStream) -> TokenStream {
-    input
-}
diff --git a/src/test/ui/proc-macro/auxiliary/attribute-with-error.rs b/src/test/ui/proc-macro/auxiliary/attribute-with-error.rs
deleted file mode 100644 (file)
index c073be0..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_attribute]
-pub fn foo(_attr: TokenStream, input: TokenStream) -> TokenStream {
-    input.into_iter().collect()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/bang_proc_macro.rs b/src/test/ui/proc-macro/auxiliary/bang_proc_macro.rs
deleted file mode 100644 (file)
index 16f3b76..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro]
-pub fn bang_proc_macro(input: TokenStream) -> TokenStream {
-    input
-}
diff --git a/src/test/ui/proc-macro/auxiliary/derive-a-b.rs b/src/test/ui/proc-macro/auxiliary/derive-a-b.rs
deleted file mode 100644 (file)
index 64d4e0f..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::TokenStream;
-
-#[proc_macro_derive(A)]
-pub fn derive_a(_: TokenStream) -> TokenStream {
-    "".parse().unwrap()
-}
-
-#[proc_macro_derive(B)]
-pub fn derive_b(_: TokenStream) -> TokenStream {
-    "".parse().unwrap()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/derive-a.rs b/src/test/ui/proc-macro/auxiliary/derive-a.rs
deleted file mode 100644 (file)
index c9d94ab..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_derive(A)]
-pub fn derive_a(input: TokenStream) -> TokenStream {
-    "".parse().unwrap()
-}
index 9912a89dafb3f0e799725e740baf8b623cb1ab5d..ab532da2992247ca5e6a7fb8fe45d79897bedd74 100644 (file)
@@ -1,2 +1,2 @@
 #[macro_export]
-macro_rules! my_attr { () => () }
+macro_rules! empty_helper { () => () }
diff --git a/src/test/ui/proc-macro/auxiliary/derive-helper-shadowed.rs b/src/test/ui/proc-macro/auxiliary/derive-helper-shadowed.rs
deleted file mode 100644 (file)
index 5b5243d..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::*;
-
-#[proc_macro_derive(MyTrait, attributes(my_attr))]
-pub fn foo(_: TokenStream) -> TokenStream {
-    TokenStream::new()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/derive-helper-shadowing.rs b/src/test/ui/proc-macro/auxiliary/derive-helper-shadowing.rs
deleted file mode 100644 (file)
index 6e0bdcb..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::*;
-
-#[proc_macro_attribute]
-pub fn my_attr(_: TokenStream, input: TokenStream) -> TokenStream {
-    input
-}
-
-#[proc_macro_derive(MyTrait, attributes(my_attr))]
-pub fn derive(input: TokenStream) -> TokenStream {
-    TokenStream::new()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/derive-panic.rs b/src/test/ui/proc-macro/auxiliary/derive-panic.rs
deleted file mode 100644 (file)
index e2afa7a..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_derive(A)]
-pub fn derive_a(_input: TokenStream) -> TokenStream {
-    panic!("nope!");
-}
index 8f15a2b975bf342567e64c121c7cdd3cfac4b0f3..d5d393b5a6457df34cddb74fd0ad058a1694affa 100644 (file)
@@ -3,14 +3,14 @@
 #[macro_export]
 macro_rules! external {
     () => {
-        dollar_crate::m! {
+        print_bang! {
             struct M($crate::S);
         }
 
-        #[dollar_crate::a]
+        #[print_attr]
         struct A($crate::S);
 
-        #[derive(dollar_crate::d)]
+        #[derive(Print)]
         struct D($crate::S);
     };
 }
diff --git a/src/test/ui/proc-macro/auxiliary/dollar-crate.rs b/src/test/ui/proc-macro/auxiliary/dollar-crate.rs
deleted file mode 100644 (file)
index c5347d2..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::TokenStream;
-
-#[proc_macro]
-pub fn m_empty(input: TokenStream) -> TokenStream {
-    println!("PROC MACRO INPUT (PRETTY-PRINTED): {}", input);
-    println!("PROC MACRO INPUT: {:#?}", input);
-    TokenStream::new()
-}
-
-#[proc_macro]
-pub fn m(input: TokenStream) -> TokenStream {
-    println!("PROC MACRO INPUT (PRETTY-PRINTED): {}", input);
-    println!("PROC MACRO INPUT: {:#?}", input);
-    input.into_iter().collect()
-}
-
-#[proc_macro_attribute]
-pub fn a(_args: TokenStream, input: TokenStream) -> TokenStream {
-    println!("ATTRIBUTE INPUT (PRETTY-PRINTED): {}", input);
-    println!("ATTRIBUTE INPUT: {:#?}", input);
-    input.into_iter().collect()
-}
-
-#[proc_macro_derive(d)]
-pub fn d(input: TokenStream) -> TokenStream {
-    println!("DERIVE INPUT (PRETTY-PRINTED): {}", input);
-    println!("DERIVE INPUT: {:#?}", input);
-    input.into_iter().collect()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/issue-41211.rs b/src/test/ui/proc-macro/auxiliary/issue-41211.rs
deleted file mode 100644 (file)
index db946e7..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::TokenStream;
-
-#[proc_macro_attribute]
-pub fn emit_unchanged(_args: TokenStream, input: TokenStream) -> TokenStream {
-    input
-}
diff --git a/src/test/ui/proc-macro/auxiliary/issue-53481.rs b/src/test/ui/proc-macro/auxiliary/issue-53481.rs
deleted file mode 100644 (file)
index d9f290d..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::*;
-
-#[proc_macro_derive(MyTrait, attributes(my_attr))]
-pub fn foo(_: TokenStream) -> TokenStream {
-    TokenStream::new()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/macro-brackets.rs b/src/test/ui/proc-macro/auxiliary/macro-brackets.rs
deleted file mode 100644 (file)
index f2c62ab..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-use proc_macro::*;
-
-#[proc_macro_attribute]
-pub fn doit(_: TokenStream, input: TokenStream) -> TokenStream {
-    input.into_iter().collect()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/nested-item-spans.rs b/src/test/ui/proc-macro/auxiliary/nested-item-spans.rs
deleted file mode 100644 (file)
index 8f720b4..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::*;
-
-#[proc_macro_attribute]
-pub fn foo(_: TokenStream, item: TokenStream) -> TokenStream {
-    item.into_iter().collect()
-}
diff --git a/src/test/ui/proc-macro/auxiliary/proc-macro-gates.rs b/src/test/ui/proc-macro/auxiliary/proc-macro-gates.rs
deleted file mode 100644 (file)
index c7c7167..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::*;
-
-#[proc_macro]
-pub fn m(a: TokenStream) -> TokenStream {
-    a
-}
-
-#[proc_macro_attribute]
-pub fn a(_a: TokenStream, b: TokenStream) -> TokenStream {
-    b
-}
diff --git a/src/test/ui/proc-macro/auxiliary/span-preservation.rs b/src/test/ui/proc-macro/auxiliary/span-preservation.rs
deleted file mode 100644 (file)
index 33c7968..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-// force-host
-// no-prefer-dynamic
-
-#![crate_type = "proc-macro"]
-
-extern crate proc_macro;
-
-use proc_macro::TokenStream;
-
-#[proc_macro_attribute]
-pub fn foo(_: TokenStream, input: TokenStream) -> TokenStream {
-    input.into_iter().collect()
-}
index 15fe3804f9b4ff73c46a2784207715e90a471026..27efa44f980323a5948d336d6e88a788d3bf7959 100644 (file)
 // force-host
 // no-prefer-dynamic
 
+// Proc macros commonly used by tests.
+// `panic`/`print` -> `panic_bang`/`print_bang` to avoid conflicts with standard macros.
+
 #![crate_type = "proc-macro"]
 
 extern crate proc_macro;
-
 use proc_macro::TokenStream;
 
+// Macro that return empty token stream.
+
+#[proc_macro]
+pub fn empty(_: TokenStream) -> TokenStream {
+    TokenStream::new()
+}
+
 #[proc_macro_attribute]
-pub fn nop_attr(_attr: TokenStream, input: TokenStream) -> TokenStream {
-    assert!(_attr.to_string().is_empty());
-    input
+pub fn empty_attr(_: TokenStream, _: TokenStream) -> TokenStream {
+    TokenStream::new()
+}
+
+#[proc_macro_derive(Empty, attributes(empty_helper))]
+pub fn empty_derive(_: TokenStream) -> TokenStream {
+    TokenStream::new()
+}
+
+// Macro that panics.
+
+#[proc_macro]
+pub fn panic_bang(_: TokenStream) -> TokenStream {
+    panic!("panic-bang");
 }
 
 #[proc_macro_attribute]
-pub fn no_output(_attr: TokenStream, _input: TokenStream) -> TokenStream {
-    assert!(_attr.to_string().is_empty());
-    assert!(!_input.to_string().is_empty());
-    "".parse().unwrap()
+pub fn panic_attr(_: TokenStream, _: TokenStream) -> TokenStream {
+    panic!("panic-attr");
+}
+
+#[proc_macro_derive(Panic, attributes(panic_helper))]
+pub fn panic_derive(_: TokenStream) -> TokenStream {
+    panic!("panic-derive");
 }
 
+// Macros that return the input stream.
+
 #[proc_macro]
-pub fn emit_input(input: TokenStream) -> TokenStream {
+pub fn identity(input: TokenStream) -> TokenStream {
     input
 }
+
+#[proc_macro_attribute]
+pub fn identity_attr(_: TokenStream, input: TokenStream) -> TokenStream {
+    input
+}
+
+#[proc_macro_derive(Identity, attributes(identity_helper))]
+pub fn identity_derive(input: TokenStream) -> TokenStream {
+    input
+}
+
+// Macros that iterate and re-collect the input stream.
+
+#[proc_macro]
+pub fn recollect(input: TokenStream) -> TokenStream {
+    input.into_iter().collect()
+}
+
+#[proc_macro_attribute]
+pub fn recollect_attr(_: TokenStream, input: TokenStream) -> TokenStream {
+    input.into_iter().collect()
+}
+
+#[proc_macro_derive(Recollect, attributes(recollect_helper))]
+pub fn recollect_derive(input: TokenStream) -> TokenStream {
+    input.into_iter().collect()
+}
+
+// Macros that print their input in the original and re-collected forms (if they differ).
+
+fn print_helper(input: TokenStream, kind: &str) -> TokenStream {
+    let input_display = format!("{}", input);
+    let input_debug = format!("{:#?}", input);
+    let recollected = input.into_iter().collect();
+    let recollected_display = format!("{}", recollected);
+    let recollected_debug = format!("{:#?}", recollected);
+    println!("PRINT-{} INPUT (DISPLAY): {}", kind, input_display);
+    if recollected_display != input_display {
+        println!("PRINT-{} RE-COLLECTED (DISPLAY): {}", kind, recollected_display);
+    }
+    println!("PRINT-{} INPUT (DEBUG): {}", kind, input_debug);
+    if recollected_debug != input_debug {
+        println!("PRINT-{} RE-COLLECTED (DEBUG): {}", kind, recollected_debug);
+    }
+    recollected
+}
+
+#[proc_macro]
+pub fn print_bang(input: TokenStream) -> TokenStream {
+    print_helper(input, "BANG")
+}
+
+#[proc_macro_attribute]
+pub fn print_attr(_: TokenStream, input: TokenStream) -> TokenStream {
+    print_helper(input, "ATTR")
+}
+
+#[proc_macro_derive(Print, attributes(print_helper))]
+pub fn print_derive(input: TokenStream) -> TokenStream {
+    print_helper(input, "DERIVE")
+}
index 792b54b3b945ae4a5f8e043934334b055896f912..0388e647b58aad7691f334de67c39ab8202380f8 100644 (file)
@@ -1,16 +1,16 @@
 // compile-pass
-// aux-build:derive-helper-shadowed.rs
+// aux-build:test-macros.rs
 // aux-build:derive-helper-shadowed-2.rs
 
 #[macro_use]
-extern crate derive_helper_shadowed;
-#[macro_use(my_attr)]
+extern crate test_macros;
+#[macro_use(empty_helper)]
 extern crate derive_helper_shadowed_2;
 
-macro_rules! my_attr { () => () }
+macro_rules! empty_helper { () => () }
 
-#[derive(MyTrait)]
-#[my_attr] // OK
+#[derive(Empty)]
+#[empty_helper] // OK
 struct S;
 
 fn main() {}
index f6fe9f9fd8b304d48d4b081e1070c29c11210b9d..cdc0d6da94695c018f3752c1248b911d699606ac 100644 (file)
@@ -1,23 +1,25 @@
-// aux-build:derive-helper-shadowing.rs
+// aux-build:test-macros.rs
 
-extern crate derive_helper_shadowing;
-use derive_helper_shadowing::*;
+#[macro_use]
+extern crate test_macros;
 
-#[my_attr] //~ ERROR `my_attr` is ambiguous
-#[derive(MyTrait)]
+use test_macros::empty_attr as empty_helper;
+
+#[empty_helper] //~ ERROR `empty_helper` is ambiguous
+#[derive(Empty)]
 struct S {
     // FIXME No ambiguity, attributes in non-macro positions are not resolved properly
-    #[my_attr]
+    #[empty_helper]
     field: [u8; {
         // FIXME No ambiguity, derive helpers are not put into scope for non-attributes
-        use my_attr;
+        use empty_helper;
 
         // FIXME No ambiguity, derive helpers are not put into scope for inner items
-        #[my_attr]
+        #[empty_helper]
         struct U;
 
         mod inner {
-            #[my_attr] //~ ERROR attribute `my_attr` is currently unknown
+            #[empty_helper] //~ ERROR attribute `empty_helper` is currently unknown
             struct V;
         }
 
index fb86cabf939c47a84ccef28c1784cb06223c5543..ed6d30516562d5e50f17a425b385fed724776ad6 100644 (file)
@@ -1,29 +1,29 @@
-error[E0658]: The attribute `my_attr` is currently unknown to the compiler and may have meaning added to it in the future
-  --> $DIR/derive-helper-shadowing.rs:20:15
+error[E0658]: The attribute `empty_helper` is currently unknown to the compiler and may have meaning added to it in the future
+  --> $DIR/derive-helper-shadowing.rs:22:15
    |
-LL |             #[my_attr]
-   |               ^^^^^^^
+LL |             #[empty_helper]
+   |               ^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29642
    = help: add #![feature(custom_attribute)] to the crate attributes to enable
 
-error[E0659]: `my_attr` is ambiguous (derive helper attribute vs any other name)
-  --> $DIR/derive-helper-shadowing.rs:6:3
+error[E0659]: `empty_helper` is ambiguous (derive helper attribute vs any other name)
+  --> $DIR/derive-helper-shadowing.rs:8:3
    |
-LL | #[my_attr]
-   |   ^^^^^^^ ambiguous name
+LL | #[empty_helper]
+   |   ^^^^^^^^^^^^ ambiguous name
    |
-note: `my_attr` could refer to the derive helper attribute defined here
-  --> $DIR/derive-helper-shadowing.rs:7:10
+note: `empty_helper` could refer to the derive helper attribute defined here
+  --> $DIR/derive-helper-shadowing.rs:9:10
    |
-LL | #[derive(MyTrait)]
-   |          ^^^^^^^
-note: `my_attr` could also refer to the attribute macro imported here
-  --> $DIR/derive-helper-shadowing.rs:4:5
+LL | #[derive(Empty)]
+   |          ^^^^^
+note: `empty_helper` could also refer to the attribute macro imported here
+  --> $DIR/derive-helper-shadowing.rs:6:5
    |
-LL | use derive_helper_shadowing::*;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
-   = help: use `crate::my_attr` to refer to this attribute macro unambiguously
+LL | use test_macros::empty_attr as empty_helper;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = help: use `crate::empty_helper` to refer to this attribute macro unambiguously
 
 error: aborting due to 2 previous errors
 
diff --git a/src/test/ui/proc-macro/derive-in-mod.rs b/src/test/ui/proc-macro/derive-in-mod.rs
new file mode 100644 (file)
index 0000000..e6b9132
--- /dev/null
@@ -0,0 +1,13 @@
+// compile-pass
+// aux-build:test-macros.rs
+
+extern crate test_macros;
+
+mod inner {
+    use test_macros::Empty;
+
+    #[derive(Empty)]
+    struct S;
+}
+
+fn main() {}
index 526eff39891ae95adc58aca7fa9a18a6142fa768..d895d26f26763385c630034d1fe31ecfba78bdb6 100644 (file)
@@ -1,11 +1,9 @@
-// aux-build:derive-a.rs
-
-#![allow(warnings)]
+// aux-build:test-macros.rs
 
 #[macro_use]
-extern crate derive_a;
+extern crate test_macros;
 
-#[derive_A] //~ ERROR attribute `derive_A` is currently unknown
+#[derive_Empty] //~ ERROR attribute `derive_Empty` is currently unknown
 struct A;
 
 fn main() {}
index d235343ff16188e1c2e7138ece81d56dc5cf96de..f299b5abdbc6be5d14a2e173593d78d4106be627 100644 (file)
@@ -1,8 +1,8 @@
-error[E0658]: The attribute `derive_A` is currently unknown to the compiler and may have meaning added to it in the future
-  --> $DIR/derive-still-gated.rs:8:3
+error[E0658]: The attribute `derive_Empty` is currently unknown to the compiler and may have meaning added to it in the future
+  --> $DIR/derive-still-gated.rs:6:3
    |
-LL | #[derive_A]
-   |   ^^^^^^^^ help: a built-in attribute with a similar name exists: `derive`
+LL | #[derive_Empty]
+   |   ^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29642
    = help: add #![feature(custom_attribute)] to the crate attributes to enable
index 2d54c07ff95309fba007bd0cbbc68c3649befb9f..2615db3e119f1366d9495631ba1a2e55f42c9fb1 100644 (file)
@@ -1,22 +1,23 @@
 // compile-pass
 // edition:2018
-// aux-build:dollar-crate.rs
+// aux-build:test-macros.rs
 
 // Anonymize unstable non-dummy spans while still showing dummy spans `0..0`.
 // normalize-stdout-test "bytes\([^0]\w*\.\.(\w+)\)" -> "bytes(LO..$1)"
 // normalize-stdout-test "bytes\((\w+)\.\.[^0]\w*\)" -> "bytes($1..HI)"
 
-extern crate dollar_crate;
+#[macro_use]
+extern crate test_macros;
 
 type S = u8;
 
 macro_rules! m {
     () => {
-        dollar_crate::m_empty! {
+        print_bang! {
             struct M($crate::S);
         }
 
-        #[dollar_crate::a]
+        #[print_attr]
         struct A($crate::S);
     };
 }
index 618380d7f0bee8aae443bbba997c7972182f238f..0611fcb13f267dc17f471345ce1976df45be51b0 100644 (file)
@@ -1,5 +1,5 @@
-PROC MACRO INPUT (PRETTY-PRINTED): struct M ( $crate :: S ) ;
-PROC MACRO INPUT: TokenStream [
+PRINT-BANG INPUT (DISPLAY): struct M ( $crate :: S ) ;
+PRINT-BANG INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #2 bytes(LO..HI),
@@ -38,8 +38,9 @@ PROC MACRO INPUT: TokenStream [
         span: #2 bytes(LO..HI),
     },
 ]
-ATTRIBUTE INPUT (PRETTY-PRINTED): struct A(crate::S);
-ATTRIBUTE INPUT: TokenStream [
+PRINT-ATTR INPUT (DISPLAY): struct A(crate::S);
+PRINT-ATTR RE-COLLECTED (DISPLAY): struct A ( $crate :: S ) ;
+PRINT-ATTR INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #2 bytes(LO..HI),
index 1460e9a3b2d55ab988a73ee675d9ccd313cd66a9..aadd87ffaf203e86d9af6bc23ebbc1c0058f3822 100644 (file)
@@ -1,29 +1,28 @@
 // edition:2018
-// aux-build:dollar-crate.rs
+// aux-build:test-macros.rs
 // aux-build:dollar-crate-external.rs
 
 // Anonymize unstable non-dummy spans while still showing dummy spans `0..0`.
 // normalize-stdout-test "bytes\([^0]\w*\.\.(\w+)\)" -> "bytes(LO..$1)"
 // normalize-stdout-test "bytes\((\w+)\.\.[^0]\w*\)" -> "bytes($1..HI)"
 
-extern crate dollar_crate;
+#[macro_use]
+extern crate test_macros;
 extern crate dollar_crate_external;
 
 type S = u8;
 
 mod local {
-    use crate::dollar_crate;
-
     macro_rules! local {
         () => {
-            dollar_crate::m! {
+            print_bang! {
                 struct M($crate::S);
             }
 
-            #[dollar_crate::a]
+            #[print_attr]
             struct A($crate::S);
 
-            #[derive(dollar_crate::d)]
+            #[derive(Print)]
             struct D($crate::S); //~ ERROR the name `D` is defined multiple times
         };
     }
index d1b836e7f6f2897f24848bd5bd898e65cc419f7c..5d78a8e1987292fa1cbd1149f10989a29b28e5b9 100644 (file)
@@ -1,5 +1,5 @@
 error[E0428]: the name `D` is defined multiple times
-  --> $DIR/dollar-crate.rs:27:13
+  --> $DIR/dollar-crate.rs:26:13
    |
 LL |             struct D($crate::S);
    |             ^^^^^^^^^^^^^^^^^^^^
@@ -13,7 +13,7 @@ LL |     local!();
    = note: `D` must be defined only once in the type namespace of this module
 
 error[E0428]: the name `D` is defined multiple times
-  --> $DIR/dollar-crate.rs:37:5
+  --> $DIR/dollar-crate.rs:36:5
    |
 LL |     dollar_crate_external::external!();
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
index 454da53943054f8cf380ace5b7a327fb18e14209..3c88ee99842a26e27f2e717fc08ce453e0372c4d 100644 (file)
@@ -1,5 +1,5 @@
-PROC MACRO INPUT (PRETTY-PRINTED): struct M ( $crate :: S ) ;
-PROC MACRO INPUT: TokenStream [
+PRINT-BANG INPUT (DISPLAY): struct M ( $crate :: S ) ;
+PRINT-BANG INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #2 bytes(LO..HI),
@@ -38,8 +38,9 @@ PROC MACRO INPUT: TokenStream [
         span: #2 bytes(LO..HI),
     },
 ]
-ATTRIBUTE INPUT (PRETTY-PRINTED): struct A(crate::S);
-ATTRIBUTE INPUT: TokenStream [
+PRINT-ATTR INPUT (DISPLAY): struct A(crate::S);
+PRINT-ATTR RE-COLLECTED (DISPLAY): struct A ( $crate :: S ) ;
+PRINT-ATTR INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #2 bytes(LO..HI),
@@ -78,8 +79,9 @@ ATTRIBUTE INPUT: TokenStream [
         span: #2 bytes(LO..HI),
     },
 ]
-DERIVE INPUT (PRETTY-PRINTED): struct D(crate::S);
-DERIVE INPUT: TokenStream [
+PRINT-DERIVE INPUT (DISPLAY): struct D(crate::S);
+PRINT-DERIVE RE-COLLECTED (DISPLAY): struct D ( $crate :: S ) ;
+PRINT-DERIVE INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #2 bytes(LO..HI),
@@ -118,8 +120,8 @@ DERIVE INPUT: TokenStream [
         span: #2 bytes(LO..HI),
     },
 ]
-PROC MACRO INPUT (PRETTY-PRINTED): struct M ( $crate :: S ) ;
-PROC MACRO INPUT: TokenStream [
+PRINT-BANG INPUT (DISPLAY): struct M ( $crate :: S ) ;
+PRINT-BANG INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #10 bytes(LO..HI),
@@ -158,8 +160,9 @@ PROC MACRO INPUT: TokenStream [
         span: #10 bytes(LO..HI),
     },
 ]
-ATTRIBUTE INPUT (PRETTY-PRINTED): struct A(::dollar_crate_external::S);
-ATTRIBUTE INPUT: TokenStream [
+PRINT-ATTR INPUT (DISPLAY): struct A(::dollar_crate_external::S);
+PRINT-ATTR RE-COLLECTED (DISPLAY): struct A ( $crate :: S ) ;
+PRINT-ATTR INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #10 bytes(LO..HI),
@@ -198,8 +201,9 @@ ATTRIBUTE INPUT: TokenStream [
         span: #10 bytes(LO..HI),
     },
 ]
-DERIVE INPUT (PRETTY-PRINTED): struct D(::dollar_crate_external::S);
-DERIVE INPUT: TokenStream [
+PRINT-DERIVE INPUT (DISPLAY): struct D(::dollar_crate_external::S);
+PRINT-DERIVE RE-COLLECTED (DISPLAY): struct D ( $crate :: S ) ;
+PRINT-DERIVE INPUT (DEBUG): TokenStream [
     Ident {
         ident: "struct",
         span: #10 bytes(LO..HI),
diff --git a/src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.rs b/src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.rs
new file mode 100644 (file)
index 0000000..3a1c56e
--- /dev/null
@@ -0,0 +1,11 @@
+// aux-build:test-macros.rs
+
+#[macro_use(Empty)]
+extern crate test_macros;
+use test_macros::empty_attr as empty_helper;
+
+#[derive(Empty)]
+#[empty_helper] //~ ERROR `empty_helper` is ambiguous
+struct S;
+
+fn main() {}
diff --git a/src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.stderr b/src/test/ui/proc-macro/helper-attr-blocked-by-import-ambig.stderr
new file mode 100644 (file)
index 0000000..012fb10
--- /dev/null
@@ -0,0 +1,21 @@
+error[E0659]: `empty_helper` is ambiguous (derive helper attribute vs any other name)
+  --> $DIR/helper-attr-blocked-by-import-ambig.rs:8:3
+   |
+LL | #[empty_helper]
+   |   ^^^^^^^^^^^^ ambiguous name
+   |
+note: `empty_helper` could refer to the derive helper attribute defined here
+  --> $DIR/helper-attr-blocked-by-import-ambig.rs:7:10
+   |
+LL | #[derive(Empty)]
+   |          ^^^^^
+note: `empty_helper` could also refer to the attribute macro imported here
+  --> $DIR/helper-attr-blocked-by-import-ambig.rs:5:5
+   |
+LL | use test_macros::empty_attr as empty_helper;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = help: use `crate::empty_helper` to refer to this attribute macro unambiguously
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0659`.
diff --git a/src/test/ui/proc-macro/helper-attr-blocked-by-import.rs b/src/test/ui/proc-macro/helper-attr-blocked-by-import.rs
new file mode 100644 (file)
index 0000000..6d3e5ec
--- /dev/null
@@ -0,0 +1,28 @@
+// compile-pass
+// aux-build:test-macros.rs
+
+#[macro_use(Empty)]
+extern crate test_macros;
+
+use self::one::*;
+use self::two::*;
+
+mod empty_helper {}
+
+mod one {
+    use empty_helper;
+
+    #[derive(Empty)]
+    #[empty_helper]
+    struct One;
+}
+
+mod two {
+    use empty_helper;
+
+    #[derive(Empty)]
+    #[empty_helper]
+    struct Two;
+}
+
+fn main() {}
index 8fbccdf1aed14cc51325b79f95cd79f953cce8b2..d1b1ff350695f10f2ca5aa63f316e910d549baa6 100644 (file)
@@ -1,11 +1,8 @@
-// aux-build:derive-a.rs
+// aux-build:test-macros.rs
 
-#![allow(warnings)]
+extern crate test_macros;
 
-#[macro_use]
-extern crate derive_a;
-
-use derive_a::derive_a;
-//~^ ERROR: unresolved import `derive_a::derive_a`
+use test_macros::empty_derive;
+//~^ ERROR: unresolved import `test_macros::empty_derive`
 
 fn main() {}
index 813a8ac2604605ce6c5ddbf813d2739d12d07ae3..aae621193ab9f3ea329765a7d36729560e88459e 100644 (file)
@@ -1,8 +1,8 @@
-error[E0432]: unresolved import `derive_a::derive_a`
-  --> $DIR/import.rs:8:5
+error[E0432]: unresolved import `test_macros::empty_derive`
+  --> $DIR/import.rs:5:5
    |
-LL | use derive_a::derive_a;
-   |     ^^^^^^^^^^^^^^^^^^ no `derive_a` in the root
+LL | use test_macros::empty_derive;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ no `empty_derive` in the root
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/proc-macro/issue-36935.rs b/src/test/ui/proc-macro/issue-36935.rs
new file mode 100644 (file)
index 0000000..f809592
--- /dev/null
@@ -0,0 +1,12 @@
+// aux-build:test-macros.rs
+
+#[macro_use]
+extern crate test_macros;
+
+#[derive(Identity, Panic)] //~ ERROR proc-macro derive panicked
+struct Baz {
+    a: i32,
+    b: i32,
+}
+
+fn main() {}
diff --git a/src/test/ui/proc-macro/issue-36935.stderr b/src/test/ui/proc-macro/issue-36935.stderr
new file mode 100644 (file)
index 0000000..da4366e
--- /dev/null
@@ -0,0 +1,10 @@
+error: proc-macro derive panicked
+  --> $DIR/issue-36935.rs:6:20
+   |
+LL | #[derive(Identity, Panic)]
+   |                    ^^^^^
+   |
+   = help: message: panic-derive
+
+error: aborting due to previous error
+
index 75fcd24d85f6f80ec6cb198f98ce6bef8fa7786f..73b1f0d58c8371a5f6599204af953e51d0953117 100644 (file)
@@ -1,7 +1,7 @@
-// aux-build:derive-a-b.rs
+// aux-build:test-macros.rs
 
 #[macro_use]
-extern crate derive_a_b;
+extern crate test_macros;
 
 fn main() {
     // Test that constructing the `visible_parent_map` (in `cstore_impl.rs`) does not ICE.
index 0b082f4818f1b53fa32f72cc1e13df96ec721cd3..ee9246e1c9b5cf25b24b106b46696e4dd4164022 100644 (file)
@@ -1,14 +1,14 @@
-// aux-build:issue-41211.rs
+// aux-build:test-macros.rs
 
 // FIXME: https://github.com/rust-lang/rust/issues/41430
 // This is a temporary regression test for the ICE reported in #41211
 
 #![feature(custom_inner_attributes)]
 
-#![emit_unchanged]
-//~^ ERROR attribute `emit_unchanged` is currently unknown to the compiler
+#![identity_attr]
+//~^ ERROR attribute `identity_attr` is currently unknown to the compiler
 //~| ERROR inconsistent resolution for a macro: first custom attribute, then attribute macro
-extern crate issue_41211;
-use issue_41211::emit_unchanged;
+extern crate test_macros;
+use test_macros::identity_attr;
 
 fn main() {}
index dfb2f6f63d84706d56c6d65ac3c066b1847ee3e6..1de6b293ecfb8601633338a52fcd2f2538355a45 100644 (file)
@@ -1,8 +1,8 @@
-error[E0658]: The attribute `emit_unchanged` is currently unknown to the compiler and may have meaning added to it in the future
+error[E0658]: The attribute `identity_attr` is currently unknown to the compiler and may have meaning added to it in the future
   --> $DIR/issue-41211.rs:8:4
    |
-LL | #![emit_unchanged]
-   |    ^^^^^^^^^^^^^^
+LL | #![identity_attr]
+   |    ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29642
    = help: add #![feature(custom_attribute)] to the crate attributes to enable
@@ -10,8 +10,8 @@ LL | #![emit_unchanged]
 error: inconsistent resolution for a macro: first custom attribute, then attribute macro
   --> $DIR/issue-41211.rs:8:4
    |
-LL | #![emit_unchanged]
-   |    ^^^^^^^^^^^^^^
+LL | #![identity_attr]
+   |    ^^^^^^^^^^^^^
 
 error: aborting due to 2 previous errors
 
index 479fd1db630a392b2350f637279650e954e43573..2fbde5fedb95b7527c9157f61a62fdeb6935b524 100644 (file)
@@ -1,21 +1,21 @@
 // compile-pass
-// aux-build:issue-53481.rs
+// aux-build:test-macros.rs
 
 #[macro_use]
-extern crate issue_53481;
+extern crate test_macros;
 
 mod m1 {
-    use m2::MyTrait;
+    use m2::Empty;
 
-    #[derive(MyTrait)]
+    #[derive(Empty)]
     struct A {}
 }
 
 mod m2 {
-    pub type MyTrait = u8;
+    pub type Empty = u8;
 
-    #[derive(MyTrait)]
-    #[my_attr]
+    #[derive(Empty)]
+    #[empty_helper]
     struct B {}
 }
 
index fa279c559fbf1890c70310e67490afe7daa12b57..2e9a311d882bd3019f107d6e11a4a28b1546e0bf 100644 (file)
@@ -1,10 +1,9 @@
-// aux-build:derive-panic.rs
-// compile-flags:--error-format human
+// aux-build:test-macros.rs
 
 #[macro_use]
-extern crate derive_panic;
+extern crate test_macros;
 
-#[derive(A)]
+#[derive(Panic)]
 //~^ ERROR: proc-macro derive panicked
 struct Foo;
 
index b448c804bff598c513a27e5fc96726a1f0aed048..40cc4ee0e3d373246c2f41583dd90472b567e13d 100644 (file)
@@ -1,10 +1,10 @@
 error: proc-macro derive panicked
-  --> $DIR/load-panic.rs:7:10
+  --> $DIR/load-panic.rs:6:10
    |
-LL | #[derive(A)]
-   |          ^
+LL | #[derive(Panic)]
+   |          ^^^^^
    |
-   = help: message: nope!
+   = help: message: panic-derive
 
 error: aborting due to previous error
 
index c46abf03654ced7475e9f9396cbfd95b6b80e84f..aa0046f458229caeb5b6b58a7538a3b364017d8b 100644 (file)
@@ -1,13 +1,13 @@
-// aux-build:macro-brackets.rs
+// aux-build:test-macros.rs
 
-extern crate macro_brackets as bar;
-use bar::doit;
+#[macro_use]
+extern crate test_macros;
 
 macro_rules! id {
     ($($t:tt)*) => ($($t)*)
 }
 
-#[doit]
+#[identity_attr]
 id![static X: u32 = 'a';]; //~ ERROR: mismatched types
 
 
index 13db0725a388b034c9d4794dbdd0d9bde929c85f..d1b1430fb5d034f5effb78dc6a711cfec95c0ddc 100644 (file)
@@ -1,9 +1,10 @@
 // compile-pass
-// aux-build:attr_proc_macro.rs
+// aux-build:test-macros.rs
 
-#[macro_use] extern crate attr_proc_macro;
+#[macro_use]
+extern crate test_macros;
 
-#[attr_proc_macro]
+#[identity_attr]
 struct Foo;
 
 fn main() {
index 4bf3bcd6f3aae5512e7e559c3753e78358741708..d39c42267fb96003d48941acaf05efdffe98c475 100644 (file)
@@ -1,11 +1,11 @@
 // compile-pass
-// aux-build:bang_proc_macro.rs
+// aux-build:test-macros.rs
 
 #![feature(proc_macro_hygiene)]
 
 #[macro_use]
-extern crate bang_proc_macro;
+extern crate test_macros;
 
 fn main() {
-    bang_proc_macro!(println!("Hello, world!"));
+    identity!(println!("Hello, world!"));
 }
index 5c5603b6c06b0491ad23e512bdd378a27a028b65..0477b5c48ecc9600bf5b67493f2736875d76d1cd 100644 (file)
@@ -1,10 +1,9 @@
 // aux-build:test-macros.rs
 // ignore-wasm32
 
+#[macro_use]
 extern crate test_macros;
 
-use test_macros::{nop_attr, no_output, emit_input};
-
 fn main() {
     assert_eq!(unsafe { rust_get_test_int() }, 0isize);
     assert_eq!(unsafe { rust_dbg_extern_identity_u32(0xDEADBEEF) }, 0xDEADBEEF);
@@ -12,14 +11,14 @@ fn main() {
 
 #[link(name = "rust_test_helpers", kind = "static")]
 extern {
-    #[no_output]
+    #[empty_attr]
     //~^ ERROR macro invocations in `extern {}` blocks are experimental
     fn some_definitely_unknown_symbol_which_should_be_removed();
 
-    #[nop_attr]
+    #[identity_attr]
     //~^ ERROR macro invocations in `extern {}` blocks are experimental
     fn rust_get_test_int() -> isize;
 
-    emit_input!(fn rust_dbg_extern_identity_u32(arg: u32) -> u32;);
+    identity!(fn rust_dbg_extern_identity_u32(arg: u32) -> u32;);
     //~^ ERROR macro invocations in `extern {}` blocks are experimental
 }
index 61571650f2f048733207c45929510d0a8d73a5c8..592c91553aa8cf6972a4100408365699bf9c0e8a 100644 (file)
@@ -1,26 +1,26 @@
 error[E0658]: macro invocations in `extern {}` blocks are experimental
-  --> $DIR/macros-in-extern.rs:15:5
+  --> $DIR/macros-in-extern.rs:14:5
    |
-LL |     #[no_output]
-   |     ^^^^^^^^^^^^
+LL |     #[empty_attr]
+   |     ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/49476
    = help: add #![feature(macros_in_extern)] to the crate attributes to enable
 
 error[E0658]: macro invocations in `extern {}` blocks are experimental
-  --> $DIR/macros-in-extern.rs:19:5
+  --> $DIR/macros-in-extern.rs:18:5
    |
-LL |     #[nop_attr]
-   |     ^^^^^^^^^^^
+LL |     #[identity_attr]
+   |     ^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/49476
    = help: add #![feature(macros_in_extern)] to the crate attributes to enable
 
 error[E0658]: macro invocations in `extern {}` blocks are experimental
-  --> $DIR/macros-in-extern.rs:23:5
+  --> $DIR/macros-in-extern.rs:22:5
    |
-LL |     emit_input!(fn rust_dbg_extern_identity_u32(arg: u32) -> u32;);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     identity!(fn rust_dbg_extern_identity_u32(arg: u32) -> u32;);
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/49476
    = help: add #![feature(macros_in_extern)] to the crate attributes to enable
index e365b74b3be8ff0dd826aa403388bba60eac2f43..63da170d0bbb263c130eccc5502cc5373e80886e 100644 (file)
@@ -1,10 +1,9 @@
-// aux-build:nested-item-spans.rs
+// aux-build:test-macros.rs
 
-extern crate nested_item_spans;
+#[macro_use]
+extern crate test_macros;
 
-use nested_item_spans::foo;
-
-#[foo]
+#[recollect_attr]
 fn another() {
     fn bar() {
         let x: u32 = "x"; //~ ERROR: mismatched types
@@ -14,7 +13,7 @@ fn bar() {
 }
 
 fn main() {
-    #[foo]
+    #[recollect_attr]
     fn bar() {
         let x: u32 = "x"; //~ ERROR: mismatched types
     }
index 011a91d446295855ab6998e47eea83c6ee7124c8..bef80311f38e5fa5f85c44b619d758ce975fba0f 100644 (file)
@@ -1,5 +1,5 @@
 error[E0308]: mismatched types
-  --> $DIR/nested-item-spans.rs:10:22
+  --> $DIR/nested-item-spans.rs:9:22
    |
 LL |         let x: u32 = "x";
    |                      ^^^ expected u32, found reference
@@ -8,7 +8,7 @@ LL |         let x: u32 = "x";
               found type `&'static str`
 
 error[E0308]: mismatched types
-  --> $DIR/nested-item-spans.rs:19:22
+  --> $DIR/nested-item-spans.rs:18:22
    |
 LL |         let x: u32 = "x";
    |                      ^^^ expected u32, found reference
index 62a501ded1006a2eaec491850e589233cad0539a..15ab431fe754af5576fbaf600ba08e8635b649f0 100644 (file)
@@ -1,9 +1,9 @@
-// aux-build:derive-a.rs
+// aux-build:test-macros.rs
 
 #![feature(rustc_attrs)]
 #![warn(unused_extern_crates)]
 
-extern crate derive_a;
+extern crate test_macros;
 //~^ WARN unused extern crate
 
 #[rustc_error]
index 4b2fce7f6e4caa1e6f65fc7e3998b61b311cfa3c..87487bcc7d6627526ecf15dcf57366d613c5a4ed 100644 (file)
@@ -1,8 +1,8 @@
 warning: unused extern crate
   --> $DIR/no-macro-use-attr.rs:6:1
    |
-LL | extern crate derive_a;
-   | ^^^^^^^^^^^^^^^^^^^^^^ help: remove it
+LL | extern crate test_macros;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^ help: remove it
    |
 note: lint level defined here
   --> $DIR/no-macro-use-attr.rs:4:9
index af6bfa08aaa942816d021297a60dc1ae334c9ebe..678dc83b753b5f7b5143b846833c62c37698b4d9 100644 (file)
@@ -1,61 +1,62 @@
-// aux-build:proc-macro-gates.rs
+// aux-build:test-macros.rs
 // gate-test-proc_macro_hygiene
 
 #![feature(stmt_expr_attributes)]
 
-extern crate proc_macro_gates as foo;
-
-use foo::*;
+#[macro_use]
+extern crate test_macros;
 
 fn _test_inner() {
-    #![a] //~ ERROR: non-builtin inner attributes are unstable
+    #![empty_attr] //~ ERROR: non-builtin inner attributes are unstable
 }
 
-#[a] //~ ERROR: custom attributes cannot be applied to modules
+#[empty_attr] //~ ERROR: custom attributes cannot be applied to modules
 mod _test2 {}
 
 mod _test2_inner {
-    #![a] //~ ERROR: custom attributes cannot be applied to modules
+    #![empty_attr] //~ ERROR: custom attributes cannot be applied to modules
           //~| ERROR: non-builtin inner attributes are unstable
 }
 
-#[a = "y"] //~ ERROR: must only be followed by a delimiter token
+#[empty_attr = "y"] //~ ERROR: must only be followed by a delimiter token
 fn _test3() {}
 
 fn attrs() {
     // Statement, item
-    #[a] // OK
+    #[empty_attr] // OK
     struct S;
 
     // Statement, macro
-    #[a] //~ ERROR: custom attributes cannot be applied to statements
+    #[empty_attr] //~ ERROR: custom attributes cannot be applied to statements
     println!();
 
     // Statement, semi
-    #[a] //~ ERROR: custom attributes cannot be applied to statements
+    #[empty_attr] //~ ERROR: custom attributes cannot be applied to statements
     S;
 
     // Statement, local
-    #[a] //~ ERROR: custom attributes cannot be applied to statements
+    #[empty_attr] //~ ERROR: custom attributes cannot be applied to statements
     let _x = 2;
 
     // Expr
-    let _x = #[a] 2; //~ ERROR: custom attributes cannot be applied to expressions
+    let _x = #[identity_attr] 2; //~ ERROR: custom attributes cannot be applied to expressions
 
     // Opt expr
-    let _x = [#[a] 2]; //~ ERROR: custom attributes cannot be applied to expressions
+    let _x = [#[identity_attr] 2]; //~ ERROR: custom attributes cannot be applied to expressions
 
     // Expr macro
-    let _x = #[a] println!(); //~ ERROR: custom attributes cannot be applied to expressions
+    let _x = #[identity_attr] println!();
+    //~^ ERROR: custom attributes cannot be applied to expressions
 }
 
 fn main() {
-    let _x: m!(u32) = 3; //~ ERROR: procedural macros cannot be expanded to types
-    if let m!(Some(_x)) = Some(3) {} //~ ERROR: procedural macros cannot be expanded to patterns
+    let _x: identity!(u32) = 3; //~ ERROR: procedural macros cannot be expanded to types
+    if let identity!(Some(_x)) = Some(3) {}
+    //~^ ERROR: procedural macros cannot be expanded to patterns
 
-    m!(struct S;); //~ ERROR: procedural macros cannot be expanded to statements
-    m!(let _x = 3;); //~ ERROR: procedural macros cannot be expanded to statements
+    empty!(struct S;); //~ ERROR: procedural macros cannot be expanded to statements
+    empty!(let _x = 3;); //~ ERROR: procedural macros cannot be expanded to statements
 
-    let _x = m!(3); //~ ERROR: procedural macros cannot be expanded to expressions
-    let _x = [m!(3)]; //~ ERROR: procedural macros cannot be expanded to expressions
+    let _x = identity!(3); //~ ERROR: procedural macros cannot be expanded to expressions
+    let _x = [empty!(3)]; //~ ERROR: procedural macros cannot be expanded to expressions
 }
index 1bb864b52ea7d32a67f380e2d24471f59d24bdd5..f53ad222a036811c09746a32255496ccb8d98dfa 100644 (file)
@@ -1,95 +1,95 @@
 error[E0658]: non-builtin inner attributes are unstable
-  --> $DIR/proc-macro-gates.rs:11:5
+  --> $DIR/proc-macro-gates.rs:10:5
    |
-LL |     #![a]
-   |     ^^^^^
+LL |     #![empty_attr]
+   |     ^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54726
    = help: add #![feature(custom_inner_attributes)] to the crate attributes to enable
 
 error[E0658]: non-builtin inner attributes are unstable
-  --> $DIR/proc-macro-gates.rs:18:5
+  --> $DIR/proc-macro-gates.rs:17:5
    |
-LL |     #![a]
-   |     ^^^^^
+LL |     #![empty_attr]
+   |     ^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54726
    = help: add #![feature(custom_inner_attributes)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to modules
-  --> $DIR/proc-macro-gates.rs:14:1
+  --> $DIR/proc-macro-gates.rs:13:1
    |
-LL | #[a]
-   | ^^^^
+LL | #[empty_attr]
+   | ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to modules
-  --> $DIR/proc-macro-gates.rs:18:5
+  --> $DIR/proc-macro-gates.rs:17:5
    |
-LL |     #![a]
-   |     ^^^^^
+LL |     #![empty_attr]
+   |     ^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error: custom attribute invocations must be of the form #[foo] or #[foo(..)], the macro name must only be followed by a delimiter token
-  --> $DIR/proc-macro-gates.rs:22:1
+  --> $DIR/proc-macro-gates.rs:21:1
    |
-LL | #[a = "y"]
-   | ^^^^^^^^^^
+LL | #[empty_attr = "y"]
+   | ^^^^^^^^^^^^^^^^^^^
 
 error[E0658]: custom attributes cannot be applied to statements
-  --> $DIR/proc-macro-gates.rs:31:5
+  --> $DIR/proc-macro-gates.rs:30:5
    |
-LL |     #[a]
-   |     ^^^^
+LL |     #[empty_attr]
+   |     ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to statements
-  --> $DIR/proc-macro-gates.rs:35:5
+  --> $DIR/proc-macro-gates.rs:34:5
    |
-LL |     #[a]
-   |     ^^^^
+LL |     #[empty_attr]
+   |     ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to statements
-  --> $DIR/proc-macro-gates.rs:39:5
+  --> $DIR/proc-macro-gates.rs:38:5
    |
-LL |     #[a]
-   |     ^^^^
+LL |     #[empty_attr]
+   |     ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to expressions
-  --> $DIR/proc-macro-gates.rs:43:14
+  --> $DIR/proc-macro-gates.rs:42:14
    |
-LL |     let _x = #[a] 2;
-   |              ^^^^
+LL |     let _x = #[identity_attr] 2;
+   |              ^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to expressions
-  --> $DIR/proc-macro-gates.rs:46:15
+  --> $DIR/proc-macro-gates.rs:45:15
    |
-LL |     let _x = [#[a] 2];
-   |               ^^^^
+LL |     let _x = [#[identity_attr] 2];
+   |               ^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: custom attributes cannot be applied to expressions
-  --> $DIR/proc-macro-gates.rs:49:14
+  --> $DIR/proc-macro-gates.rs:48:14
    |
-LL |     let _x = #[a] println!();
-   |              ^^^^
+LL |     let _x = #[identity_attr] println!();
+   |              ^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
@@ -97,8 +97,8 @@ LL |     let _x = #[a] println!();
 error[E0658]: procedural macros cannot be expanded to types
   --> $DIR/proc-macro-gates.rs:53:13
    |
-LL |     let _x: m!(u32) = 3;
-   |             ^^^^^^^
+LL |     let _x: identity!(u32) = 3;
+   |             ^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
@@ -106,44 +106,44 @@ LL |     let _x: m!(u32) = 3;
 error[E0658]: procedural macros cannot be expanded to patterns
   --> $DIR/proc-macro-gates.rs:54:12
    |
-LL |     if let m!(Some(_x)) = Some(3) {}
-   |            ^^^^^^^^^^^^
+LL |     if let identity!(Some(_x)) = Some(3) {}
+   |            ^^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: procedural macros cannot be expanded to statements
-  --> $DIR/proc-macro-gates.rs:56:5
+  --> $DIR/proc-macro-gates.rs:57:5
    |
-LL |     m!(struct S;);
-   |     ^^^^^^^^^^^^^^
+LL |     empty!(struct S;);
+   |     ^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: procedural macros cannot be expanded to statements
-  --> $DIR/proc-macro-gates.rs:57:5
+  --> $DIR/proc-macro-gates.rs:58:5
    |
-LL |     m!(let _x = 3;);
-   |     ^^^^^^^^^^^^^^^^
+LL |     empty!(let _x = 3;);
+   |     ^^^^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: procedural macros cannot be expanded to expressions
-  --> $DIR/proc-macro-gates.rs:59:14
+  --> $DIR/proc-macro-gates.rs:60:14
    |
-LL |     let _x = m!(3);
-   |              ^^^^^
+LL |     let _x = identity!(3);
+   |              ^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
 
 error[E0658]: procedural macros cannot be expanded to expressions
-  --> $DIR/proc-macro-gates.rs:60:15
+  --> $DIR/proc-macro-gates.rs:61:15
    |
-LL |     let _x = [m!(3)];
-   |               ^^^^^
+LL |     let _x = [empty!(3)];
+   |               ^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/54727
    = help: add #![feature(proc_macro_hygiene)] to the crate attributes to enable
index 46b543a397cc7ac5fe8904253af7bbbc2e85343f..35d7fc8042a3d838038b13df0ebf02893069e0a1 100644 (file)
@@ -1,21 +1,20 @@
-// aux-build:proc-macro-gates.rs
+// aux-build:test-macros.rs
 
 #![feature(stmt_expr_attributes)]
 
-extern crate proc_macro_gates as foo;
-
-use foo::*;
+#[macro_use]
+extern crate test_macros;
 
 // NB. these errors aren't the best errors right now, but they're definitely
 // intended to be errors. Somehow using a custom attribute in these positions
 // should either require a feature gate or not be allowed on stable.
 
-fn _test6<#[a] T>() {}
+fn _test6<#[empty_attr] T>() {}
 //~^ ERROR: unknown to the compiler
 
 fn _test7() {
     match 1 {
-        #[a] //~ ERROR: unknown to the compiler
+        #[empty_attr] //~ ERROR: unknown to the compiler
         0 => {}
         _ => {}
     }
index 0e8236f460f8ca2b5ae32d9baff86d1af8834857..8eeca99ab39849723675650240eed6a9e946d12b 100644 (file)
@@ -1,17 +1,17 @@
-error[E0658]: The attribute `a` is currently unknown to the compiler and may have meaning added to it in the future
-  --> $DIR/proc-macro-gates2.rs:13:11
+error[E0658]: The attribute `empty_attr` is currently unknown to the compiler and may have meaning added to it in the future
+  --> $DIR/proc-macro-gates2.rs:12:11
    |
-LL | fn _test6<#[a] T>() {}
-   |           ^^^^
+LL | fn _test6<#[empty_attr] T>() {}
+   |           ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29642
    = help: add #![feature(custom_attribute)] to the crate attributes to enable
 
-error[E0658]: The attribute `a` is currently unknown to the compiler and may have meaning added to it in the future
-  --> $DIR/proc-macro-gates2.rs:18:9
+error[E0658]: The attribute `empty_attr` is currently unknown to the compiler and may have meaning added to it in the future
+  --> $DIR/proc-macro-gates2.rs:17:9
    |
-LL |         #[a]
-   |         ^^^^
+LL |         #[empty_attr]
+   |         ^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29642
    = help: add #![feature(custom_attribute)] to the crate attributes to enable
index bb242f302496e4ecfa79b620ece0f5beb745eb77..82607136f0b6f2d87ee4ff3dc3f6d162ab3ceacc 100644 (file)
@@ -1,7 +1,6 @@
 // aux-build:derive-foo.rs
 // aux-build:derive-clona.rs
-// aux-build:attr_proc_macro.rs
-// aux-build:bang_proc_macro.rs
+// aux-build:test-macros.rs
 
 #![feature(custom_attribute)]
 
@@ -9,11 +8,10 @@
 extern crate derive_foo;
 #[macro_use]
 extern crate derive_clona;
-extern crate attr_proc_macro;
-extern crate bang_proc_macro;
+extern crate test_macros;
 
-use attr_proc_macro::attr_proc_macro;
-use bang_proc_macro::bang_proc_macro;
+use test_macros::empty as bang_proc_macro;
+use test_macros::empty_attr as attr_proc_macro;
 
 macro_rules! FooWithLongNam {
     () => {}
index cf7de578c7d42f514f3aa93656a1bb8686543b70..705ef6006a049929573175538a1497428fab5fd4 100644 (file)
@@ -1,47 +1,47 @@
 error: cannot find derive macro `FooWithLongNan` in this scope
-  --> $DIR/resolve-error.rs:26:10
+  --> $DIR/resolve-error.rs:24:10
    |
 LL | #[derive(FooWithLongNan)]
    |          ^^^^^^^^^^^^^^ help: try: `FooWithLongName`
 
 error: cannot find derive macro `Dlone` in this scope
-  --> $DIR/resolve-error.rs:36:10
+  --> $DIR/resolve-error.rs:34:10
    |
 LL | #[derive(Dlone)]
    |          ^^^^^ help: try: `Clone`
 
 error: cannot find derive macro `Dlona` in this scope
-  --> $DIR/resolve-error.rs:40:10
+  --> $DIR/resolve-error.rs:38:10
    |
 LL | #[derive(Dlona)]
    |          ^^^^^ help: try: `Clona`
 
 error: cannot find derive macro `attr_proc_macra` in this scope
-  --> $DIR/resolve-error.rs:44:10
+  --> $DIR/resolve-error.rs:42:10
    |
 LL | #[derive(attr_proc_macra)]
    |          ^^^^^^^^^^^^^^^
 
 error: cannot find macro `FooWithLongNama!` in this scope
-  --> $DIR/resolve-error.rs:49:5
+  --> $DIR/resolve-error.rs:47:5
    |
 LL |     FooWithLongNama!();
    |     ^^^^^^^^^^^^^^^ help: you could try the macro: `FooWithLongNam`
 
 error: cannot find macro `attr_proc_macra!` in this scope
-  --> $DIR/resolve-error.rs:52:5
+  --> $DIR/resolve-error.rs:50:5
    |
 LL |     attr_proc_macra!();
    |     ^^^^^^^^^^^^^^^ help: you could try the macro: `attr_proc_mac`
 
 error: cannot find macro `Dlona!` in this scope
-  --> $DIR/resolve-error.rs:55:5
+  --> $DIR/resolve-error.rs:53:5
    |
 LL |     Dlona!();
    |     ^^^^^
 
 error: cannot find macro `bang_proc_macrp!` in this scope
-  --> $DIR/resolve-error.rs:58:5
+  --> $DIR/resolve-error.rs:56:5
    |
 LL |     bang_proc_macrp!();
    |     ^^^^^^^^^^^^^^^ help: you could try the macro: `bang_proc_macro`
index 9c49bae28a3bc78f9143080e84b4d61d7c999f0d..61959594c7981b3c6386ce30916d06f58f16e943 100644 (file)
@@ -1,8 +1,8 @@
-// aux-build:derive-a.rs
+// aux-build:test-macros.rs
 
 #[macro_use]
-extern crate derive_a;
+extern crate test_macros;
 #[macro_use]
-extern crate derive_a; //~ ERROR the name `derive_a` is defined multiple times
+extern crate test_macros; //~ ERROR the name `test_macros` is defined multiple times
 
 fn main() {}
index 08057e163496dd633147ee3d5922ebe8f63760f9..e7d95cc8358117d0c24f480b3cba9b40758845d3 100644 (file)
@@ -1,13 +1,13 @@
-error[E0259]: the name `derive_a` is defined multiple times
+error[E0259]: the name `test_macros` is defined multiple times
   --> $DIR/shadow.rs:6:1
    |
-LL | extern crate derive_a;
-   | ---------------------- previous import of the extern crate `derive_a` here
+LL | extern crate test_macros;
+   | ------------------------- previous import of the extern crate `test_macros` here
 LL | #[macro_use]
-LL | extern crate derive_a;
-   | ^^^^^^^^^^^^^^^^^^^^^^ `derive_a` reimported here
+LL | extern crate test_macros;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^ `test_macros` reimported here
    |
-   = note: `derive_a` must be defined only once in the type namespace of this module
+   = note: `test_macros` must be defined only once in the type namespace of this module
 
 error: aborting due to previous error
 
index 64f675ecc1c4d1f3579e1eaff60cdc52ab3341cc..0a82d28e9e544f830964545c26fc85348233effd 100644 (file)
@@ -1,19 +1,18 @@
 //~ ERROR mismatched types
-// aux-build:span-preservation.rs
+// aux-build:test-macros.rs
 
 // For each of these, we should get the appropriate type mismatch error message,
 // and the function should be echoed.
 
-extern crate span_preservation as foo;
+#[macro_use]
+extern crate test_macros;
 
-use foo::foo;
-
-#[foo]
+#[recollect_attr]
 fn a() {
     let x: usize = "hello";;;;; //~ ERROR mismatched types
 }
 
-#[foo]
+#[recollect_attr]
 fn b(x: Option<isize>) -> usize {
     match x {
         Some(x) => { return x }, //~ ERROR mismatched types
@@ -21,7 +20,7 @@ fn b(x: Option<isize>) -> usize {
     }
 }
 
-#[foo]
+#[recollect_attr]
 fn c() {
     struct Foo {
         a: usize
@@ -39,12 +38,12 @@ struct Bar {
 // FIXME: This doesn't work at the moment. See the one below. The pretty-printer
 // injects a "C" between `extern` and `fn` which causes a "probably_eq"
 // `TokenStream` mismatch. The lack of `"C"` should be preserved in the AST.
-#[foo]
+#[recollect_attr]
 extern fn bar() {
     0
 }
 
-#[foo]
+#[recollect_attr]
 extern "C" fn baz() {
     0 //~ ERROR mismatched types
 }
index 1cc7706ce3a4c6e86d304dc191867cc559a23c5a..cf03deee7e44554dd2003cfe1a7a723f156c8f01 100644 (file)
@@ -4,7 +4,7 @@ error[E0308]: mismatched types
               found type `{integer}`
 
 error[E0308]: mismatched types
-  --> $DIR/span-preservation.rs:13:20
+  --> $DIR/span-preservation.rs:12:20
    |
 LL |     let x: usize = "hello";;;;;
    |                    ^^^^^^^ expected usize, found reference
@@ -13,7 +13,7 @@ LL |     let x: usize = "hello";;;;;
               found type `&'static str`
 
 error[E0308]: mismatched types
-  --> $DIR/span-preservation.rs:19:29
+  --> $DIR/span-preservation.rs:18:29
    |
 LL | fn b(x: Option<isize>) -> usize {
    |                           ----- expected `usize` because of return type
@@ -22,13 +22,13 @@ LL |         Some(x) => { return x },
    |                             ^ expected usize, found isize
 
 error[E0308]: mismatched types
-  --> $DIR/span-preservation.rs:35:22
+  --> $DIR/span-preservation.rs:34:22
    |
 LL |     let x = Foo { a: 10isize };
    |                      ^^^^^^^ expected usize, found isize
 
 error[E0560]: struct `c::Foo` has no field named `b`
-  --> $DIR/span-preservation.rs:36:26
+  --> $DIR/span-preservation.rs:35:26
    |
 LL |     let y = Foo { a: 10, b: 10isize };
    |                          ^ `c::Foo` does not have this field
@@ -36,7 +36,7 @@ LL |     let y = Foo { a: 10, b: 10isize };
    = note: available fields are: `a`
 
 error[E0308]: mismatched types
-  --> $DIR/span-preservation.rs:49:5
+  --> $DIR/span-preservation.rs:48:5
    |
 LL | extern "C" fn baz() {
    |                     - possibly return type missing here?
index a1ccf66767104c56a5bd8595553d678745d70840..5f1c2ed08f6b76afdfb36258bb56c4885e4d3ae7 100644 (file)
@@ -51,7 +51,7 @@ fn ok_borrow_of_fn_params(a: usize, b:usize) {
 // TOP-LEVEL FN'S
 
 fn escaping_borrow_of_fn_params_1() {
-    fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+    fn g<'a>(x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
         let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
         //~^ ERROR E0373
         //~| ERROR E0373
@@ -62,7 +62,7 @@ fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 }
 
 fn escaping_borrow_of_fn_params_2() {
-    fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+    fn g<'a>(x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
         let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
         //~^ ERROR E0373
         //~| ERROR E0373
@@ -73,7 +73,7 @@ fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 }
 
 fn move_of_fn_params() {
-    fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+    fn g<'a>(x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
         let f = move |t: bool| if t { x } else { y };
         return Box::new(f);
     };
@@ -86,7 +86,7 @@ fn g<'a>(x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 fn escaping_borrow_of_method_params_1() {
     struct S;
     impl S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -100,7 +100,7 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 fn escaping_borrow_of_method_params_2() {
     struct S;
     impl S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -113,7 +113,7 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 fn move_of_method_params() {
     struct S;
     impl S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = move |t: bool| if t { x } else { y };
             return Box::new(f);
         }
@@ -125,10 +125,10 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 // TRAIT IMPL METHODS
 
 fn escaping_borrow_of_trait_impl_params_1() {
-    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a>; }
+    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a>; }
     struct S;
     impl T for S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -140,10 +140,10 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 }
 
 fn escaping_borrow_of_trait_impl_params_2() {
-    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a>; }
+    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a>; }
     struct S;
     impl T for S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -154,10 +154,10 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 }
 
 fn move_of_trait_impl_params() {
-    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a>; }
+    trait T { fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a>; }
     struct S;
     impl T for S {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = move |t: bool| if t { x } else { y };
             return Box::new(f);
         }
@@ -171,7 +171,7 @@ fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
 fn escaping_borrow_of_trait_default_params_1() {
     struct S;
     trait T {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -185,7 +185,7 @@ impl T for S {}
 fn escaping_borrow_of_trait_default_params_2() {
     struct S;
     trait T {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = |t: bool| if t { x } else { y }; // (separate errors for `x` vs `y`)
             //~^ ERROR E0373
             //~| ERROR E0373
@@ -199,7 +199,7 @@ impl T for S {}
 fn move_of_trait_default_params() {
     struct S;
     trait T {
-        fn g<'a>(&self, x: usize, y:usize) -> Box<Fn(bool) -> usize + 'a> {
+        fn g<'a>(&self, x: usize, y:usize) -> Box<dyn Fn(bool) -> usize + 'a> {
             let f = move |t: bool| if t { x } else { y };
             return Box::new(f);
         }
index 3a211b0463605d58123a8d73bbfde18d25b7c870..40d2b740b430331c7d273bd1d243629dff0b35be 100644 (file)
@@ -10,15 +10,15 @@ trait SomeTrait { }
 
 struct Foo<'a,'b,'c> { //~ ERROR parameter `'c` is never used
     // All of these are ok, because we can derive exactly one bound:
-    a: Box<IsStatic>,
-    b: Box<Is<'static>>,
-    c: Box<Is<'a>>,
-    d: Box<IsSend>,
-    e: Box<Is<'a>+Send>, // we can derive two bounds, but one is 'static, so ok
-    f: Box<SomeTrait>,   // OK, defaults to 'static due to RFC 599.
-    g: Box<SomeTrait+'a>,
+    a: Box<dyn IsStatic>,
+    b: Box<dyn Is<'static>>,
+    c: Box<dyn Is<'a>>,
+    d: Box<dyn IsSend>,
+    e: Box<dyn Is<'a>+Send>, // we can derive two bounds, but one is 'static, so ok
+    f: Box<dyn SomeTrait>,   // OK, defaults to 'static due to RFC 599.
+    g: Box<dyn SomeTrait+'a>,
 
-    z: Box<Is<'a>+'b+'c>,
+    z: Box<dyn Is<'a>+'b+'c>,
     //~^ ERROR only a single explicit lifetime bound is permitted
     //~| ERROR lifetime bound not satisfied
 }
index 8bcb2da4577926cbf2e2e02d351420747a8d7958..003dd0699d3811e58084b4927ea95817a7487f26 100644 (file)
@@ -1,14 +1,14 @@
 error[E0226]: only a single explicit lifetime bound is permitted
-  --> $DIR/region-bounds-on-objects-and-type-parameters.rs:21:22
+  --> $DIR/region-bounds-on-objects-and-type-parameters.rs:21:26
    |
-LL |     z: Box<Is<'a>+'b+'c>,
-   |                      ^^
+LL |     z: Box<dyn Is<'a>+'b+'c>,
+   |                          ^^
 
 error[E0478]: lifetime bound not satisfied
   --> $DIR/region-bounds-on-objects-and-type-parameters.rs:21:5
    |
-LL |     z: Box<Is<'a>+'b+'c>,
-   |     ^^^^^^^^^^^^^^^^^^^^
+LL |     z: Box<dyn Is<'a>+'b+'c>,
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: lifetime parameter instantiated with the lifetime 'b as defined on the struct at 11:15
   --> $DIR/region-bounds-on-objects-and-type-parameters.rs:11:15
index 56e8c40c99f71eae5c6cd559c8c41b7a1ef58bdc..60084773466a6857d2dfc97b8d2f0841c4e023ab 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/region-object-lifetime-2.rs:10:5
    |
-LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a Foo) -> &'b () {
+LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a dyn Foo) -> &'b () {
    |                                          -- -- lifetime `'b` defined here
    |                                          |
    |                                          lifetime `'a` defined here
index 92c85020e9a85110f0b4cb77977511f83dbea5d5..42798487893382471dbc364cfb1cf4a31350a5f5 100644 (file)
@@ -6,7 +6,7 @@ trait Foo {
 }
 
 // Borrowed receiver but two distinct lifetimes, we get an error.
-fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a Foo) -> &'b () {
+fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a dyn Foo) -> &'b () {
     x.borrowed() //~ ERROR cannot infer
 }
 
index d3552ab0c4b2372afc70737276926b9f7862741d..0c5e22ebae2835d3726b914f482d49b3a6d73600 100644 (file)
@@ -7,7 +7,7 @@ LL |     x.borrowed()
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 9:42...
   --> $DIR/region-object-lifetime-2.rs:9:42
    |
-LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a Foo) -> &'b () {
+LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a dyn Foo) -> &'b () {
    |                                          ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/region-object-lifetime-2.rs:10:5
@@ -17,7 +17,7 @@ LL |     x.borrowed()
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 9:45...
   --> $DIR/region-object-lifetime-2.rs:9:45
    |
-LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a Foo) -> &'b () {
+LL | fn borrowed_receiver_different_lifetimes<'a,'b>(x: &'a dyn Foo) -> &'b () {
    |                                             ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/region-object-lifetime-2.rs:10:5
index aa91c371f41b982f69cabdcdd56dfc991937b7c9..75b049dae21f88dc1768a8801b93c29ad463cec4 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/region-object-lifetime-4.rs:12:5
    |
-LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (Foo+'b)) -> &'b () {
+LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (dyn Foo + 'b)) -> &'b () {
    |                                         -- -- lifetime `'b` defined here
    |                                         |
    |                                         lifetime `'a` defined here
index d2ab617ebb76435cfb10d4f1aa94ff32376ff432..4fe12b2acfc69895ebc3fdb2494a2ab0fa94ef01 100644 (file)
@@ -8,7 +8,7 @@ trait Foo {
 // Here we have two distinct lifetimes, but we try to return a pointer
 // with the longer lifetime when (from the signature) we only know
 // that it lives as long as the shorter lifetime. Therefore, error.
-fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (Foo+'b)) -> &'b () {
+fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (dyn Foo + 'b)) -> &'b () {
     x.borrowed() //~ ERROR cannot infer
 }
 
index 75b26ffc6d576a2b094cb6c1eca20edfe3dd4937..e737d27d5606f67f8c769899328334bae85f41bb 100644 (file)
@@ -7,7 +7,7 @@ LL |     x.borrowed()
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 11:41...
   --> $DIR/region-object-lifetime-4.rs:11:41
    |
-LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (Foo+'b)) -> &'b () {
+LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (dyn Foo + 'b)) -> &'b () {
    |                                         ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/region-object-lifetime-4.rs:12:5
@@ -17,7 +17,7 @@ LL |     x.borrowed()
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 11:44...
   --> $DIR/region-object-lifetime-4.rs:11:44
    |
-LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (Foo+'b)) -> &'b () {
+LL | fn borrowed_receiver_related_lifetimes2<'a,'b>(x: &'a (dyn Foo + 'b)) -> &'b () {
    |                                            ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/region-object-lifetime-4.rs:12:5
index bd68aebbeeb0956f99c8bebff8aa6725dcce638d..307bbcbd58d7a37fcc105eef5d7765abf64cdb9f 100644 (file)
@@ -7,7 +7,7 @@ trait Foo {
 
 // Here, the object is bounded by an anonymous lifetime and returned
 // as `&'static`, so you get an error.
-fn owned_receiver(x: Box<Foo>) -> &'static () {
+fn owned_receiver(x: Box<dyn Foo>) -> &'static () {
     x.borrowed() //~ ERROR cannot return value referencing local data `*x`
 }
 
index a54f8f5faab54c150ac6b7feec234c346b97a9d1..43acbfd412d91fc602e8bdaead8d452899f3b088 100644 (file)
@@ -1,15 +1,15 @@
 error[E0621]: explicit lifetime required in the type of `v`
   --> $DIR/region-object-lifetime-in-coercion.rs:8:12
    |
-LL | fn a(v: &[u8]) -> Box<Foo + 'static> {
+LL | fn a(v: &[u8]) -> Box<dyn Foo + 'static> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
-LL |     let x: Box<Foo + 'static> = Box::new(v);
-   |            ^^^^^^^^^^^^^^^^^^ lifetime `'static` required
+LL |     let x: Box<dyn Foo + 'static> = Box::new(v);
+   |            ^^^^^^^^^^^^^^^^^^^^^^ lifetime `'static` required
 
 error[E0621]: explicit lifetime required in the type of `v`
   --> $DIR/region-object-lifetime-in-coercion.rs:14:5
    |
-LL | fn b(v: &[u8]) -> Box<Foo + 'static> {
+LL | fn b(v: &[u8]) -> Box<dyn Foo + 'static> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
 LL |     Box::new(v)
    |     ^^^^^^^^^^^ lifetime `'static` required
@@ -17,7 +17,7 @@ LL |     Box::new(v)
 error[E0621]: explicit lifetime required in the type of `v`
   --> $DIR/region-object-lifetime-in-coercion.rs:21:5
    |
-LL | fn c(v: &[u8]) -> Box<Foo> {
+LL | fn c(v: &[u8]) -> Box<dyn Foo> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
 ...
 LL |     Box::new(v)
@@ -26,7 +26,7 @@ LL |     Box::new(v)
 error: lifetime may not live long enough
   --> $DIR/region-object-lifetime-in-coercion.rs:26:5
    |
-LL | fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
+LL | fn d<'a,'b>(v: &'a [u8]) -> Box<dyn Foo+'b> {
    |      -- -- lifetime `'b` defined here
    |      |
    |      lifetime `'a` defined here
index dfba04b0d25fca10b01e0146f8416ba877d5b2fa..2dc67599913a6041297382c9221ccec57b0d6cc7 100644 (file)
@@ -4,30 +4,30 @@
 trait Foo {}
 impl<'a> Foo for &'a [u8] {}
 
-fn a(v: &[u8]) -> Box<Foo + 'static> {
-    let x: Box<Foo + 'static> = Box::new(v);
+fn a(v: &[u8]) -> Box<dyn Foo + 'static> {
+    let x: Box<dyn Foo + 'static> = Box::new(v);
     //~^ ERROR explicit lifetime required in the type of `v` [E0621]
     x
 }
 
-fn b(v: &[u8]) -> Box<Foo + 'static> {
+fn b(v: &[u8]) -> Box<dyn Foo + 'static> {
     Box::new(v)
         //~^ ERROR explicit lifetime required in the type of `v` [E0621]
 }
 
-fn c(v: &[u8]) -> Box<Foo> {
+fn c(v: &[u8]) -> Box<dyn Foo> {
     // same as previous case due to RFC 599
 
     Box::new(v)
         //~^ ERROR explicit lifetime required in the type of `v` [E0621]
 }
 
-fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
+fn d<'a,'b>(v: &'a [u8]) -> Box<dyn Foo+'b> {
     Box::new(v)
         //~^ ERROR cannot infer an appropriate lifetime due to conflicting
 }
 
-fn e<'a:'b,'b>(v: &'a [u8]) -> Box<Foo+'b> {
+fn e<'a:'b,'b>(v: &'a [u8]) -> Box<dyn Foo+'b> {
     Box::new(v) // OK, thanks to 'a:'b
 }
 
index c94a25ce60478cade7ad75ee6b9bf5cb4807f017..8209fa1840d05d12611aacf30e80edc54c27d419 100644 (file)
@@ -1,15 +1,15 @@
 error[E0621]: explicit lifetime required in the type of `v`
-  --> $DIR/region-object-lifetime-in-coercion.rs:8:33
+  --> $DIR/region-object-lifetime-in-coercion.rs:8:37
    |
-LL | fn a(v: &[u8]) -> Box<Foo + 'static> {
+LL | fn a(v: &[u8]) -> Box<dyn Foo + 'static> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
-LL |     let x: Box<Foo + 'static> = Box::new(v);
-   |                                 ^^^^^^^^^^^ lifetime `'static` required
+LL |     let x: Box<dyn Foo + 'static> = Box::new(v);
+   |                                     ^^^^^^^^^^^ lifetime `'static` required
 
 error[E0621]: explicit lifetime required in the type of `v`
   --> $DIR/region-object-lifetime-in-coercion.rs:14:5
    |
-LL | fn b(v: &[u8]) -> Box<Foo + 'static> {
+LL | fn b(v: &[u8]) -> Box<dyn Foo + 'static> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
 LL |     Box::new(v)
    |     ^^^^^^^^^^^ lifetime `'static` required
@@ -17,7 +17,7 @@ LL |     Box::new(v)
 error[E0621]: explicit lifetime required in the type of `v`
   --> $DIR/region-object-lifetime-in-coercion.rs:21:5
    |
-LL | fn c(v: &[u8]) -> Box<Foo> {
+LL | fn c(v: &[u8]) -> Box<dyn Foo> {
    |         ----- help: add explicit lifetime `'static` to the type of `v`: `&'static [u8]`
 ...
 LL |     Box::new(v)
@@ -32,7 +32,7 @@ LL |     Box::new(v)
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 25:6...
   --> $DIR/region-object-lifetime-in-coercion.rs:25:6
    |
-LL | fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
+LL | fn d<'a,'b>(v: &'a [u8]) -> Box<dyn Foo+'b> {
    |      ^^
    = note: ...so that the expression is assignable:
            expected &[u8]
@@ -40,7 +40,7 @@ LL | fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 25:9...
   --> $DIR/region-object-lifetime-in-coercion.rs:25:9
    |
-LL | fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
+LL | fn d<'a,'b>(v: &'a [u8]) -> Box<dyn Foo+'b> {
    |         ^^
    = note: ...so that the expression is assignable:
            expected std::boxed::Box<(dyn Foo + 'b)>
index 853d96113871884cc4ada0729f98592ad9d125d2..0cbdc828c507fa5ecdcf9111ad0e1d6b28381317 100644 (file)
@@ -9,54 +9,54 @@ trait Iter {
     fn as_item(&self) -> &Self::Item;
 }
 
-fn bad1<T: Iter>(v: T) -> Box<X+'static>
+fn bad1<T: Iter>(v: T) -> Box<dyn X + 'static>
 {
     let item = v.into_item();
     Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live long enough
 }
 
-fn bad2<T: Iter>(v: T) -> Box<X+'static>
+fn bad2<T: Iter>(v: T) -> Box<dyn X + 'static>
     where Box<T::Item> : X
 {
     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>
+fn bad3<'a, T: Iter>(v: T) -> Box<dyn X + 'a>
 {
     let item = v.into_item();
     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>
+fn bad4<'a, T: Iter>(v: T) -> Box<dyn X + 'a>
     where Box<T::Item> : X
 {
     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>
+fn ok1<'a, T: Iter>(v: T) -> Box<dyn X + 'a>
     where T::Item : 'a
 {
     let item = v.into_item();
     Box::new(item) // OK, T::Item : 'a is declared
 }
 
-fn ok2<'a, T: Iter>(v: &T, w: &'a T::Item) -> Box<X+'a>
+fn ok2<'a, T: Iter>(v: &T, w: &'a T::Item) -> Box<dyn X + 'a>
     where T::Item : Clone
 {
     let item = Clone::clone(w);
     Box::new(item) // OK, T::Item : 'a is implied
 }
 
-fn ok3<'a, T: Iter>(v: &'a T) -> Box<X+'a>
+fn ok3<'a, T: Iter>(v: &'a T) -> Box<dyn X + 'a>
     where T::Item : Clone + 'a
 {
     let item = Clone::clone(v.as_item());
     Box::new(item) // OK, T::Item : 'a was declared
 }
 
-fn meh1<'a, T: Iter>(v: &'a T) -> Box<X+'a>
+fn meh1<'a, T: Iter>(v: &'a T) -> Box<dyn X + 'a>
     where T::Item : Clone
 {
     // This case is kind of interesting. It's the same as `ok3` but
index 42df9b1c49fba2fec14e6a6f30dda068c6a1fdee..806a3ca82425b5c2ba2086d4e32ff33d0a777cd0 100644 (file)
@@ -1,16 +1,16 @@
 error: lifetime may not live long enough
   --> $DIR/regions-close-object-into-object-2.rs:10:5
    |
-LL | fn g<'a, T: 'static>(v: Box<A<T>+'a>) -> Box<X+'static> {
+LL | fn g<'a, T: 'static>(v: Box<dyn A<T> + 'a>) -> Box<dyn X + 'static> {
    |      -- lifetime `'a` defined here
-LL |     box B(&*v) as Box<X>
-   |     ^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
+LL |     box B(&*v) as Box<dyn X>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
 
 error[E0515]: cannot return value referencing local data `*v`
   --> $DIR/regions-close-object-into-object-2.rs:10:5
    |
-LL |     box B(&*v) as Box<X>
-   |     ^^^^^^---^^^^^^^^^^^
+LL |     box B(&*v) as Box<dyn X>
+   |     ^^^^^^---^^^^^^^^^^^^^^^
    |     |     |
    |     |     `*v` is borrowed here
    |     returns a value referencing data owned by the current function
index cebb4ac68cbc613a6111687c5aa1e6bd282efeb7..2364ba2728600e7f7a4478c3b4621318ee78689c 100644 (file)
@@ -1,13 +1,13 @@
 #![feature(box_syntax)]
 
 trait A<T> { }
-struct B<'a, T:'a>(&'a (A<T>+'a));
+struct B<'a, T:'a>(&'a (dyn A<T> + 'a));
 
 trait X { }
 impl<'a, T> X for B<'a, T> {}
 
-fn g<'a, T: 'static>(v: Box<A<T>+'a>) -> Box<X+'static> {
-    box B(&*v) as Box<X> //~ ERROR cannot infer
+fn g<'a, T: 'static>(v: Box<dyn A<T> + 'a>) -> Box<dyn X + 'static> {
+    box B(&*v) as Box<dyn X> //~ ERROR cannot infer
 }
 
 fn main() { }
index b5b03e618e1deb7561ac1f2a711c7aa2af528a41..fa203debb3a1b4705923fb25f1ef6ba0005c369d 100644 (file)
@@ -1,18 +1,18 @@
 error[E0495]: cannot infer an appropriate lifetime for borrow expression due to conflicting requirements
   --> $DIR/regions-close-object-into-object-2.rs:10:11
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |           ^^^
    |
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 9:6...
   --> $DIR/regions-close-object-into-object-2.rs:9:6
    |
-LL | fn g<'a, T: 'static>(v: Box<A<T>+'a>) -> Box<X+'static> {
+LL | fn g<'a, T: 'static>(v: Box<dyn A<T> + 'a>) -> Box<dyn X + 'static> {
    |      ^^
 note: ...so that the type `(dyn A<T> + 'a)` is not borrowed for too long
   --> $DIR/regions-close-object-into-object-2.rs:10:11
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |           ^^^
    = note: but, the lifetime must be valid for the static lifetime...
    = note: ...so that the expression is assignable:
index 8af94fa7e79b8b6952ac68ad74069056c0050b01..1e57023bc2320aa64fabe02e270c68fdc937a333 100644 (file)
@@ -1,7 +1,7 @@
 error[E0310]: the parameter type `U` may not live long enough
   --> $DIR/regions-close-object-into-object-4.rs:10:5
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |     ^^^^^^^^^^
    |
    = help: consider adding an explicit lifetime bound `U: 'static`...
@@ -9,16 +9,16 @@ LL |     box B(&*v) as Box<X>
 error: lifetime may not live long enough
   --> $DIR/regions-close-object-into-object-4.rs:10:5
    |
-LL | fn i<'a, T, U>(v: Box<A<U>+'a>) -> Box<X+'static> {
+LL | fn i<'a, T, U>(v: Box<dyn A<U>+'a>) -> Box<dyn X + 'static> {
    |      -- lifetime `'a` defined here
-LL |     box B(&*v) as Box<X>
-   |     ^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
+LL |     box B(&*v) as Box<dyn X>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
 
 error[E0515]: cannot return value referencing local data `*v`
   --> $DIR/regions-close-object-into-object-4.rs:10:5
    |
-LL |     box B(&*v) as Box<X>
-   |     ^^^^^^---^^^^^^^^^^^
+LL |     box B(&*v) as Box<dyn X>
+   |     ^^^^^^---^^^^^^^^^^^^^^^
    |     |     |
    |     |     `*v` is borrowed here
    |     returns a value referencing data owned by the current function
@@ -26,7 +26,7 @@ LL |     box B(&*v) as Box<X>
 error[E0310]: the parameter type `U` may not live long enough
   --> $DIR/regions-close-object-into-object-4.rs:10:9
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |         ^^^^^^
    |
    = help: consider adding an explicit lifetime bound `U: 'static`...
index 91aab057bb9a278c96a5dd212615e13df73baf36..d5310770436866d544eae03d33347d6a3027b907 100644 (file)
@@ -1,13 +1,13 @@
 #![feature(box_syntax)]
 
 trait A<T> { }
-struct B<'a, T:'a>(&'a (A<T>+'a));
+struct B<'a, T:'a>(&'a (dyn A<T> + 'a));
 
 trait X { }
 impl<'a, T> X for B<'a, T> {}
 
-fn i<'a, T, U>(v: Box<A<U>+'a>) -> Box<X+'static> {
-    box B(&*v) as Box<X> //~ ERROR cannot infer
+fn i<'a, T, U>(v: Box<dyn A<U>+'a>) -> Box<dyn X + 'static> {
+    box B(&*v) as Box<dyn X> //~ ERROR cannot infer
 }
 
 fn main() {}
index 20cbcbb841f2babd88c15f10152faf93d6f01368..f5e66f84a9ee7657edad02d8a7cd890a840a3170 100644 (file)
@@ -1,18 +1,18 @@
 error[E0495]: cannot infer an appropriate lifetime for borrow expression due to conflicting requirements
   --> $DIR/regions-close-object-into-object-4.rs:10:11
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |           ^^^
    |
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 9:6...
   --> $DIR/regions-close-object-into-object-4.rs:9:6
    |
-LL | fn i<'a, T, U>(v: Box<A<U>+'a>) -> Box<X+'static> {
+LL | fn i<'a, T, U>(v: Box<dyn A<U>+'a>) -> Box<dyn X + 'static> {
    |      ^^
 note: ...so that the type `(dyn A<U> + 'a)` is not borrowed for too long
   --> $DIR/regions-close-object-into-object-4.rs:10:11
    |
-LL |     box B(&*v) as Box<X>
+LL |     box B(&*v) as Box<dyn X>
    |           ^^^
    = note: but, the lifetime must be valid for the static lifetime...
    = note: ...so that the expression is assignable:
index 30fdb820e3630226bec9f631e9d3b073d8418b3d..7d3d51bdb437ebe8caa02ad430935beec947d00a 100644 (file)
@@ -1,7 +1,7 @@
 error[E0310]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:10:5
    |
-LL |     box v as Box<SomeTrait+'static>
+LL |     box v as Box<dyn SomeTrait + 'static>
    |     ^^^^^
    |
    = help: consider adding an explicit lifetime bound `A: 'static`...
@@ -9,7 +9,7 @@ LL |     box v as Box<SomeTrait+'static>
 error[E0309]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:20:5
    |
-LL |     box v as Box<SomeTrait+'b>
+LL |     box v as Box<dyn SomeTrait + 'b>
    |     ^^^^^
    |
    = help: consider adding an explicit lifetime bound `A: 'b`...
index 9aee9663e8f46a1f828cdb1fd1c6255f68d9fe5b..6a9aa66a446c378cbd54a19b34327139b7ea122c 100644 (file)
@@ -6,18 +6,18 @@
 
 trait SomeTrait { fn get(&self) -> isize; }
 
-fn make_object1<A:SomeTrait>(v: A) -> Box<SomeTrait+'static> {
-    box v as Box<SomeTrait+'static>
+fn make_object1<A:SomeTrait>(v: A) -> Box<dyn SomeTrait + 'static> {
+    box v as Box<dyn SomeTrait + 'static>
         //~^ ERROR the parameter type `A` may not live long enough
         //~| ERROR the parameter type `A` may not live long enough
 }
 
-fn make_object2<'a,A:SomeTrait+'a>(v: A) -> Box<SomeTrait+'a> {
-    box v as Box<SomeTrait+'a>
+fn make_object2<'a,A:SomeTrait+'a>(v: A) -> Box<dyn SomeTrait + 'a> {
+    box v as Box<dyn SomeTrait + 'a>
 }
 
-fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<SomeTrait+'b> {
-    box v as Box<SomeTrait+'b>
+fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<dyn SomeTrait + 'b> {
+    box v as Box<dyn SomeTrait + 'b>
         //~^ ERROR the parameter type `A` may not live long enough
         //~| ERROR the parameter type `A` may not live long enough
 }
index 615c55d9da3460c446b3c2102e0aed417b2e57dd..81534b7b770d0df3e55a5307453ffced1bea2a9c 100644 (file)
@@ -1,58 +1,58 @@
 error[E0310]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:10:5
    |
-LL | fn make_object1<A:SomeTrait>(v: A) -> Box<SomeTrait+'static> {
+LL | fn make_object1<A:SomeTrait>(v: A) -> Box<dyn SomeTrait + 'static> {
    |                 -- help: consider adding an explicit lifetime bound `A: 'static`...
-LL |     box v as Box<SomeTrait+'static>
+LL |     box v as Box<dyn SomeTrait + 'static>
    |     ^^^^^
    |
 note: ...so that the type `A` will meet its required lifetime bounds
   --> $DIR/regions-close-over-type-parameter-1.rs:10:5
    |
-LL |     box v as Box<SomeTrait+'static>
+LL |     box v as Box<dyn SomeTrait + 'static>
    |     ^^^^^
 
 error[E0310]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:10:5
    |
-LL | fn make_object1<A:SomeTrait>(v: A) -> Box<SomeTrait+'static> {
+LL | fn make_object1<A:SomeTrait>(v: A) -> Box<dyn SomeTrait + 'static> {
    |                 -- help: consider adding an explicit lifetime bound `A: 'static`...
-LL |     box v as Box<SomeTrait+'static>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'static>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: ...so that it can be closed over into an object
   --> $DIR/regions-close-over-type-parameter-1.rs:10:5
    |
-LL |     box v as Box<SomeTrait+'static>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'static>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0309]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:20:5
    |
-LL | fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<SomeTrait+'b> {
+LL | fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<dyn SomeTrait + 'b> {
    |                       -- help: consider adding an explicit lifetime bound `A: 'b`...
-LL |     box v as Box<SomeTrait+'b>
+LL |     box v as Box<dyn SomeTrait + 'b>
    |     ^^^^^
    |
 note: ...so that the type `A` will meet its required lifetime bounds
   --> $DIR/regions-close-over-type-parameter-1.rs:20:5
    |
-LL |     box v as Box<SomeTrait+'b>
+LL |     box v as Box<dyn SomeTrait + 'b>
    |     ^^^^^
 
 error[E0309]: the parameter type `A` may not live long enough
   --> $DIR/regions-close-over-type-parameter-1.rs:20:5
    |
-LL | fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<SomeTrait+'b> {
+LL | fn make_object3<'a,'b,A:SomeTrait+'a>(v: A) -> Box<dyn SomeTrait + 'b> {
    |                       -- help: consider adding an explicit lifetime bound `A: 'b`...
-LL |     box v as Box<SomeTrait+'b>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'b>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: ...so that it can be closed over into an object
   --> $DIR/regions-close-over-type-parameter-1.rs:20:5
    |
-LL |     box v as Box<SomeTrait+'b>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'b>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to 4 previous errors
 
index 001ed7fe4c53a678b262deeb35a9596a43b48267..88d6abd1428aaf4376356cf10c747b9c0f90c744 100644 (file)
@@ -1,13 +1,13 @@
 error: lifetime may not live long enough
   --> $DIR/regions-close-over-type-parameter-multiple.rs:20:5
    |
-LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'c> {
+LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'c> {
    |                    --    -- lifetime `'c` defined here
    |                    |
    |                    lifetime `'a` defined here
 LL |     // A outlives 'a AND 'b...but not 'c.
-LL |     box v as Box<SomeTrait+'a>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'c`
+LL |     box v as Box<dyn SomeTrait + 'a>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'c`
 
 error: aborting due to previous error
 
index defbc5d9f2395ead8a23d50b1ba35dca626b2266..26643e08985be6107d873e27a0c481a4d390cbba 100644 (file)
@@ -5,19 +5,19 @@
 
 trait SomeTrait { fn get(&self) -> isize; }
 
-fn make_object_good1<'a,'b,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'a> {
+fn make_object_good1<'a,'b,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'a> {
     // A outlives 'a AND 'b...
-    box v as Box<SomeTrait+'a> // ...hence this type is safe.
+    box v as Box<dyn SomeTrait + 'a> // ...hence this type is safe.
 }
 
-fn make_object_good2<'a,'b,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'b> {
+fn make_object_good2<'a,'b,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'b> {
     // A outlives 'a AND 'b...
-    box v as Box<SomeTrait+'b> // ...hence this type is safe.
+    box v as Box<dyn SomeTrait + 'b> // ...hence this type is safe.
 }
 
-fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'c> {
+fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'c> {
     // A outlives 'a AND 'b...but not 'c.
-    box v as Box<SomeTrait+'a> //~ ERROR cannot infer an appropriate lifetime
+    box v as Box<dyn SomeTrait + 'a> //~ ERROR cannot infer an appropriate lifetime
 }
 
 fn main() {
index 96e6a329e7d52cb9b939d72afc2b78f41d05ea95..8b3dbc8b64902c6f1f1d8c9a6ddf678dbe115e08 100644 (file)
@@ -1,23 +1,23 @@
 error[E0495]: cannot infer an appropriate lifetime due to conflicting requirements
   --> $DIR/regions-close-over-type-parameter-multiple.rs:20:5
    |
-LL |     box v as Box<SomeTrait+'a>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'a>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 18:20...
   --> $DIR/regions-close-over-type-parameter-multiple.rs:18:20
    |
-LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'c> {
+LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'c> {
    |                    ^^
 note: ...so that the declared lifetime parameter bounds are satisfied
   --> $DIR/regions-close-over-type-parameter-multiple.rs:20:5
    |
-LL |     box v as Box<SomeTrait+'a>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     box v as Box<dyn SomeTrait + 'a>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 note: but, the lifetime must be valid for the lifetime 'c as defined on the function body at 18:26...
   --> $DIR/regions-close-over-type-parameter-multiple.rs:18:26
    |
-LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<SomeTrait+'c> {
+LL | fn make_object_bad<'a,'b,'c,A:SomeTrait+'a+'b>(v: A) -> Box<dyn SomeTrait + 'c> {
    |                          ^^
    = note: ...so that the expression is assignable:
            expected std::boxed::Box<(dyn SomeTrait + 'c)>
index 86590748cb2d41431253d7181309be7477c73bd3..2760e5eed9595c5be1ede8cde7f2c785bc42c443 100644 (file)
@@ -1,24 +1,24 @@
 trait X { fn foo(&self) {} }
 
-fn p1<T>(v: T) -> Box<X+'static>
+fn p1<T>(v: T) -> Box<dyn X + 'static>
     where T : X
 {
     Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
-fn p2<T>(v: Box<T>) -> Box<X+'static>
+fn p2<T>(v: Box<T>) -> Box<dyn X + 'static>
     where Box<T> : X
 {
     Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
-fn p3<'a,T>(v: T) -> Box<X+'a>
+fn p3<'a,T>(v: T) -> Box<dyn X + 'a>
     where T : X
 {
     Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
-fn p4<'a,T>(v: Box<T>) -> Box<X+'a>
+fn p4<'a,T>(v: Box<T>) -> Box<dyn X + 'a>
     where Box<T> : X
 {
     Box::new(v) //~ ERROR parameter type `T` may not live long enough
index ef226073de6d37651bec82dfc396886f9e6bda83..7f2c646c12196ea5e70d12be0d1e7e43b45b98dd 100644 (file)
@@ -1,7 +1,7 @@
 error[E0310]: the parameter type `T` may not live long enough
   --> $DIR/regions-close-param-into-object.rs:6:5
    |
-LL | fn p1<T>(v: T) -> Box<X+'static>
+LL | fn p1<T>(v: T) -> Box<dyn X + 'static>
    |       - help: consider adding an explicit lifetime bound `T: 'static`...
 ...
 LL |     Box::new(v)
@@ -16,7 +16,7 @@ LL |     Box::new(v)
 error[E0310]: the parameter type `T` may not live long enough
   --> $DIR/regions-close-param-into-object.rs:12:5
    |
-LL | fn p2<T>(v: Box<T>) -> Box<X+'static>
+LL | fn p2<T>(v: Box<T>) -> Box<dyn X + 'static>
    |       - help: consider adding an explicit lifetime bound `T: 'static`...
 ...
 LL |     Box::new(v)
@@ -31,7 +31,7 @@ LL |     Box::new(v)
 error[E0309]: the parameter type `T` may not live long enough
   --> $DIR/regions-close-param-into-object.rs:18:5
    |
-LL | fn p3<'a,T>(v: T) -> Box<X+'a>
+LL | fn p3<'a,T>(v: T) -> Box<dyn X + 'a>
    |          - help: consider adding an explicit lifetime bound `T: 'a`...
 ...
 LL |     Box::new(v)
@@ -46,7 +46,7 @@ LL |     Box::new(v)
 error[E0309]: the parameter type `T` may not live long enough
   --> $DIR/regions-close-param-into-object.rs:24:5
    |
-LL | fn p4<'a,T>(v: Box<T>) -> Box<X+'a>
+LL | fn p4<'a,T>(v: Box<T>) -> Box<dyn X + 'a>
    |          - help: consider adding an explicit lifetime bound `T: 'a`...
 ...
 LL |     Box::new(v)
index 7e04b6782eba1c52c5edf8cda8f8f916af80e0eb..a4272802af54d0ee453b0e2e6a260ce405d5da5a 100644 (file)
@@ -18,7 +18,7 @@ trait Trait2<'a, 'b> {
 // this argument `t` is not automatically considered well-formed,
 // since for it to be WF, we would need to know that `'y: 'x`, but we
 // do not infer that.
-fn callee<'x, 'y, T>(t: &'x for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
+fn callee<'x, 'y, T>(t: &'x dyn for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
     //~^ ERROR reference has a longer lifetime than the data it references
 {
 }
index ca86eb7edae18282e55b06eef545ddbc5833e06f..b3390bcc4d50b3ebb30fdd25b0ff927e569869d1 100644 (file)
@@ -1,7 +1,7 @@
 error[E0491]: in type `&'x (dyn for<'z> Trait1<<T as Trait2<'y, 'z>>::Foo> + 'x)`, reference has a longer lifetime than the data it references
   --> $DIR/regions-implied-bounds-projection-gap-hr-1.rs:21:1
    |
-LL | / fn callee<'x, 'y, T>(t: &'x for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
+LL | / fn callee<'x, 'y, T>(t: &'x dyn for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
 LL | |
 LL | | {
 LL | | }
@@ -10,12 +10,12 @@ LL | | }
 note: the pointer is valid for the lifetime 'x as defined on the function body at 21:11
   --> $DIR/regions-implied-bounds-projection-gap-hr-1.rs:21:11
    |
-LL | fn callee<'x, 'y, T>(t: &'x for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
+LL | fn callee<'x, 'y, T>(t: &'x dyn for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
    |           ^^
 note: but the referenced data is only valid for the lifetime 'y as defined on the function body at 21:15
   --> $DIR/regions-implied-bounds-projection-gap-hr-1.rs:21:15
    |
-LL | fn callee<'x, 'y, T>(t: &'x for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
+LL | fn callee<'x, 'y, T>(t: &'x dyn for<'z> Trait1< <T as Trait2<'y, 'z>>::Foo >)
    |               ^^
 
 error: aborting due to previous error
index 0fd734d57b5ce5ea5e4a246492d083c0f7faff37..fb9c5d5c210c92d26618dbdbd1d007d4d22e38f4 100644 (file)
@@ -1,13 +1,13 @@
 struct Parameterized1<'a> {
-    g: Box<FnMut() + 'a>
+    g: Box<dyn FnMut() + 'a>
 }
 
 struct NotParameterized1 {
-    g: Box<FnMut() + 'static>
+    g: Box<dyn FnMut() + 'static>
 }
 
 struct NotParameterized2 {
-    g: Box<FnMut() + 'static>
+    g: Box<dyn FnMut() + 'static>
 }
 
 fn take1<'a>(p: Parameterized1) -> Parameterized1<'a> { p }
index 168bf0284a18ea8d5718c8bc1275922f92d9fc90..5843598ab48e47cb358167d8e51059d05b95a096 100644 (file)
@@ -1,5 +1,5 @@
 struct Invariant<'a> {
-    f: Box<FnOnce(&mut &'a isize) + 'static>,
+    f: Box<dyn FnOnce(&mut &'a isize) + 'static>,
 }
 
 fn to_same_lifetime<'r>(b_isize: Invariant<'r>) {
index 90c86cebce38f8299f186327bbf2de7deb43cd3d..f0af18cf61804e353b148688399c1046cb98b8f0 100644 (file)
@@ -1,5 +1,5 @@
 struct Invariant<'a> {
-    f: Box<FnOnce() -> *mut &'a isize + 'static>,
+    f: Box<dyn FnOnce() -> *mut &'a isize + 'static>,
 }
 
 fn to_same_lifetime<'r>(b_isize: Invariant<'r>) {
index 214402952a3db653a81c146783d32d6a2dc81c02..d1744f8a51eee85c8adb886f346198411cb6f6be 100644 (file)
@@ -4,12 +4,12 @@ struct Direct<'a> {
 
 struct Indirect1 {
     // Here the lifetime parameter of direct is bound by the fn()
-    g: Box<FnOnce(Direct) + 'static>
+    g: Box<dyn FnOnce(Direct) + 'static>
 }
 
 struct Indirect2<'a> {
     // But here it is set to 'a
-    g: Box<FnOnce(Direct<'a>) + 'static>
+    g: Box<dyn FnOnce(Direct<'a>) + 'static>
 }
 
 fn take_direct<'a,'b>(p: Direct<'a>) -> Direct<'b> { p } //~ ERROR mismatched types
index 230a97a04b625f81c187d8a968f4cdf2fdda045e..044c688977262a2de110edd247b9cffe9c92d17d 100644 (file)
@@ -33,14 +33,14 @@ fn f(a: &'a isize) { } //~ ERROR undeclared lifetime
 
     // &'a CAN be declared on functions and used then:
     fn g<'a>(a: &'a isize) { } // OK
-    fn h(a: Box<for<'a> FnOnce(&'a isize)>) { } // OK
+    fn h(a: Box<dyn for<'a> FnOnce(&'a isize)>) { } // OK
 }
 
 // Test nesting of lifetimes in fn type declarations
 fn fn_types(a: &'a isize, //~ ERROR undeclared lifetime
-            b: Box<for<'a> FnOnce(&'a isize,
+            b: Box<dyn for<'a> FnOnce(&'a isize,
                                   &'b isize, //~ ERROR undeclared lifetime
-                                  Box<for<'b> FnOnce(&'a isize,
+                                  Box<dyn for<'b> FnOnce(&'a isize,
                                                      &'b isize)>,
                                   &'b isize)>, //~ ERROR undeclared lifetime
             c: &'a isize) //~ ERROR undeclared lifetime
index c11c09b6d0d51cdfa0d1db77e4a38f968043a224..97650636cb67f2b63311479fdf05d5dfddb1db15 100644 (file)
@@ -4,8 +4,8 @@ error[E0521]: borrowed data escapes outside of closure
 LL |     let mut ay = &y;
    |         ------ `ay` is declared here, outside of the closure body
 LL | 
-LL |     ignore::<Box<for<'z> FnMut(&'z isize)>>(Box::new(|z| {
-   |                                                       - `z` is a reference that is only valid in the closure body
+LL |     ignore::<Box<dyn for<'z> FnMut(&'z isize)>>(Box::new(|z| {
+   |                                                           - `z` is a reference that is only valid in the closure body
 ...
 LL |         ay = z;
    |         ^^^^^^ `z` escapes the closure body here
@@ -25,8 +25,8 @@ LL | }
 error[E0597]: `y` does not live long enough
   --> $DIR/regions-nested-fns.rs:9:15
    |
-LL |     ignore::<Box<for<'z> FnMut(&'z isize)>>(Box::new(|z| {
-   |                                                      --- value captured here
+LL |     ignore::<Box<dyn for<'z> FnMut(&'z isize)>>(Box::new(|z| {
+   |                                                          --- value captured here
 LL |         ay = x;
 LL |         ay = &y;
    |               ^ borrowed value does not live long enough
index 161d812f016a6545c7ee87401cba7b908d52d831..c02d4e0ce453b1629c7a2fc93c14e584a3810012 100644 (file)
@@ -4,13 +4,13 @@ fn nested<'x>(x: &'x isize) {
     let y = 3;
     let mut ay = &y; //~ ERROR E0495
 
-    ignore::<Box<for<'z> FnMut(&'z isize)>>(Box::new(|z| {
+    ignore::<Box<dyn for<'z> FnMut(&'z isize)>>(Box::new(|z| {
         ay = x;
         ay = &y;
         ay = z;
     }));
 
-    ignore::< Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+    ignore::< Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
         if false { return x; } //~ ERROR E0312
         if false { return ay; }
         return z;
index 702254a0ac42331eb1404f509ddade0f3ecefa45..15c9c9ca4ddbbf4e08296dd3304bbeafa2ca6264 100644 (file)
@@ -4,11 +4,11 @@ error[E0495]: cannot infer an appropriate lifetime due to conflicting requiremen
 LL |     let mut ay = &y;
    |                  ^^
    |
-note: first, the lifetime cannot outlive the anonymous lifetime #2 defined on the body at 7:54...
-  --> $DIR/regions-nested-fns.rs:7:54
+note: first, the lifetime cannot outlive the anonymous lifetime #2 defined on the body at 7:58...
+  --> $DIR/regions-nested-fns.rs:7:58
    |
-LL |       ignore::<Box<for<'z> FnMut(&'z isize)>>(Box::new(|z| {
-   |  ______________________________________________________^
+LL |       ignore::<Box<dyn for<'z> FnMut(&'z isize)>>(Box::new(|z| {
+   |  __________________________________________________________^
 LL | |         ay = x;
 LL | |         ay = &y;
 LL | |         ay = z;
@@ -19,11 +19,11 @@ note: ...so that reference does not outlive borrowed content
    |
 LL |         ay = z;
    |              ^
-note: but, the lifetime must be valid for the anonymous lifetime #2 defined on the body at 13:68...
-  --> $DIR/regions-nested-fns.rs:13:68
+note: but, the lifetime must be valid for the anonymous lifetime #2 defined on the body at 13:72...
+  --> $DIR/regions-nested-fns.rs:13:72
    |
-LL |       ignore::< Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
-   |  ____________________________________________________________________^
+LL |       ignore::< Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+   |  ________________________________________________________________________^
 LL | |         if false { return x; }
 LL | |         if false { return ay; }
 LL | |         return z;
@@ -39,11 +39,11 @@ error[E0312]: lifetime of reference outlives lifetime of borrowed content...
 LL |         if false { return x; }
    |                           ^
    |
-note: ...the reference is valid for the anonymous lifetime #2 defined on the body at 13:68...
-  --> $DIR/regions-nested-fns.rs:13:68
+note: ...the reference is valid for the anonymous lifetime #2 defined on the body at 13:72...
+  --> $DIR/regions-nested-fns.rs:13:72
    |
-LL |       ignore::< Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
-   |  ____________________________________________________________________^
+LL |       ignore::< Box<dyn for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
+   |  ________________________________________________________________________^
 LL | |         if false { return x; }
 LL | |         if false { return ay; }
 LL | |         return z;
index f2010dbe62d8d602c2ee8e1655eb7e8c810c34ee..0c903b738499265288fc5c0bcd5fc928c8e976ff 100644 (file)
@@ -1,10 +1,10 @@
-fn borrowed_proc<'a>(x: &'a isize) -> Box<FnMut()->(isize) + 'a> {
+fn borrowed_proc<'a>(x: &'a isize) -> Box<dyn FnMut()->(isize) + 'a> {
     // This is legal, because the region bound on `proc`
     // states that it captures `x`.
     Box::new(move|| { *x })
 }
 
-fn static_proc(x: &isize) -> Box<FnMut()->(isize) + 'static> {
+fn static_proc(x: &isize) -> Box<dyn FnMut()->(isize) + 'static> {
     // This is illegal, because the region bound on `proc` is 'static.
     Box::new(move|| { *x }) //~ ERROR explicit lifetime required in the type of `x` [E0621]
 }
index aea7347d53c27546c355c9dcb69ec8883c68b382..c53af34456ef3126650fd5dc2c7da6aba2dce916 100644 (file)
@@ -1,7 +1,7 @@
 error[E0621]: explicit lifetime required in the type of `x`
   --> $DIR/regions-proc-bound-capture.rs:9:5
    |
-LL | fn static_proc(x: &isize) -> Box<FnMut()->(isize) + 'static> {
+LL | fn static_proc(x: &isize) -> Box<dyn FnMut()->(isize) + 'static> {
    |                   ------ help: add explicit lifetime `'static` to the type of `x`: `&'static isize`
 LL |     // This is illegal, because the region bound on `proc` is 'static.
 LL |     Box::new(move|| { *x })
index e6b34510bb567722681c7032bdb37e51f1a61974..83e93522c9483c93951eba13dfd3a32f29fe5c45 100644 (file)
@@ -1,10 +1,10 @@
 #![feature(fn_traits)]
 
 struct ClosureBox<'a> {
-    cl: Box<FnMut() + 'a>,
+    cl: Box<dyn FnMut() + 'a>,
 }
 
-fn box_it<'r>(x: Box<FnMut() + 'r>) -> ClosureBox<'r> {
+fn box_it<'r>(x: Box<dyn FnMut() + 'r>) -> ClosureBox<'r> {
     ClosureBox {cl: x}
 }
 
index 7273887193620448337c953b5092983a8698d299..0da8ac53695e954078a01fe24e87c89e95bc132c 100644 (file)
@@ -19,12 +19,12 @@ fn get_ctxt(&self) -> &'a Ctxt { //~ ERROR method not compatible with trait
 
 }
 
-fn get_v(gc: Box<GetCtxt>) -> usize {
+fn get_v(gc: Box<dyn GetCtxt>) -> usize {
     gc.get_ctxt().v
 }
 
 fn main() {
     let ctxt = Ctxt { v: 22 };
     let hc = HasCtxt { c: &ctxt };
-    assert_eq!(get_v(box hc as Box<GetCtxt>), 22);
+    assert_eq!(get_v(box hc as Box<dyn GetCtxt>), 22);
 }
index eccf1b5e8cf76f0add4a63e0054ed8cb3480fa2e..f4b1a89db9a73ef8ef1510a465a72aebffb4cce3 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/regions-trait-object-subtyping.rs:15:5
    |
-LL | fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+LL | fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
    |         -- -- lifetime `'b` defined here
    |         |
    |         lifetime `'a` defined here
@@ -12,7 +12,7 @@ LL |     x
 error: lifetime may not live long enough
   --> $DIR/regions-trait-object-subtyping.rs:22:5
    |
-LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut Dummy>) -> Wrapper<&'b mut Dummy> {
+LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut dyn Dummy>) -> Wrapper<&'b mut dyn Dummy> {
    |         --    -- lifetime `'b` defined here
    |         |
    |         lifetime `'a` defined here
index eb2623544563f29b23dc9c49cb171776c6bd286b..5b36194870ef697c9955082957f3520359331efc 100644 (file)
@@ -1,23 +1,23 @@
 trait Dummy { fn dummy(&self); }
 
-fn foo1<'a:'b,'b>(x: &'a mut (Dummy+'a)) -> &'b mut (Dummy+'b) {
+fn foo1<'a:'b,'b>(x: &'a mut (dyn Dummy+'a)) -> &'b mut (dyn Dummy+'b) {
     // Here, we are able to coerce
     x
 }
 
-fn foo2<'a:'b,'b>(x: &'b mut (Dummy+'a)) -> &'b mut (Dummy+'b) {
+fn foo2<'a:'b,'b>(x: &'b mut (dyn Dummy+'a)) -> &'b mut (dyn Dummy+'b) {
     // Here, we are able to coerce
     x
 }
 
-fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
     // Without knowing 'a:'b, we can't coerce
     x //~ ERROR lifetime bound not satisfied
      //~^ ERROR cannot infer an appropriate lifetime
 }
 
 struct Wrapper<T>(T);
-fn foo4<'a:'b,'b>(x: Wrapper<&'a mut Dummy>) -> Wrapper<&'b mut Dummy> {
+fn foo4<'a:'b,'b>(x: Wrapper<&'a mut dyn Dummy>) -> Wrapper<&'b mut dyn Dummy> {
     // We can't coerce because it is packed in `Wrapper`
     x //~ ERROR mismatched types
 }
index f2d2b37d90726569340398be813fdeef573dedfe..6de92f13840b3310b3a931a63a05e6702736315f 100644 (file)
@@ -7,12 +7,12 @@ LL |     x
 note: lifetime parameter instantiated with the lifetime 'a as defined on the function body at 13:9
   --> $DIR/regions-trait-object-subtyping.rs:13:9
    |
-LL | fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+LL | fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
    |         ^^
 note: but lifetime parameter must outlive the lifetime 'b as defined on the function body at 13:12
   --> $DIR/regions-trait-object-subtyping.rs:13:12
    |
-LL | fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+LL | fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
    |            ^^
 
 error[E0495]: cannot infer an appropriate lifetime for automatic coercion due to conflicting requirements
@@ -24,7 +24,7 @@ LL |     x
 note: first, the lifetime cannot outlive the lifetime 'a as defined on the function body at 13:9...
   --> $DIR/regions-trait-object-subtyping.rs:13:9
    |
-LL | fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+LL | fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
    |         ^^
 note: ...so that reference does not outlive borrowed content
   --> $DIR/regions-trait-object-subtyping.rs:15:5
@@ -34,7 +34,7 @@ LL |     x
 note: but, the lifetime must be valid for the lifetime 'b as defined on the function body at 13:12...
   --> $DIR/regions-trait-object-subtyping.rs:13:12
    |
-LL | fn foo3<'a,'b>(x: &'a mut Dummy) -> &'b mut Dummy {
+LL | fn foo3<'a,'b>(x: &'a mut dyn Dummy) -> &'b mut dyn Dummy {
    |            ^^
    = note: ...so that the expression is assignable:
            expected &'b mut (dyn Dummy + 'b)
@@ -51,12 +51,12 @@ LL |     x
 note: the lifetime 'b as defined on the function body at 20:15...
   --> $DIR/regions-trait-object-subtyping.rs:20:15
    |
-LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut Dummy>) -> Wrapper<&'b mut Dummy> {
+LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut dyn Dummy>) -> Wrapper<&'b mut dyn Dummy> {
    |               ^^
 note: ...does not necessarily outlive the lifetime 'a as defined on the function body at 20:9
   --> $DIR/regions-trait-object-subtyping.rs:20:9
    |
-LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut Dummy>) -> Wrapper<&'b mut Dummy> {
+LL | fn foo4<'a:'b,'b>(x: Wrapper<&'a mut dyn Dummy>) -> Wrapper<&'b mut dyn Dummy> {
    |         ^^
 
 error: aborting due to 3 previous errors
index 73baa84ec9049fd3d5bc7070eb145957474acc0c..9169d457d40514dda3334cfa23f844923d76d17c 100644 (file)
@@ -23,10 +23,10 @@ fn drop(&mut self) {
 }
 
 struct A<'r> {
-    p: &'r (X+'r)
+    p: &'r (dyn X + 'r)
 }
 
-fn make_a(p:&X) -> A {
+fn make_a(p: &dyn X) -> A {
     A{p:p}
 }
 
index 61bab359f9a088e5c86850b7976407b62e31ebbb..d0053b202344559a597b26f28215bab9243033fa 100644 (file)
@@ -4,7 +4,7 @@
 trait TheTrait<'t>: 't { }
 
 struct Foo<'a,'b> {
-    x: Box<TheTrait<'a>+'b> //~ ERROR E0478
+    x: Box<dyn TheTrait<'a>+'b> //~ ERROR E0478
 }
 
 fn main() { }
index 3dc1c4dcd22d242aea3d2efd2f1876218b91ca40..4e12478c36da3d890ba6760b943c6aeaac52749c 100644 (file)
@@ -1,8 +1,8 @@
 error[E0478]: lifetime bound not satisfied
   --> $DIR/regions-wf-trait-object.rs:7:5
    |
-LL |     x: Box<TheTrait<'a>+'b>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^
+LL |     x: Box<dyn TheTrait<'a>+'b>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: lifetime parameter instantiated with the lifetime 'b as defined on the struct at 6:15
   --> $DIR/regions-wf-trait-object.rs:6:15
index af335acd41bc34a51b8518cedf8de45ca824053b..95635e12a63b123ba53107ceb8ec99279d2532de 100644 (file)
@@ -2,7 +2,7 @@ pub trait ToNbt<T> {
     fn new(val: T) -> Self;
 }
 
-impl ToNbt<Self> {}
+impl dyn ToNbt<Self> {}
 //~^ ERROR cycle detected
 
 fn main() {}
index 1da56ad05d28c11b3fd12e5a4cbb045a20d74904..0ed3af81d566820a4d7a137b13cf7fa4f49d7758 100644 (file)
@@ -1,10 +1,10 @@
-error[E0391]: cycle detected when processing `<impl at $DIR/issue-23305.rs:5:1: 5:20>`
-  --> $DIR/issue-23305.rs:5:12
+error[E0391]: cycle detected when processing `<impl at $DIR/issue-23305.rs:5:1: 5:24>`
+  --> $DIR/issue-23305.rs:5:16
    |
-LL | impl ToNbt<Self> {}
-   |            ^^^^
+LL | impl dyn ToNbt<Self> {}
+   |                ^^^^
    |
-   = note: ...which again requires processing `<impl at $DIR/issue-23305.rs:5:1: 5:20>`, completing the cycle
+   = note: ...which again requires processing `<impl at $DIR/issue-23305.rs:5:1: 5:24>`, completing the cycle
 note: cycle used when collecting item types in top-level module
   --> $DIR/issue-23305.rs:1:1
    |
index dd31fc231cfb5d4654ca251eac72350b3641dd01..e233ec631cc13d7e57f8296a63978fbe6c389bc7 100644 (file)
@@ -7,6 +7,6 @@ trait Bar {}
 impl Bar for Foo {}
 
 fn main() {
-    let any: &Any = &Bar; //~ ERROR expected value, found trait `Bar`
+    let any: &dyn Any = &Bar; //~ ERROR expected value, found trait `Bar`
     if any.is::<u32>() { println!("u32"); }
 }
index 29a63fdd11fe57c3906292301e67608e2394bae1..52308f2a7f028241054a07e1f33ee97cb1b8ac69 100644 (file)
@@ -1,8 +1,8 @@
 error[E0423]: expected value, found trait `Bar`
-  --> $DIR/issue-33876.rs:10:22
+  --> $DIR/issue-33876.rs:10:26
    |
-LL |     let any: &Any = &Bar;
-   |                      ^^^ not a value
+LL |     let any: &dyn Any = &Bar;
+   |                          ^^^ not a value
 
 error: aborting due to previous error
 
index dc9624698dfdd15c17b8a36fb75c519ad113ab16..46f145e63e1579d10c27dea67589e3299f7a7335 100644 (file)
@@ -2,7 +2,7 @@
 
 extern crate issue_3907;
 
-type Foo = issue_3907::Foo+'static;
+type Foo = dyn issue_3907::Foo + 'static;
 
 struct S {
     name: isize
index 87e465489a481be0ab34fdccf2dcbb20229820e4..6211de4271782ebb7491172dd6207a950a63d128 100644 (file)
@@ -2,7 +2,7 @@
 
 extern crate issue_3907;
 
-type Foo = issue_3907::Foo;
+type Foo = dyn issue_3907::Foo;
 
 struct S {
     name: isize
index f88a2375a4315094233414ca7d43d6b08ce91e69..b831bb4be34877410470f8f062f8d94a9288c673 100644 (file)
@@ -1,5 +1,5 @@
 trait I {}
-type K = I+'static;
+type K = dyn I + 'static;
 
 fn foo(_x: K) {}
 //~^ ERROR the size for values of type
index c00567a75b7a3b9aa0af28d746b5abe9de2b2011..49fa312f9d257f1f8ba74c0fa1031e7322ba7cd1 100644 (file)
@@ -1,5 +1,5 @@
 trait I {}
-type K = I;
+type K = dyn I;
 impl K for isize {} //~ ERROR expected trait, found type alias `K`
 
 use ImportError; //~ ERROR unresolved import `ImportError` [E0432]
index d2550a99e814ce4c26517c81e218bfaac8fb82df..8f2d29d6f17c2e68c78af865f6ff387d8fc39b8c 100644 (file)
@@ -2,7 +2,7 @@
 
 #[rustc_outlives]
 struct Foo<'a, 'b, T> { //~ ERROR rustc_outlives
-    field1: Bar<'a, 'b, T>
+    field1: dyn Bar<'a, 'b, T>
 }
 
 trait Bar<'x, 's, U>
index 9ae05dab74d5e412706f11241aadb40f3118f958..b32c9743e9edbd8d203b8eeedf5f08118e1b18fe 100644 (file)
@@ -2,7 +2,7 @@ error: rustc_outlives
   --> $DIR/self-structs.rs:4:1
    |
 LL | / struct Foo<'a, 'b, T> {
-LL | |     field1: Bar<'a, 'b, T>
+LL | |     field1: dyn Bar<'a, 'b, T>
 LL | | }
    | |_^
    |
index b0d1fa1a74fb584229e236e73087493a353a3e4f..01daf307c00688e87e1ca6097ea37de957461b34 100644 (file)
@@ -9,7 +9,7 @@ trait Foo {
     type Assoc where Self: Sized;
     type Assoc2<T> where T: Display;
     type Assoc3<T>;
-    type WithDefault<T> where T: Debug = Iterator<Item=T>;
+    type WithDefault<T> where T: Debug = dyn Iterator<Item=T>;
     type NoGenerics;
 }
 
@@ -19,7 +19,7 @@ impl Foo for Bar {
     type Assoc = usize;
     type Assoc2<T> = Vec<T>;
     type Assoc3<T> where T: Iterator = Vec<T>;
-    type WithDefault<'a, T> = &'a Iterator<T>;
+    type WithDefault<'a, T> = &'a dyn Iterator<T>;
     type NoGenerics = ::std::cell::Cell<i32>;
 }
 
index 5920446dbc2e2d0cd9459578efb2d1e9b0d3fdea..ebb4d56af9eec37350ea48f70a763dbbdd750b30 100644 (file)
@@ -13,7 +13,7 @@ fn non_elidable<'a, 'b>(a: &'a u8, b: &'b u8) -> &'a u8 {
 struct SomeStruct<'x, 'y, 'z: 'x> {
     foo: &'x Foo<'z>,
     bar: &'x Bar<'z>,
-    f: &'y for<'a, 'b> Fn(&'a Foo<'b>) -> &'a Bar<'b>,
+    f: &'y dyn for<'a, 'b> Fn(&'a Foo<'b>) -> &'a Bar<'b>,
 }
 
 fn id<T>(t: T) -> T {
index 3158328b3ff15751d4b0da39e5533cb2bec0208f..a0871ca18094ed89d5377cb02fa01bbe670a5055 100644 (file)
@@ -4,7 +4,7 @@
 
 pub fn f() {
     trait Trait {}
-    impl Trait {
+    impl dyn Trait {
         const FLAG: u32 = bogus.field; //~ ERROR cannot find value `bogus`
     }
 }
index 2c1fd937a65adc9ea661ea7555789668f43fa245..7443d888c9ec89d045b4066dbd823aa347532ddf 100644 (file)
@@ -28,13 +28,13 @@ fn bar(self: Rc<Self>) -> usize {
 }
 
 fn make_foo() {
-    let x = Rc::new(5usize) as Rc<Foo>;
+    let x = Rc::new(5usize) as Rc<dyn Foo>;
     //~^ ERROR E0038
     //~| ERROR E0038
 }
 
 fn make_bar() {
-    let x = Rc::new(5usize) as Rc<Bar>;
+    let x = Rc::new(5usize) as Rc<dyn Bar>;
     x.bar();
 }
 
index dacab1222aba37dc7c48116e9bd61b21685014ed..e45bc2657f1ea03534d5e3b1490de3489ac239f6 100644 (file)
@@ -1,15 +1,15 @@
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/arbitrary-self-types-not-object-safe.rs:31:32
    |
-LL |     let x = Rc::new(5usize) as Rc<Foo>;
-   |                                ^^^^^^^ the trait `Foo` cannot be made into an object
+LL |     let x = Rc::new(5usize) as Rc<dyn Foo>;
+   |                                ^^^^^^^^^^^ the trait `Foo` cannot be made into an object
    |
    = note: method `foo`'s receiver cannot be dispatched on
 
 error[E0038]: the trait `Foo` cannot be made into an object
   --> $DIR/arbitrary-self-types-not-object-safe.rs:31:13
    |
-LL |     let x = Rc::new(5usize) as Rc<Foo>;
+LL |     let x = Rc::new(5usize) as Rc<dyn Foo>;
    |             ^^^^^^^^^^^^^^^ the trait `Foo` cannot be made into an object
    |
    = note: method `foo`'s receiver cannot be dispatched on
index acbe896eebe77a7876e83e6372d5108c939b32ae..0a9370e6f5ac79493dc6f9b4280cfd1af5deeb4b 100644 (file)
@@ -34,8 +34,8 @@ unsafe fn bar(self: *const Self) -> i64 {
 }
 
 fn main() {
-    let null_i32 = ptr::null::<i32>() as *const Foo;
-    let null_u32 = ptr::null::<u32>() as *const Foo;
+    let null_i32 = ptr::null::<i32>() as *const dyn Foo;
+    let null_u32 = ptr::null::<u32>() as *const dyn Foo;
 
     assert_eq!("I'm an i32!", null_i32.foo());
     assert_eq!("I'm a u32!", null_u32.foo());
@@ -45,7 +45,7 @@ fn main() {
     assert_eq!("I'm an i32!", valid_i32_thin.foo());
     assert_eq!(5, unsafe { valid_i32_thin.bar() });
     assert_eq!(5, unsafe { (&valid_i32_thin as *const *const i32).complicated() });
-    let valid_i32_fat = valid_i32_thin as *const Foo;
+    let valid_i32_fat = valid_i32_thin as *const dyn Foo;
     assert_eq!("I'm an i32!", valid_i32_fat.foo());
     assert_eq!(5, unsafe { valid_i32_fat.bar() });
 
@@ -54,7 +54,7 @@ fn main() {
     assert_eq!("I'm a u32!", valid_u32_thin.foo());
     assert_eq!(18, unsafe { valid_u32_thin.bar() });
     assert_eq!(18, unsafe { (&valid_u32_thin as *const *const u32).complicated() });
-    let valid_u32_fat = valid_u32_thin as *const Foo;
+    let valid_u32_fat = valid_u32_thin as *const dyn Foo;
     assert_eq!("I'm a u32!", valid_u32_fat.foo());
     assert_eq!(18, unsafe { valid_u32_fat.bar() });
 
index f95686cf11234212ce5c587541679b89d27e6ca3..0050bc7124d7183da5136ceb4b99d802b8e52700 100644 (file)
@@ -17,6 +17,6 @@ fn f(self: Box<S>) {
 
 pub fn main() {
     let x = box S { x: 3 };
-    let y = x as Box<Foo>;
+    let y = x as Box<dyn Foo>;
     y.f();
 }
index ae0512666ce0bcd24a0499aa44ac6734c12bb436..43b1d8b9149a1ebf18767515672fb890bb9afa20 100644 (file)
@@ -23,7 +23,7 @@ fn tick1<C:Counter>(mut c: C) -> u32 {
     c.get()
 }
 
-fn tick2(c: &mut Counter) {
+fn tick2(c: &mut dyn Counter) {
     tick3(c);
 }
 
index 0b3f66337378509beae083eee7338f6f87a16021..e0b0526a3338a4fd355e96d4e975cf418eadd572 100644 (file)
@@ -23,7 +23,7 @@ fn tick1<C:Counter>(c: &mut C) {
     c.with(|i| ());
 }
 
-fn tick2(c: &mut Counter) {
+fn tick2(c: &mut dyn Counter) {
     tick3(c);
 }
 
index e88dba0a4e8a3085938596ccfa0b12e4af8500f5..222c754394569d2541cd008d10b8c1d7c86e9095 100644 (file)
@@ -23,7 +23,7 @@ fn preticked<C:Counter>() -> C {
     c
 }
 
-fn tick(c: &mut Counter) {
+fn tick(c: &mut dyn Counter) {
     tick_generic(c);
 }
 
index db48bdf4c01b2df50334170842531e296b2abc11..6099263ccd0e95bfb7a28abc82f8b70751c58fb0 100644 (file)
@@ -2,10 +2,10 @@
 
 // Ensure that invoking a closure counts as a unique immutable borrow
 
-type Fn<'a> = Box<FnMut() + 'a>;
+type Fn<'a> = Box<dyn FnMut() + 'a>;
 
 struct Test<'a> {
-    f: Box<FnMut() + 'a>
+    f: Box<dyn FnMut() + 'a>
 }
 
 fn call<F>(mut f: F) where F: FnMut(Fn) {
@@ -47,9 +47,9 @@ fn test6() {
 }
 
 fn test7() {
-    fn foo<F>(_: F) where F: FnMut(Box<FnMut(isize)>, isize) {}
+    fn foo<F>(_: F) where F: FnMut(Box<dyn FnMut(isize)>, isize) {}
     let s = String::new();  // Capture to make f !Copy
-    let mut f = move |g: Box<FnMut(isize)>, b: isize| {
+    let mut f = move |g: Box<dyn FnMut(isize)>, b: isize| {
         let _ = s.len();
     };
     f(Box::new(|a| {
index 847f6865624bff6d3289449b3ecd43c1bba91aa9..72f979e8d3c348d35c894ff01928053a1d8cb3af 100644 (file)
@@ -29,7 +29,7 @@ LL |     f.f.call_mut(())
 error[E0507]: cannot move out of captured variable in an `FnMut` closure
   --> $DIR/borrowck-call-is-borrow-issue-12224.rs:57:13
    |
-LL |     let mut f = move |g: Box<FnMut(isize)>, b: isize| {
+LL |     let mut f = move |g: Box<dyn FnMut(isize)>, b: isize| {
    |         ----- captured outer variable
 ...
 LL |         foo(f);
index e672c46453582b95b7e62560e8a86e2665f8dde6..f5adc2cc1413e7e9e0b81e3287b758f600a15780 100644 (file)
@@ -3,22 +3,22 @@ trait Foo {
     fn borrowed_mut(&mut self);
 }
 
-fn borrowed_receiver(x: &Foo) {
+fn borrowed_receiver(x: &dyn Foo) {
     x.borrowed();
     x.borrowed_mut(); //~ ERROR cannot borrow
 }
 
-fn borrowed_mut_receiver(x: &mut Foo) {
+fn borrowed_mut_receiver(x: &mut dyn Foo) {
     x.borrowed();
     x.borrowed_mut();
 }
 
-fn owned_receiver(x: Box<Foo>) {
+fn owned_receiver(x: Box<dyn Foo>) {
     x.borrowed();
     x.borrowed_mut(); //~ ERROR cannot borrow
 }
 
-fn mut_owned_receiver(mut x: Box<Foo>) {
+fn mut_owned_receiver(mut x: Box<dyn Foo>) {
     x.borrowed();
     x.borrowed_mut();
 }
index fe6014cd5ad83ffe62c7a5baa3bfbcdf6bb5342c..fe6d05c588f7ffbeeee60c823eb1126a88d3d7c3 100644 (file)
@@ -1,8 +1,8 @@
 error[E0596]: cannot borrow `*x` as mutable, as it is behind a `&` reference
   --> $DIR/borrowck-object-mutability.rs:8:5
    |
-LL | fn borrowed_receiver(x: &Foo) {
-   |                         ---- help: consider changing this to be a mutable reference: `&mut dyn Foo`
+LL | fn borrowed_receiver(x: &dyn Foo) {
+   |                         -------- help: consider changing this to be a mutable reference: `&mut dyn Foo`
 LL |     x.borrowed();
 LL |     x.borrowed_mut();
    |     ^ `x` is a `&` reference, so the data it refers to cannot be borrowed as mutable
@@ -10,7 +10,7 @@ LL |     x.borrowed_mut();
 error[E0596]: cannot borrow `*x` as mutable, as `x` is not declared as mutable
   --> $DIR/borrowck-object-mutability.rs:18:5
    |
-LL | fn owned_receiver(x: Box<Foo>) {
+LL | fn owned_receiver(x: Box<dyn Foo>) {
    |                   - help: consider changing this to be mutable: `mut x`
 LL |     x.borrowed();
 LL |     x.borrowed_mut();
index 8dc70ea252b27a5f01f212b4a21147438f23bd72..a26123d5246f675a869b8b9e49ea4b5dedccc05a 100644 (file)
@@ -8,7 +8,7 @@ trait Trait<'a> {
     fn short<'b>(&'b self) -> isize;
 }
 
-fn object_invoke1<'d>(x: &'d Trait<'d>) -> (isize, isize) { loop { } }
+fn object_invoke1<'d>(x: &'d dyn Trait<'d>) -> (isize, isize) { loop { } }
 
 trait MakerTrait {
     fn mk() -> Self;
@@ -18,12 +18,12 @@ fn make_val<T:MakerTrait>() -> T {
     MakerTrait::mk()
 }
 
-impl<'t> MakerTrait for Box<Trait<'t>+'static> {
-    fn mk() -> Box<Trait<'t>+'static> { loop { } }
+impl<'t> MakerTrait for Box<dyn Trait<'t>+'static> {
+    fn mk() -> Box<dyn Trait<'t>+'static> { loop { } }
 }
 
 pub fn main() {
-    let m : Box<Trait+'static> = make_val();
+    let m : Box<dyn Trait+'static> = make_val();
     assert_eq!(object_invoke1(&*m), (4,5));
     //~^ ERROR `*m` does not live long enough
 
index ed690443d4ddb25fa7427be4047e5ccf9d21e88f..dbc3b190068ec6d89c792109cc8d572e5e48d7a9 100644 (file)
@@ -34,7 +34,7 @@ fn drop(&mut self) {
 
 struct Container<'a> {
     v: VecHolder,
-    d: RefCell<Vec<Box<Obj+'a>>>,
+    d: RefCell<Vec<Box<dyn Obj+'a>>>,
 }
 
 impl<'a> Container<'a> {
index c5a70c87ed8736dc2f41453ee60c3658ac352c05..cde68da1897367291be849ce25cfdd5ee095b869 100644 (file)
@@ -10,7 +10,7 @@ fn fire(&self, b: &mut B) {
 
 // Still unsound Zook
 trait Button { fn push(&self); }
-struct Zook<B> { button: B, trigger: Box<Trigger<B>+'static> }
+struct Zook<B> { button: B, trigger: Box<dyn Trigger<B>+'static> }
 
 impl<B> Drop for Zook<B> {
     fn drop(&mut self) {
index 13e651fa56b8f3d9078b684a02c389ac48487d55..e34f84683bbc7777b994f55dc7f737c7e87dfeb1 100644 (file)
@@ -11,6 +11,6 @@ fn main() {
     {
         let ss: &isize = &id(1);
         //~^ ERROR temporary value dropped while borrowed
-        blah = box ss as Box<Foo>;
+        blah = box ss as Box<dyn Foo>;
     }
 }
index 11187b74c42998a75e2ad6075a984ed0ba90e259..29083154b899130abb98560220adf58b22f1ab2e 100644 (file)
@@ -10,8 +10,8 @@ impl<A> Foo for A {
     fn get(&self) { }
 }
 
-fn repeater3<'a,A:'a>(v: A) -> Box<Foo+'a> {
-    box v as Box<Foo+'a>
+fn repeater3<'a,A:'a>(v: A) -> Box<dyn Foo + 'a> {
+    box v as Box<dyn Foo+'a>
 }
 
 fn main() {
index ac07420ee362ddc1e3550ac33945c40c1a830133..2aecc2a7e0d96a8b79eb6386d349fdfe37ff276c 100644 (file)
@@ -1,5 +1,5 @@
 struct Guard<'a> {
-    f: Box<Fn() + Send + 'a>,
+    f: Box<dyn Fn() + Send + 'a>,
 }
 
 fn scoped<'a, F: Fn() + Send + 'a>(f: F) -> Guard<'a> {
diff --git a/src/test/ui/suggestions/issue-52820.rs b/src/test/ui/suggestions/issue-52820.rs
new file mode 100644 (file)
index 0000000..075b07f
--- /dev/null
@@ -0,0 +1,12 @@
+struct Bravery {
+    guts: String,
+    brains: String,
+}
+
+fn main() {
+    let guts = "mettle";
+    let _ = Bravery {
+        guts, //~ ERROR mismatched types
+        brains: guts.clone(), //~ ERROR mismatched types
+    };
+}
diff --git a/src/test/ui/suggestions/issue-52820.stderr b/src/test/ui/suggestions/issue-52820.stderr
new file mode 100644 (file)
index 0000000..fb568ac
--- /dev/null
@@ -0,0 +1,27 @@
+error[E0308]: mismatched types
+  --> $DIR/issue-52820.rs:9:9
+   |
+LL |         guts,
+   |         ^^^^
+   |         |
+   |         expected struct `std::string::String`, found &str
+   |         help: try using a conversion method: `guts: guts.to_string()`
+   |
+   = note: expected type `std::string::String`
+              found type `&str`
+
+error[E0308]: mismatched types
+  --> $DIR/issue-52820.rs:10:17
+   |
+LL |         brains: guts.clone(),
+   |                 ^^^^^^^^^^^^
+   |                 |
+   |                 expected struct `std::string::String`, found &str
+   |                 help: try using a conversion method: `guts.to_string()`
+   |
+   = note: expected type `std::string::String`
+              found type `&str`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0308`.
index a3cc53e69e20e87d4d2aec03405d4bfa97c18280..78487bd7bb58c73b826322f476bd565f53894fc8 100644 (file)
@@ -4,7 +4,7 @@ pub trait T<X, Y> {
     type C;
 }
 pub struct Foo {
-    i: Box<T<usize, usize, usize, usize, B=usize>>,
+    i: Box<dyn T<usize, usize, usize, usize, B=usize>>,
     //~^ ERROR must be specified
     //~| ERROR wrong number of type arguments
 }
index 5e333187e3d3614bc5f14245b815a030693a54a3..d273ec3fca59ba83a4b7655dbce127a28e4b3638 100644 (file)
@@ -1,10 +1,10 @@
 error[E0107]: wrong number of type arguments: expected 2, found 4
-  --> $DIR/use-type-argument-instead-of-assoc-type.rs:7:28
+  --> $DIR/use-type-argument-instead-of-assoc-type.rs:7:32
    |
-LL |     i: Box<T<usize, usize, usize, usize, B=usize>>,
-   |                            ^^^^^  ^^^^^ unexpected type argument
-   |                            |
-   |                            unexpected type argument
+LL |     i: Box<dyn T<usize, usize, usize, usize, B=usize>>,
+   |                                ^^^^^  ^^^^^ unexpected type argument
+   |                                |
+   |                                unexpected type argument
 
 error[E0191]: the value of the associated types `A` (from the trait `T`), `C` (from the trait `T`) must be specified
   --> $DIR/use-type-argument-instead-of-assoc-type.rs:7:12
@@ -15,15 +15,15 @@ LL |     type B;
 LL |     type C;
    |     ------- `C` defined here
 ...
-LL |     i: Box<T<usize, usize, usize, usize, B=usize>>,
-   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     i: Box<dyn T<usize, usize, usize, usize, B=usize>>,
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |            |
    |            associated type `A` must be specified
    |            associated type `C` must be specified
 help: if you meant to specify the associated types, write
    |
-LL |     i: Box<T<usize, usize, A = usize, C = usize, B=usize>>,
-   |                            ^^^^^^^^^  ^^^^^^^^^
+LL |     i: Box<dyn T<usize, usize, A = usize, C = usize, B=usize>>,
+   |                                ^^^^^^^^^  ^^^^^^^^^
 
 error: aborting due to 2 previous errors
 
diff --git a/src/test/ui/symbol-names/issue-60925.rs b/src/test/ui/symbol-names/issue-60925.rs
new file mode 100644 (file)
index 0000000..e9f763a
--- /dev/null
@@ -0,0 +1,39 @@
+#![feature(rustc_attrs)]
+
+// This test is the same code as in ui/issue-53912.rs but this test checks that the symbol mangling
+// fix produces the correct result, whereas that test just checks that the reproduction compiles
+// successfully and doesn't segfault
+
+fn dummy() {}
+
+mod llvm {
+    pub(crate) struct Foo;
+}
+mod foo {
+    pub(crate) struct Foo<T>(T);
+
+    impl Foo<::llvm::Foo> {
+        #[rustc_symbol_name]
+//~^ ERROR _ZN11issue_609253foo36Foo$LT$issue_60925..llv$6d$..Foo$GT$3foo17h059a991a004536adE
+        pub(crate) fn foo() {
+            for _ in 0..0 {
+                for _ in &[::dummy()] {
+                    ::dummy();
+                    ::dummy();
+                    ::dummy();
+                }
+            }
+        }
+    }
+
+    pub(crate) fn foo() {
+        Foo::foo();
+        Foo::foo();
+    }
+}
+
+pub fn foo() {
+    foo::foo();
+}
+
+fn main() {}
diff --git a/src/test/ui/symbol-names/issue-60925.stderr b/src/test/ui/symbol-names/issue-60925.stderr
new file mode 100644 (file)
index 0000000..84a1874
--- /dev/null
@@ -0,0 +1,8 @@
+error: symbol-name(_ZN11issue_609253foo36Foo$LT$issue_60925..llv$6d$..Foo$GT$3foo17h059a991a004536adE)
+  --> $DIR/issue-60925.rs:16:9
+   |
+LL |         #[rustc_symbol_name]
+   |         ^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
index 428ce5102bad89415067d057c1a4da107e5b1c91..b97eb38c5af8d915f9f7d39723945adb0d015dbc 100644 (file)
@@ -17,7 +17,7 @@ trait Empty {}
 #[allow(dead_code)]
 struct Bar<T>(PhantomData<T>) where T: SendSyncAlias;
 
-impl EmptyAlias {}
+impl dyn EmptyAlias {}
 
 impl<T: SendSyncAlias> Empty for T {}
 
index afd8400e2305016693015d94d26a3390fe0dfa57..88feb89170dd333e8f031787fe72d72bdb089a8a 100644 (file)
@@ -114,13 +114,13 @@ trait Obj {}
 trait ObjL<'l> {}
 trait _9 = for<'a> ObjL<'a>;
 trait _10 = for<'b> ObjL<'b>;
-type _T50 = _9 + _10;
+type _T50 = dyn _9 + _10;
 //~^ ERROR only auto traits can be used as additional traits in a trait object [E0225]
 
 trait ObjT<T> {}
 trait _11 = ObjT<for<'a> fn(&'a u8)>;
 trait _12 = ObjT<for<'b> fn(&'b u8)>;
-type _T60 = _11 + _12;
+type _T60 = dyn _11 + _12;
 //~^ ERROR only auto traits can be used as additional traits in a trait object [E0225]
 
 fn main() {}
index eb667c9522ce118a824d35fc4b05f9d1076341f0..6df1df86508ee48f65de6c57062331458fdd089b 100644 (file)
@@ -430,28 +430,28 @@ LL | type _T44 = dyn _4 + Send + Sync + _8;
    |                 trait alias used in trait object type (first use)
 
 error[E0225]: only auto traits can be used as additional traits in a trait object
-  --> $DIR/trait-alias-no-duplicates.rs:117:18
+  --> $DIR/trait-alias-no-duplicates.rs:117:22
    |
 LL | trait _9 = for<'a> ObjL<'a>;
    |            ---------------- first non-auto trait
 LL | trait _10 = for<'b> ObjL<'b>;
    |             ---------------- additional non-auto trait
-LL | type _T50 = _9 + _10;
-   |             --   ^^^ trait alias used in trait object type (additional use)
-   |             |
-   |             trait alias used in trait object type (first use)
+LL | type _T50 = dyn _9 + _10;
+   |                 --   ^^^ trait alias used in trait object type (additional use)
+   |                 |
+   |                 trait alias used in trait object type (first use)
 
 error[E0225]: only auto traits can be used as additional traits in a trait object
-  --> $DIR/trait-alias-no-duplicates.rs:123:19
+  --> $DIR/trait-alias-no-duplicates.rs:123:23
    |
 LL | trait _11 = ObjT<for<'a> fn(&'a u8)>;
    |             ------------------------ first non-auto trait
 LL | trait _12 = ObjT<for<'b> fn(&'b u8)>;
    |             ------------------------ additional non-auto trait
-LL | type _T60 = _11 + _12;
-   |             ---   ^^^ trait alias used in trait object type (additional use)
-   |             |
-   |             trait alias used in trait object type (first use)
+LL | type _T60 = dyn _11 + _12;
+   |                 ---   ^^^ trait alias used in trait object type (additional use)
+   |                 |
+   |                 trait alias used in trait object type (first use)
 
 error: aborting due to 27 previous errors
 
index fd3af6f3a9aaaefef172ae6c8ae7aca4c510052e..33c9f2f00cfeeb4654c421c2f20430a8bbe16279 100644 (file)
@@ -6,6 +6,7 @@ fn dummy(&self) { }
 
 fn foo(_x: Foo + Send) {
     //~^ ERROR the size for values of type
+    //~| WARN trait objects without an explicit `dyn` are deprecated
 }
 
 fn main() { }
index 5aee1e7e982a8968b34531015f182c3e7e636176..250ea4b1c3201a89dcd67df9b482fcf7955e2f70 100644 (file)
@@ -1,3 +1,11 @@
+warning: trait objects without an explicit `dyn` are deprecated
+  --> $DIR/trait-bounds-not-on-bare-trait.rs:7:12
+   |
+LL | fn foo(_x: Foo + Send) {
+   |            ^^^^^^^^^^ help: use `dyn`: `dyn Foo + Send`
+   |
+   = note: #[warn(bare_trait_objects)] on by default
+
 error[E0277]: the size for values of type `(dyn Foo + std::marker::Send + 'static)` cannot be known at compilation time
   --> $DIR/trait-bounds-not-on-bare-trait.rs:7:8
    |
index 0892153c0cf86e426f499f0068741f21a7411d34..65b6f6faa425099a58edbdf14fe132e6246b92f7 100644 (file)
@@ -2,17 +2,17 @@
 
 trait Foo {}
 
-fn a(_x: Box<Foo+Send>) {
+fn a(_x: Box<dyn Foo + Send>) {
 }
 
-fn b(_x: &'static (Foo+'static)) {
+fn b(_x: &'static (dyn Foo + 'static)) {
 }
 
-fn c(x: Box<Foo+Sync>) {
+fn c(x: Box<dyn Foo + Sync>) {
     a(x); //~ ERROR mismatched types
 }
 
-fn d(x: &'static (Foo+Sync)) {
+fn d(x: &'static (dyn Foo + Sync)) {
     b(x);
 }
 
index 5aa21834148205c638d1aa8c96ad43bbe9f9b049..2e115c732b9d76d282e30dc0357532f7a39ec609 100644 (file)
@@ -13,7 +13,7 @@ fn f(&self, x: &'static str) {
 }
 
 fn main() {
-    let s: Box<Trait<isize>> = Box::new(Struct { person: "Fred" });
+    let s: Box<dyn Trait<isize>> = Box::new(Struct { person: "Fred" });
     //~^ ERROR `Struct: Trait<isize>` is not satisfied
     s.f(1);
 }
index 7f3b46b8ae52d87e24a56ab4856555faccfeba6c..f2710dea0952f55127283f4dea524e30c106dad0 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the trait bound `Struct: Trait<isize>` is not satisfied
-  --> $DIR/trait-coercion-generic-bad.rs:16:32
+  --> $DIR/trait-coercion-generic-bad.rs:16:36
    |
-LL |     let s: Box<Trait<isize>> = Box::new(Struct { person: "Fred" });
-   |                                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Trait<isize>` is not implemented for `Struct`
+LL |     let s: Box<dyn Trait<isize>> = Box::new(Struct { person: "Fred" });
+   |                                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Trait<isize>` is not implemented for `Struct`
    |
    = help: the following implementations were found:
              <Struct as Trait<&'static str>>
index 148b7dd5c43dac5f10f5b14e12276833fe2e85bc..af478df6dfa995f671dc2c003d30366f662fa86a 100644 (file)
@@ -15,5 +15,5 @@ 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::new(Struct { person: person });
+    let s: Box<dyn Trait<&'static str>> = Box::new(Struct { person: person });
 }
index 4ee3e4cacc372d444f4fd8b1e1c86c65b7578c7b..d21b48e571df9d6cebdb6362a8cb7a33cdf887ea 100644 (file)
@@ -6,7 +6,7 @@ LL |     let person: &str = &person;
    |                        |
    |                        borrowed value does not live long enough
    |                        assignment requires that `person` is borrowed for `'static`
-LL |     let s: Box<Trait<&'static str>> = Box::new(Struct { person: person });
+LL |     let s: Box<dyn Trait<&'static str>> = Box::new(Struct { person: person });
 LL | }
    | - `person` dropped here while still borrowed
 
index 29f58a6a9cbc195e00b500a01caa1250a52e7673..43b822218354fafa4def2fff1cf7d350c18ecb1a 100644 (file)
@@ -4,7 +4,7 @@
 
 trait T {}
 
-impl<'a> T+'a {
+impl<'a> dyn T + 'a {
     fn foo(&self) {}
 }
 
index dfc8c8f4f6cc19efd5bc5a45699a85eebcd1f6de..d58bbef38c492ba238c8b94c751ca919d5a1a44c 100644 (file)
@@ -68,7 +68,7 @@ fn check_method() {
     S.b(); //~ ERROR no method named `b` found for type `S` in the current scope
     S.c(); // OK
     // a, b, c are resolved as inherent items, their traits don't need to be in scope
-    let c = &S as &C;
+    let c = &S as &dyn C;
     c.a(); //~ ERROR method `a` is private
     c.b(); // OK
     c.c(); // OK
@@ -121,10 +121,10 @@ fn check_assoc_ty<T: assoc_ty::C>() {
     let _: T::C; // OK
 
     // Associated types, bindings
-    let _: assoc_ty::B<
+    let _: dyn assoc_ty::B<
         B = u8, // OK
     >;
-    let _: C<
+    let _: dyn C<
         A = u8, //~ ERROR associated type `A` is private
         B = u8, // OK
         C = u8, // OK
index 6ba5d28a6c4c2b6795559c36769c73bba577c510..85698f1948904120d05a1125982307b2ebd7e428 100644 (file)
@@ -5,15 +5,15 @@
 impl Trait for Struct {}
 trait Trait {}
 
-type Send1 = Trait + Send;
-type Send2 = Trait + Send + Send;
+type Send1 = dyn Trait + Send;
+type Send2 = dyn Trait + Send + Send;
 
 fn main () {}
 
-impl Trait + Send {
+impl dyn Trait + Send {
     fn test(&self) { println!("one"); } //~ ERROR duplicate definitions with name `test`
 }
 
-impl Trait + Send + Send {
+impl dyn Trait + Send + Send {
     fn test(&self) { println!("two"); }
 }
index 0f55e2dc4f21eaf1883d88e3425d20357eeecc4c..5ec157275a6291a7101349a603f8f65bc07251c6 100644 (file)
@@ -5,7 +5,8 @@ macro_rules! m {
 }
 
 fn main() {
-    m!(Copy + Send + 'static); //~ ERROR the trait `std::marker::Copy` cannot be made into an object
-    m!('static + Send);
-    m!('static +); //~ ERROR at least one non-builtin trait is required for an object type
+    m!(dyn Copy + Send + 'static);
+    //~^ ERROR the trait `std::marker::Copy` cannot be made into an object
+    m!(dyn 'static + Send);
+    m!(dyn 'static +); //~ ERROR at least one non-builtin trait is required for an object type
 }
index 57a529ebc5765e7f457f020fbcdb89770cfe847f..0b84c3dfcb0577fd8ca61dac34c76fbef14a80ff 100644 (file)
@@ -1,14 +1,14 @@
 error[E0224]: at least one non-builtin trait is required for an object type
-  --> $DIR/trait-object-macro-matcher.rs:10:8
+  --> $DIR/trait-object-macro-matcher.rs:11:8
    |
-LL |     m!('static +);
-   |        ^^^^^^^^^
+LL |     m!(dyn 'static +);
+   |        ^^^^^^^^^^^^^
 
 error[E0038]: the trait `std::marker::Copy` cannot be made into an object
   --> $DIR/trait-object-macro-matcher.rs:8:8
    |
-LL |     m!(Copy + Send + 'static);
-   |        ^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` cannot be made into an object
+LL |     m!(dyn Copy + Send + 'static);
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` cannot be made into an object
    |
    = note: the trait cannot require that `Self : Sized`
 
index e333bf6bfe53baa8aa2c89e8f5be71335515d9f3..f43d332d6963707ec570af8cc57f804b663dbf0f 100644 (file)
@@ -12,6 +12,6 @@ fn foo() {}
 }
 
 fn main() {
-    let _: &Tr = &St; //~ ERROR E0038
+    let _: &dyn Tr = &St; //~ ERROR E0038
     //~^ ERROR E0038
 }
index a7fe83cb7564ae199a46eba74027f9b2438384ef..68edc1787053432cc1e3974c9064c8b676a5068d 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `Tr` cannot be made into an object
-  --> $DIR/trait-object-safety.rs:15:18
+  --> $DIR/trait-object-safety.rs:15:22
    |
-LL |     let _: &Tr = &St;
-   |                  ^^^ the trait `Tr` cannot be made into an object
+LL |     let _: &dyn Tr = &St;
+   |                      ^^^ the trait `Tr` cannot be made into an object
    |
    = note: method `foo` has no receiver
    = note: required because of the requirements on the impl of `std::ops::CoerceUnsized<&dyn Tr>` for `&St`
@@ -10,8 +10,8 @@ LL |     let _: &Tr = &St;
 error[E0038]: the trait `Tr` cannot be made into an object
   --> $DIR/trait-object-safety.rs:15:12
    |
-LL |     let _: &Tr = &St;
-   |            ^^^ the trait `Tr` cannot be made into an object
+LL |     let _: &dyn Tr = &St;
+   |            ^^^^^^^ the trait `Tr` cannot be made into an object
    |
    = note: method `foo` has no receiver
 
index 2579a0056f142f67c4ff85c24e24a1ce80ab91df..4d56fcf11e39e1fea08bb8ab4608772c53ac82f7 100644 (file)
@@ -6,7 +6,7 @@
 // `'static` is a lifetime, `'static +` is a type, `'a` is a type
 fn g() where
     'static: 'static,
-    'static +: 'static + Copy,
+    dyn 'static +: 'static + Copy,
     //~^ ERROR at least one non-builtin trait is required for an object type
 {}
 
index 057f587a7b6307fd8e630af59282efc64964fd73..24162c920be33701968d014c1a4ed732a44c0304 100644 (file)
@@ -1,8 +1,8 @@
 error[E0224]: at least one non-builtin trait is required for an object type
   --> $DIR/trait-object-vs-lifetime-2.rs:9:5
    |
-LL |     'static +: 'static + Copy,
-   |     ^^^^^^^^^
+LL |     dyn 'static +: 'static + Copy,
+   |     ^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index 36dec21be0520987d390d1ba59bc0db4982a07a3..803b29367c8a81e3de5d15ed29877c538a9b3238 100644 (file)
@@ -6,12 +6,12 @@
 fn main() {
     // `'static` is a lifetime argument, `'static +` is a type argument
     let _: S<'static, u8>;
-    let _: S<'static, 'static +>;
+    let _: S<'static, dyn 'static +>;
     //~^ at least one non-builtin trait is required for an object type
     let _: S<'static, 'static>;
     //~^ ERROR wrong number of lifetime arguments: expected 1, found 2
     //~| ERROR wrong number of type arguments: expected 1, found 0
-    let _: S<'static +, 'static>;
+    let _: S<dyn 'static +, 'static>;
     //~^ ERROR lifetime arguments must be declared prior to type arguments
     //~| ERROR at least one non-builtin trait is required for an object type
 }
index c13d0e3f29373f97567d7a26144cce1c2054ba0c..be1af59ed4f5c3e69af43af6b7dd60cbacbf6227 100644 (file)
@@ -1,14 +1,14 @@
 error: lifetime arguments must be declared prior to type arguments
-  --> $DIR/trait-object-vs-lifetime.rs:14:25
+  --> $DIR/trait-object-vs-lifetime.rs:14:29
    |
-LL |     let _: S<'static +, 'static>;
-   |                         ^^^^^^^
+LL |     let _: S<dyn 'static +, 'static>;
+   |                             ^^^^^^^
 
 error[E0224]: at least one non-builtin trait is required for an object type
   --> $DIR/trait-object-vs-lifetime.rs:9:23
    |
-LL |     let _: S<'static, 'static +>;
-   |                       ^^^^^^^^^
+LL |     let _: S<'static, dyn 'static +>;
+   |                       ^^^^^^^^^^^^^
 
 error[E0107]: wrong number of lifetime arguments: expected 1, found 2
   --> $DIR/trait-object-vs-lifetime.rs:11:23
@@ -25,8 +25,8 @@ LL |     let _: S<'static, 'static>;
 error[E0224]: at least one non-builtin trait is required for an object type
   --> $DIR/trait-object-vs-lifetime.rs:14:14
    |
-LL |     let _: S<'static +, 'static>;
-   |              ^^^^^^^^^
+LL |     let _: S<dyn 'static +, 'static>;
+   |              ^^^^^^^^^^^^^
 
 error: aborting due to 5 previous errors
 
index 20d979df4bf436ef4b6af9fe93560ecb9446bc27..86570f1152e1e11197e5174479599e19aefbf010 100644 (file)
@@ -8,7 +8,7 @@ impl bar for u32 { fn dup(&self) -> u32 { *self } fn blah<X>(&self) {} }
 fn main() {
     10.dup::<i32>(); //~ ERROR wrong number of type arguments: expected 0, found 1
     10.blah::<i32, i32>(); //~ ERROR wrong number of type arguments: expected 1, found 2
-    (box 10 as Box<bar>).dup();
+    (box 10 as Box<dyn bar>).dup();
     //~^ ERROR E0038
     //~| ERROR E0038
 }
index 0e3446e0d231d85f73c9448021105ea4c882aba5..5d5251925a1ae5bdf56c4d26ad0266879a288076 100644 (file)
@@ -13,8 +13,8 @@ LL |     10.blah::<i32, i32>();
 error[E0038]: the trait `bar` cannot be made into an object
   --> $DIR/trait-test-2.rs:11:16
    |
-LL |     (box 10 as Box<bar>).dup();
-   |                ^^^^^^^^ the trait `bar` cannot be made into an object
+LL |     (box 10 as Box<dyn bar>).dup();
+   |                ^^^^^^^^^^^^ the trait `bar` cannot be made into an object
    |
    = note: method `dup` references the `Self` type in its arguments or return type
    = note: method `blah` has generic type parameters
@@ -22,7 +22,7 @@ LL |     (box 10 as Box<bar>).dup();
 error[E0038]: the trait `bar` cannot be made into an object
   --> $DIR/trait-test-2.rs:11:6
    |
-LL |     (box 10 as Box<bar>).dup();
+LL |     (box 10 as Box<dyn bar>).dup();
    |      ^^^^^^ the trait `bar` cannot be made into an object
    |
    = note: method `dup` references the `Self` type in its arguments or return type
index 5fa7e87aa4b97e89f9a794b88194330b9aa9aa5b..6aaef8a305bce1cd916e745f613015eb643c12a1 100644 (file)
@@ -22,7 +22,7 @@ fn same_as(&self, t: u64) -> bool { *self == (t as i64) }
 
 impl CompareToInts for i64 { }
 
-fn with_obj(c: &CompareToInts) -> bool {
+fn with_obj(c: &dyn CompareToInts) -> bool {
     c.same_as(22) //~ ERROR `dyn CompareToInts: CompareTo<i32>` is not satisfied
 }
 
index a5d5b937726515a8df6bed87d7614c9878bff73d..d411807673c667d1fbb9f386ce751687396fbb00 100644 (file)
@@ -13,8 +13,8 @@ struct T<X: ?Sized> {
 
 struct S(str, str) where str: Sized;
 
-fn unsized_local() where for<'a> T<A + 'a>: Sized {
-    let x: T<A> = *(Box::new(T { x: 1 }) as Box<T<A>>);
+fn unsized_local() where for<'a> T<dyn A + 'a>: Sized {
+    let x: T<dyn A> = *(Box::new(T { x: 1 }) as Box<T<dyn A>>);
 }
 
 fn return_str() -> str where str: Sized {
index a9d2634c1ad71f8d49e615230a56f82664085096..fda1d6d70ac586284fcbce0483cacf05492b770e 100644 (file)
@@ -7,10 +7,10 @@ LL | struct S(str, str) where str: Sized;
    = note: #[warn(trivial_bounds)] on by default
 
 warning: Trait bound for<'a> T<(dyn A + 'a)>: std::marker::Sized does not depend on any type or lifetime parameters
-  --> $DIR/trivial-bounds-inconsistent-sized.rs:16:45
+  --> $DIR/trivial-bounds-inconsistent-sized.rs:16:49
    |
-LL | fn unsized_local() where for<'a> T<A + 'a>: Sized {
-   |                                             ^^^^^
+LL | fn unsized_local() where for<'a> T<dyn A + 'a>: Sized {
+   |                                                 ^^^^^
 
 warning: Trait bound str: std::marker::Sized does not depend on any type or lifetime parameters
   --> $DIR/trivial-bounds-inconsistent-sized.rs:20:35
index fdbaec9a5c7ffd90c249cbd9f1faad58974096fc..f6538b14d171198a87f8ae282ff51000df7c6429 100644 (file)
@@ -52,8 +52,8 @@ struct Dst<X: ?Sized> {
 
 struct TwoStrs(str, str) where str: Sized;
 
-fn unsized_local() where for<'a> Dst<A + 'a>: Sized {
-    let x: Dst<A> = *(Box::new(Dst { x: 1 }) as Box<Dst<A>>);
+fn unsized_local() where for<'a> Dst<dyn A + 'a>: Sized {
+    let x: Dst<dyn A> = *(Box::new(Dst { x: 1 }) as Box<Dst<dyn A>>);
 }
 
 fn return_str() -> str where str: Sized {
index 744e146f830031785cf5115bb95a99122decc444..a0d638f17147e330d422d05b52d1ed81688609b8 100644 (file)
@@ -64,10 +64,10 @@ LL | struct TwoStrs(str, str) where str: Sized;
    |                                     ^^^^^
 
 warning: Trait bound for<'a> Dst<(dyn A + 'a)>: std::marker::Sized does not depend on any type or lifetime parameters
-  --> $DIR/trivial-bounds-inconsistent.rs:55:47
+  --> $DIR/trivial-bounds-inconsistent.rs:55:51
    |
-LL | fn unsized_local() where for<'a> Dst<A + 'a>: Sized {
-   |                                               ^^^^^
+LL | fn unsized_local() where for<'a> Dst<dyn A + 'a>: Sized {
+   |                                                   ^^^^^
 
 warning: Trait bound str: std::marker::Sized does not depend on any type or lifetime parameters
   --> $DIR/trivial-bounds-inconsistent.rs:59:35
index c1f5441a36b083df5f6396114629904a47288675..dd578e074fdac9c6945366f716367449ec948328 100644 (file)
@@ -49,29 +49,29 @@ pub fn main() {
 
     // unsize trait
     let x: &Bar = &Bar;
-    let _ = x as &Foo; //~ERROR trivial cast: `&Bar` as `&dyn Foo`
-    let _ = x as *const Foo; //~ERROR trivial cast: `&Bar` as `*const dyn Foo`
-    let _: &Foo = x;
-    let _: *const Foo = x;
+    let _ = x as &dyn Foo; //~ERROR trivial cast: `&Bar` as `&dyn Foo`
+    let _ = x as *const dyn Foo; //~ERROR trivial cast: `&Bar` as `*const dyn Foo`
+    let _: &dyn Foo = x;
+    let _: *const dyn Foo = x;
 
     let x: &mut Bar = &mut Bar;
-    let _ = x as &mut Foo; //~ERROR trivial cast: `&mut Bar` as `&mut dyn Foo`
-    let _ = x as *mut Foo; //~ERROR trivial cast: `&mut Bar` as `*mut dyn Foo`
-    let _: &mut Foo = x;
-    let _: *mut Foo = x;
+    let _ = x as &mut dyn Foo; //~ERROR trivial cast: `&mut Bar` as `&mut dyn Foo`
+    let _ = x as *mut dyn Foo; //~ERROR trivial cast: `&mut Bar` as `*mut dyn Foo`
+    let _: &mut dyn Foo = x;
+    let _: *mut dyn Foo = x;
 
     let x: Box<Bar> = Box::new(Bar);
-    let _ = x as Box<Foo>; //~ERROR `std::boxed::Box<Bar>` as `std::boxed::Box<dyn Foo>`
+    let _ = x as Box<dyn Foo>; //~ERROR `std::boxed::Box<Bar>` as `std::boxed::Box<dyn Foo>`
     let x: Box<Bar> = Box::new(Bar);
-    let _: Box<Foo> = x;
+    let _: Box<dyn Foo> = x;
 
     // functions
     fn baz(_x: i32) {}
-    let _ = &baz as &Fn(i32); //~ERROR `&fn(i32) {main::baz}` as `&dyn std::ops::Fn(i32)`
-    let _: &Fn(i32) = &baz;
+    let _ = &baz as &dyn Fn(i32); //~ERROR `&fn(i32) {main::baz}` as `&dyn std::ops::Fn(i32)`
+    let _: &dyn Fn(i32) = &baz;
     let x = |_x: i32| {};
-    let _ = &x as &Fn(i32); //~ERROR trivial cast
-    let _: &Fn(i32) = &x;
+    let _ = &x as &dyn Fn(i32); //~ERROR trivial cast
+    let _: &dyn Fn(i32) = &x;
 }
 
 // subtyping
index 524eb7feaafbdfd37e6df9fa12bf036ab8d51146..8fa44372f0b4f8e858532db82f394d401edf9dc8 100644 (file)
@@ -83,56 +83,56 @@ LL |     let _ = x as Box<[u32]>;
 error: trivial cast: `&Bar` as `&dyn Foo`
   --> $DIR/trivial_casts.rs:52:13
    |
-LL |     let _ = x as &Foo;
-   |             ^^^^^^^^^
+LL |     let _ = x as &dyn Foo;
+   |             ^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `&Bar` as `*const dyn Foo`
   --> $DIR/trivial_casts.rs:53:13
    |
-LL |     let _ = x as *const Foo;
-   |             ^^^^^^^^^^^^^^^
+LL |     let _ = x as *const dyn Foo;
+   |             ^^^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `&mut Bar` as `&mut dyn Foo`
   --> $DIR/trivial_casts.rs:58:13
    |
-LL |     let _ = x as &mut Foo;
-   |             ^^^^^^^^^^^^^
+LL |     let _ = x as &mut dyn Foo;
+   |             ^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `&mut Bar` as `*mut dyn Foo`
   --> $DIR/trivial_casts.rs:59:13
    |
-LL |     let _ = x as *mut Foo;
-   |             ^^^^^^^^^^^^^
+LL |     let _ = x as *mut dyn Foo;
+   |             ^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `std::boxed::Box<Bar>` as `std::boxed::Box<dyn Foo>`
   --> $DIR/trivial_casts.rs:64:13
    |
-LL |     let _ = x as Box<Foo>;
-   |             ^^^^^^^^^^^^^
+LL |     let _ = x as Box<dyn Foo>;
+   |             ^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `&fn(i32) {main::baz}` as `&dyn std::ops::Fn(i32)`
   --> $DIR/trivial_casts.rs:70:13
    |
-LL |     let _ = &baz as &Fn(i32);
-   |             ^^^^^^^^^^^^^^^^
+LL |     let _ = &baz as &dyn Fn(i32);
+   |             ^^^^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
 error: trivial cast: `&[closure@$DIR/trivial_casts.rs:72:13: 72:25]` as `&dyn std::ops::Fn(i32)`
   --> $DIR/trivial_casts.rs:73:13
    |
-LL |     let _ = &x as &Fn(i32);
-   |             ^^^^^^^^^^^^^^
+LL |     let _ = &x as &dyn Fn(i32);
+   |             ^^^^^^^^^^^^^^^^^^
    |
    = help: cast can be replaced by coercion; this might require a temporary variable
 
index 1c8b881d2469e0ba18c1bb9f29a6607586c5286c..4f505c05a6a2ce9021d7c263138a573318988007 100644 (file)
@@ -13,5 +13,5 @@ fn main() {
     //~^ ERROR mismatched types
     //~| expected type `(isize, f64)`
     //~| found type `(isize,)`
-    //~| expected a tuple with 2 elements, found one with 1 elements
+    //~| expected a tuple with 2 elements, found one with 1 element
 }
index 650f4c58c776c6bb2c1a2afc6fa52d7dd31f4799..6946a60c59af9b1e6a0bef1a55cf9d86369b7514 100644 (file)
@@ -11,7 +11,7 @@ error[E0308]: mismatched types
   --> $DIR/tuple-arity-mismatch.rs:12:20
    |
 LL |     let y = first ((1,));
-   |                    ^^^^ expected a tuple with 2 elements, found one with 1 elements
+   |                    ^^^^ expected a tuple with 2 elements, found one with 1 element
    |
    = note: expected type `(isize, f64)`
               found type `(isize,)`
index d5b815f6a95e9ab99aef0c315eb654430fb357c9..02aad00770793ec8fc0176844e31b7f40ab7bbd0 100644 (file)
@@ -1,5 +1,5 @@
 // error-pattern:can't use generic parameters from outer function
 fn foo<T>(x: T) {
-    fn bar(f: Box<FnMut(T) -> T>) { }
+    fn bar(f: Box<dyn FnMut(T) -> T>) { }
 }
 fn main() { foo(1); }
index ea991069c08ddc1925103d692090a3f3ad107ebd..0b6283fbc51e9bf4ae5dbd4d86f2b1d22175dd89 100644 (file)
@@ -1,20 +1,20 @@
 error[E0401]: can't use generic parameters from outer function
-  --> $DIR/type-arg-out-of-scope.rs:3:25
+  --> $DIR/type-arg-out-of-scope.rs:3:29
    |
 LL | fn foo<T>(x: T) {
    |        - type parameter from outer function
-LL |     fn bar(f: Box<FnMut(T) -> T>) { }
-   |        ---              ^ use of generic parameter from outer function
+LL |     fn bar(f: Box<dyn FnMut(T) -> T>) { }
+   |        ---                  ^ use of generic parameter from outer function
    |        |
    |        help: try using a local generic parameter instead: `bar<T>`
 
 error[E0401]: can't use generic parameters from outer function
-  --> $DIR/type-arg-out-of-scope.rs:3:31
+  --> $DIR/type-arg-out-of-scope.rs:3:35
    |
 LL | fn foo<T>(x: T) {
    |        - type parameter from outer function
-LL |     fn bar(f: Box<FnMut(T) -> T>) { }
-   |        ---                    ^ use of generic parameter from outer function
+LL |     fn bar(f: Box<dyn FnMut(T) -> T>) { }
+   |        ---                        ^ use of generic parameter from outer function
    |        |
    |        help: try using a local generic parameter instead: `bar<T>`
 
index 51bd116fbd61c071caed3376d2ffbe5f8aa668fa..5ad50ffcbc389cabdef2eba58d1d284275495aed 100644 (file)
@@ -3,4 +3,5 @@ fn main() {
     const l: usize = v.count(); //~ ERROR attempt to use a non-constant value in a constant
     let s: [u32; l] = v.into_iter().collect();
     //~^ ERROR evaluation of constant value failed
+    //~^^ ERROR a collection of type
 }
index 25cae8d9e4954dfc0f678d8fb85b6dc44c4cd119..851004d10589712426b56cbdf720aba562b201fb 100644 (file)
@@ -10,7 +10,15 @@ error[E0080]: evaluation of constant value failed
 LL |     let s: [u32; l] = v.into_iter().collect();
    |                  ^ referenced constant has errors
 
-error: aborting due to 2 previous errors
+error[E0277]: a collection of type `[u32; _]` cannot be built from an iterator over elements of type `{integer}`
+  --> $DIR/type-dependent-def-issue-49241.rs:4:37
+   |
+LL |     let s: [u32; l] = v.into_iter().collect();
+   |                                     ^^^^^^^ a collection of type `[u32; _]` cannot be built from `std::iter::Iterator<Item={integer}>`
+   |
+   = help: the trait `std::iter::FromIterator<{integer}>` is not implemented for `[u32; _]`
+
+error: aborting due to 3 previous errors
 
-Some errors have detailed explanations: E0080, E0435.
+Some errors have detailed explanations: E0080, E0277, E0435.
 For more information about an error, try `rustc --explain E0080`.
index 3e1c876c76ba8762cdceb8aa31ed214771450b37..444453dc69437c05726106fd4cbb1710858e0dfa 100644 (file)
@@ -11,7 +11,7 @@ fn add(&self, other: &i32) -> i32 { *self + *other }
 
 fn main() {
     let x: i32 = 5;
-    let y = x as MyAdd<i32>;
+    let y = x as dyn MyAdd<i32>;
     //~^ ERROR E0038
     //~| ERROR cast to unsized type: `i32` as `dyn MyAdd<i32>`
 }
index 0beb9e9eb4b03a9065230fe1efdf66e56a3b3f6a..58727ea0fef99646207d4b67678f1f98ed3c5cd5 100644 (file)
@@ -1,20 +1,20 @@
 error[E0620]: cast to unsized type: `i32` as `dyn MyAdd<i32>`
   --> $DIR/type-parameter-defaults-referencing-Self-ppaux.rs:14:13
    |
-LL |     let y = x as MyAdd<i32>;
-   |             ^^^^^^^^^^^^^^^
+LL |     let y = x as dyn MyAdd<i32>;
+   |             ^^^^^^^^^^^^^^^^^^^
    |
 help: consider using a box or reference as appropriate
   --> $DIR/type-parameter-defaults-referencing-Self-ppaux.rs:14:13
    |
-LL |     let y = x as MyAdd<i32>;
+LL |     let y = x as dyn MyAdd<i32>;
    |             ^
 
 error[E0038]: the trait `MyAdd` cannot be made into an object
   --> $DIR/type-parameter-defaults-referencing-Self-ppaux.rs:14:18
    |
-LL |     let y = x as MyAdd<i32>;
-   |                  ^^^^^^^^^^ the trait `MyAdd` cannot be made into an object
+LL |     let y = x as dyn MyAdd<i32>;
+   |                  ^^^^^^^^^^^^^^ the trait `MyAdd` cannot be made into an object
    |
    = note: method `add` references the `Self` type in its arguments or return type
 
index 721bf960a55c29eb72b6a864a10a598336c1e0f9..a4c59dced029a89db7514e82d9e3f0242230fd86 100644 (file)
@@ -7,7 +7,7 @@ trait Foo<T=Self> {
     fn method(&self);
 }
 
-fn foo(x: &Foo) { }
+fn foo(x: &dyn Foo) { }
 //~^ ERROR the type parameter `T` must be explicitly specified
 
 fn main() { }
index 70093b61f251b6b78d7fb5c37ceacc94dd76621d..0d6ca9d9dcd9ff035f4c5b93ab58d822e1a916e1 100644 (file)
@@ -1,8 +1,8 @@
 error[E0393]: the type parameter `T` must be explicitly specified
-  --> $DIR/type-parameter-defaults-referencing-Self.rs:10:12
+  --> $DIR/type-parameter-defaults-referencing-Self.rs:10:16
    |
-LL | fn foo(x: &Foo) { }
-   |            ^^^ missing reference to `T`
+LL | fn foo(x: &dyn Foo) { }
+   |                ^^^ missing reference to `T`
    |
    = note: because of the default `Self` reference, type parameters must be specified on object types
 
index 9d07c86356b67ed80ad99176621926cfe57fd0f5..7e308f107ba00049bbc71b69f57afec35b51bc60 100644 (file)
@@ -1,5 +1,5 @@
 error: reached the type-length limit while instantiating `std::mem::drop::<std::option::Op... G), (G, G, G), (G, G, G))))))>>`
-  --> $SRC_DIR/libcore/mem.rs:LL:COL
+  --> $SRC_DIR/libcore/mem/mod.rs:LL:COL
    |
 LL | pub fn drop<T>(_x: T) { }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^
index 7760866436210877beef8e84bbc36b500a754522..f466c19e051eda0e4e32af7c588e4c0068d6269f 100644 (file)
@@ -1,7 +1,7 @@
 fn foo1<T:Copy<U>, U>(x: T) {}
 //~^ ERROR wrong number of type arguments: expected 0, found 1 [E0107]
 
-trait Trait: Copy<Send> {}
+trait Trait: Copy<dyn Send> {}
 //~^ ERROR wrong number of type arguments: expected 0, found 1 [E0107]
 
 struct MyStruct1<T: Copy<T>>;
index 0242287a3e5ef906b1516b2b0636fe8036e1e62f..0be1c8ef3bc16ca371adcfcc3c13e7071c569f1d 100644 (file)
@@ -7,8 +7,8 @@ LL | fn foo1<T:Copy<U>, U>(x: T) {}
 error[E0107]: wrong number of type arguments: expected 0, found 1
   --> $DIR/typeck-builtin-bound-type-parameters.rs:4:19
    |
-LL | trait Trait: Copy<Send> {}
-   |                   ^^^^ unexpected type argument
+LL | trait Trait: Copy<dyn Send> {}
+   |                   ^^^^^^^^ unexpected type argument
 
 error[E0107]: wrong number of type arguments: expected 0, found 1
   --> $DIR/typeck-builtin-bound-type-parameters.rs:7:26
index 1eb9de778e82dc275c7ed973c0d920cff3409725..d8b201bf82d3be8cbd91211d93a165c32bf9a4bd 100644 (file)
@@ -10,11 +10,11 @@ fn dummy(&self, a: A) { }
 }
 
 fn main() {
-    let x: Box<Foo(isize)>;
+    let x: Box<dyn Foo(isize)>;
     //~^ ERROR parenthetical notation is only stable when used with `Fn`-family
 
     // No errors with these:
-    let x: Box<Fn(isize)>;
-    let x: Box<FnMut(isize)>;
-    let x: Box<FnOnce(isize)>;
+    let x: Box<dyn Fn(isize)>;
+    let x: Box<dyn FnMut(isize)>;
+    let x: Box<dyn FnOnce(isize)>;
 }
index 1604aa4a0f7006973fa5695d2ddb590e915978bb..c23acbcb311d6d487480e64e58cd0e250b2bf973 100644 (file)
@@ -1,8 +1,8 @@
 error[E0658]: parenthetical notation is only stable when used with `Fn`-family traits
-  --> $DIR/unboxed-closure-feature-gate.rs:13:16
+  --> $DIR/unboxed-closure-feature-gate.rs:13:20
    |
-LL |     let x: Box<Foo(isize)>;
-   |                ^^^^^^^^^^
+LL |     let x: Box<dyn Foo(isize)>;
+   |                    ^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29625
    = help: add #![feature(unboxed_closures)] to the crate attributes to enable
index 044859de6a4a58283d0cb01351ba77916c4722de..f1c83f0606fad2d3984b27aac04128d2f448912f 100644 (file)
@@ -15,14 +15,14 @@ fn eq<A: ?Sized,B: ?Sized>() where A : Eq<B> { }
 
 fn test<'a,'b>() {
     // Parens are equivalent to omitting default in angle.
-    eq::< Foo<(isize,),Output=()>,                   Foo(isize)                      >();
+    eq::<dyn Foo<(isize,), Output=()>, dyn Foo(isize)>();
 
     // In angle version, we supply something other than the default
-    eq::< Foo<(isize,),isize,Output=()>,      Foo(isize)                      >();
+    eq::<dyn Foo<(isize,), isize, Output=()>, dyn Foo(isize)>();
     //~^ ERROR E0277
 
     // Supply default explicitly.
-    eq::< Foo<(isize,),(isize,),Output=()>,   Foo(isize)                      >();
+    eq::<dyn Foo<(isize,), (isize,), Output=()>, dyn Foo(isize)>();
 }
 
 fn main() { }
index ce90f5b9d2486b61cc584b88f13193bc5b955305..fd5ef4b9df15aa178d1e3049320be8b8dfd43f25 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the trait bound `dyn Foo<(isize,), isize, Output = ()>: Eq<dyn Foo<(isize,), Output = ()>>` is not satisfied
   --> $DIR/unboxed-closure-sugar-default.rs:21:5
    |
-LL |     eq::< Foo<(isize,),isize,Output=()>,      Foo(isize)                      >();
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Eq<dyn Foo<(isize,), Output = ()>>` is not implemented for `dyn Foo<(isize,), isize, Output = ()>`
+LL |     eq::<dyn Foo<(isize,), isize, Output=()>, dyn Foo(isize)>();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Eq<dyn Foo<(isize,), Output = ()>>` is not implemented for `dyn Foo<(isize,), isize, Output = ()>`
    |
 note: required by `eq`
   --> $DIR/unboxed-closure-sugar-default.rs:14:1
index 95bd391f251b8ce047d9a1a6aa18bdb47f9b590b..0fc3e23ec73ef17c4995c71630ab2e9a2b6db9b4 100644 (file)
@@ -17,31 +17,31 @@ fn eq<A: ?Sized,B: ?Sized +Eq<A>>() { }
 
 fn test<'a,'b>() {
     // No errors expected:
-    eq::< Foo<(),Output=()>,                       Foo()                         >();
-    eq::< Foo<(isize,),Output=()>,                 Foo(isize)                      >();
-    eq::< Foo<(isize,usize),Output=()>,            Foo(isize,usize)                 >();
-    eq::< Foo<(isize,usize),Output=usize>,         Foo(isize,usize) -> usize         >();
-    eq::< Foo<(&'a isize,&'b usize),Output=usize>, Foo(&'a isize,&'b usize) -> usize >();
+    eq::< dyn Foo<(),Output=()>,                       dyn Foo()                         >();
+    eq::< dyn Foo<(isize,),Output=()>,                 dyn Foo(isize)                      >();
+    eq::< dyn Foo<(isize,usize),Output=()>,            dyn Foo(isize,usize)                 >();
+    eq::< dyn Foo<(isize,usize),Output=usize>,         dyn Foo(isize,usize) -> usize         >();
+    eq::< dyn Foo<(&'a isize,&'b usize),Output=usize>, dyn Foo(&'a isize,&'b usize) -> usize >();
 
     // Test that anonymous regions in `()` form are equivalent
     // to fresh bound regions, and that we can intermingle
     // named and anonymous as we choose:
-    eq::< for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
-          for<'x,'y> Foo(&'x isize,&'y usize) -> usize            >();
-    eq::< for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
-          for<'x> Foo(&'x isize,&usize) -> usize                  >();
-    eq::< for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
-          for<'y> Foo(&isize,&'y usize) -> usize                  >();
-    eq::< for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
-          Foo(&isize,&usize) -> usize                             >();
+    eq::< dyn for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
+          dyn for<'x,'y> Foo(&'x isize,&'y usize) -> usize            >();
+    eq::< dyn for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
+          dyn for<'x> Foo(&'x isize,&usize) -> usize                  >();
+    eq::< dyn for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
+          dyn for<'y> Foo(&isize,&'y usize) -> usize                  >();
+    eq::< dyn for<'x,'y> Foo<(&'x isize,&'y usize),Output=usize>,
+          dyn Foo(&isize,&usize) -> usize                             >();
 
     // lifetime elision
-    eq::< for<'x> Foo<(&'x isize,), Output=&'x isize>,
-          Foo(&isize) -> &isize                                   >();
+    eq::< dyn for<'x> Foo<(&'x isize,), Output=&'x isize>,
+          dyn Foo(&isize) -> &isize                                   >();
 
     // Errors expected:
-    eq::< Foo<(),Output=()>,
-          Foo(char)                                               >();
+    eq::< dyn Foo<(),Output=()>,
+          dyn Foo(char)                                               >();
     //~^^ ERROR E0277
 }
 
index 857a32ca69e73a49b309f25654e65115eed6f4bf..005a86bc2178b0f79523e4abaae520d96c7fde24 100644 (file)
@@ -1,9 +1,9 @@
 error[E0277]: the trait bound `dyn Foo<(char,), Output = ()>: Eq<dyn Foo<(), Output = ()>>` is not satisfied
   --> $DIR/unboxed-closure-sugar-equiv.rs:43:5
    |
-LL | /     eq::< Foo<(),Output=()>,
-LL | |           Foo(char)                                               >();
-   | |___________________________________________________________________^ the trait `Eq<dyn Foo<(), Output = ()>>` is not implemented for `dyn Foo<(char,), Output = ()>`
+LL | /     eq::< dyn Foo<(),Output=()>,
+LL | |           dyn Foo(char)                                               >();
+   | |_______________________________________________________________________^ the trait `Eq<dyn Foo<(), Output = ()>>` is not implemented for `dyn Foo<(char,), Output = ()>`
    |
 note: required by `eq`
   --> $DIR/unboxed-closure-sugar-equiv.rs:16:1
index b61d8b8c8c790c917152e6d836da999118f781dc..d11d663f17261afbe8a8b0de6642574e5a556f28 100644 (file)
@@ -18,10 +18,10 @@ impl<X: ?Sized> Eq<X> for X { }
 fn eq<A: ?Sized,B: ?Sized +Eq<A>>() { }
 
 fn main() {
-    eq::< for<'a> Foo<(&'a isize,), Output=&'a isize>,
-          Foo(&isize) -> &isize                                   >();
-    eq::< for<'a> Foo<(&'a isize,), Output=(&'a isize, &'a isize)>,
-          Foo(&isize) -> (&isize, &isize)                           >();
+    eq::< dyn for<'a> Foo<(&'a isize,), Output=&'a isize>,
+          dyn Foo(&isize) -> &isize                                   >();
+    eq::< dyn for<'a> Foo<(&'a isize,), Output=(&'a isize, &'a isize)>,
+          dyn Foo(&isize) -> (&isize, &isize)                           >();
 
-    let _: Foo(&isize, &usize) -> &usize; //~ ERROR missing lifetime specifier
+    let _: dyn Foo(&isize, &usize) -> &usize; //~ ERROR missing lifetime specifier
 }
index 8c3480744fe3d0e50e5b4d131c883051d7f155ef..9fb9a07166f849f0bcfbf471deb9c06d27e748bd 100644 (file)
@@ -1,8 +1,8 @@
 error[E0106]: missing lifetime specifier
-  --> $DIR/unboxed-closure-sugar-lifetime-elision.rs:26:35
+  --> $DIR/unboxed-closure-sugar-lifetime-elision.rs:26:39
    |
-LL |     let _: Foo(&isize, &usize) -> &usize;
-   |                                   ^ expected lifetime parameter
+LL |     let _: dyn Foo(&isize, &usize) -> &usize;
+   |                                       ^ expected lifetime parameter
    |
    = help: this function's return type contains a borrowed value, but the signature does not say whether it is borrowed from argument 1 or argument 2
 
index 09927a940192a900d572bc541729f8ba34c6e57f..6d6ed4b568f0b73cd4188d8479f48f14084975c4 100644 (file)
@@ -1,6 +1,6 @@
 // Test that the `Fn` traits require `()` form without a feature gate.
 
-fn bar1(x: &Fn<(), Output=()>) {
+fn bar1(x: &dyn Fn<(), Output=()>) {
     //~^ ERROR of `Fn`-family traits' type parameters is subject to change
 }
 
index 0901126a3fec366d83617eb105795cd1c8a95ba1..e1ed85d4f46726a3cf8567b502ad29d0dcbe0481 100644 (file)
@@ -1,8 +1,8 @@
 error[E0658]: the precise format of `Fn`-family traits' type parameters is subject to change. Use parenthetical notation (Fn(Foo, Bar) -> Baz) instead
-  --> $DIR/unboxed-closure-sugar-not-used-on-fn.rs:3:13
+  --> $DIR/unboxed-closure-sugar-not-used-on-fn.rs:3:17
    |
-LL | fn bar1(x: &Fn<(), Output=()>) {
-   |             ^^^^^^^^^^^^^^^^^
+LL | fn bar1(x: &dyn Fn<(), Output=()>) {
+   |                 ^^^^^^^^^^^^^^^^^
    |
    = note: for more information, see https://github.com/rust-lang/rust/issues/29625
    = help: add #![feature(unboxed_closures)] to the crate attributes to enable
index 799d9f33e2e9d1b5d9f0493b38416f0d8b770cab..76c928d7b6ab5ed4b08ae2f4de2f6b07c229d331 100644 (file)
@@ -20,14 +20,14 @@ fn same_type<A,B:Eq<A>>(a: A, b: B) { }
 
 fn test<'a,'b>() {
     // Parens are equivalent to omitting default in angle.
-    eq::< Foo<(isize,),Output=()>,               Foo(isize)                      >();
+    eq::< dyn Foo<(isize,),Output=()>,               dyn Foo(isize)                      >();
 
     // Here we specify 'static explicitly in angle-bracket version.
     // Parenthesized winds up getting inferred.
-    eq::< Foo<'static, (isize,),Output=()>,      Foo(isize)                      >();
+    eq::< dyn Foo<'static, (isize,),Output=()>,      dyn Foo(isize)                      >();
 }
 
-fn test2(x: &Foo<(isize,),Output=()>, y: &Foo(isize)) {
+fn test2(x: &dyn Foo<(isize,),Output=()>, y: &dyn Foo(isize)) {
 //~^ ERROR wrong number of lifetime arguments: expected 1, found 0
     // Here, the omitted lifetimes are expanded to distinct things.
     same_type(x, y)
index 8eed7d58c4666e8174c0785464a6044deaaaeb50..e9d51983a7a483f077daec9897419acad1e03a15 100644 (file)
@@ -1,8 +1,8 @@
 error[E0107]: wrong number of lifetime arguments: expected 1, found 0
-  --> $DIR/unboxed-closure-sugar-region.rs:30:43
+  --> $DIR/unboxed-closure-sugar-region.rs:30:51
    |
-LL | fn test2(x: &Foo<(isize,),Output=()>, y: &Foo(isize)) {
-   |                                           ^^^^^^^^^^ expected 1 lifetime argument
+LL | fn test2(x: &dyn Foo<(isize,),Output=()>, y: &dyn Foo(isize)) {
+   |                                                   ^^^^^^^^^^ expected 1 lifetime argument
 
 error: aborting due to previous error
 
index df0c495a11cc659371b09dc42b6130024df8a1a9..a6c86311b37722ff5bf9dd04e4b70ca23f593a21 100644 (file)
@@ -2,7 +2,7 @@
 
 trait One<A> { fn foo(&self) -> A; }
 
-fn foo(_: &One()) //~ ERROR associated type `Output` not found for `One<()>`
+fn foo(_: &dyn One()) //~ ERROR associated type `Output` not found for `One<()>`
 {}
 
 fn main() { }
index 304339c89e6444ed98cbc2a2b8e44b46779635e6..c59082932ddfec05c0f83ee049c6eba080bec13d 100644 (file)
@@ -1,8 +1,8 @@
 error[E0220]: associated type `Output` not found for `One<()>`
-  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-1.rs:5:15
+  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-1.rs:5:19
    |
-LL | fn foo(_: &One())
-   |               ^^ associated type `Output` not found
+LL | fn foo(_: &dyn One())
+   |                   ^^ associated type `Output` not found
 
 error: aborting due to previous error
 
index 5f5ad7902aa3e85f4269bddf04f06e48f81d2b34..01c76d64c6ba05b367a05c99344191bd5784fd8e 100644 (file)
@@ -2,7 +2,7 @@
 
 trait Three<A,B,C> { fn dummy(&self) -> (A,B,C); }
 
-fn foo(_: &Three())
+fn foo(_: &dyn Three())
 //~^ ERROR wrong number of type arguments
 //~| ERROR associated type `Output` not found
 {}
index 62b3a2544305565ac49b89e00e32b08f07516545..6c61e74584a502ddd092e434d31a426d0c4c4d34 100644 (file)
@@ -1,14 +1,14 @@
 error[E0107]: wrong number of type arguments: expected 3, found 1
-  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-3.rs:5:12
+  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-3.rs:5:16
    |
-LL | fn foo(_: &Three())
-   |            ^^^^^^^ expected 3 type arguments
+LL | fn foo(_: &dyn Three())
+   |                ^^^^^^^ expected 3 type arguments
 
 error[E0220]: associated type `Output` not found for `Three<(), [type error], [type error]>`
-  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-3.rs:5:17
+  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters-3.rs:5:21
    |
-LL | fn foo(_: &Three())
-   |                 ^^ associated type `Output` not found
+LL | fn foo(_: &dyn Three())
+   |                     ^^ associated type `Output` not found
 
 error: aborting due to 2 previous errors
 
index 2e87d91f8bdc04a7be68f194645d64e0b1e90554..bc9901c795b3a894415c147aa4631f8a04ac8023 100644 (file)
@@ -2,7 +2,7 @@
 
 trait Zero { fn dummy(&self); }
 
-fn foo(_: Zero())
+fn foo(_: dyn Zero())
     //~^ ERROR wrong number of type arguments
     //~| ERROR associated type `Output` not found for `Zero`
 {}
index b64fc61cc85685ed3edc28cabe906e56054332e7..b96e2cbc36bb40ad278a43918a3d4b87ff4b0aff 100644 (file)
@@ -1,14 +1,14 @@
 error[E0107]: wrong number of type arguments: expected 0, found 1
-  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters.rs:5:15
+  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters.rs:5:19
    |
-LL | fn foo(_: Zero())
-   |               ^^ unexpected type argument
+LL | fn foo(_: dyn Zero())
+   |                   ^^ unexpected type argument
 
 error[E0220]: associated type `Output` not found for `Zero`
-  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters.rs:5:15
+  --> $DIR/unboxed-closure-sugar-wrong-number-number-type-parameters.rs:5:19
    |
-LL | fn foo(_: Zero())
-   |               ^^ associated type `Output` not found
+LL | fn foo(_: dyn Zero())
+   |                   ^^ associated type `Output` not found
 
 error: aborting due to 2 previous errors
 
index 82dc536bb5693ca8ebac0c3b3581046e153d0f02..1358ba0f953e8e91aa19b619ab64117f52fa22b6 100644 (file)
@@ -9,7 +9,7 @@ fn a() {
     // iteration, but it still doesn't work. The weird structure with
     // the `Option` is to avoid giving any useful hints about the `Fn`
     // kind via the expected type.
-    let mut factorial: Option<Box<Fn(u32) -> u32>> = None;
+    let mut factorial: Option<Box<dyn Fn(u32) -> u32>> = None;
 
     let f = |x: u32| -> u32 {
         let g = factorial.as_ref().unwrap();
@@ -22,7 +22,7 @@ fn a() {
 }
 
 fn b() {
-    let mut factorial: Option<Box<Fn(u32) -> u32 + 'static>> = None;
+    let mut factorial: Option<Box<dyn Fn(u32) -> u32 + 'static>> = None;
 
     let f = |x: u32| -> u32 {
         let g = factorial.as_ref().unwrap();
index 8d39fb026b3d7a07bd02124c5acb4937aab80d0d..0466887e371e9a2dd05a096d96b5ff2f62b4e965 100644 (file)
@@ -29,8 +29,8 @@ LL |     factorial = Some(Box::new(f));
 error[E0597]: `factorial` does not live long enough
   --> $DIR/unboxed-closures-failed-recursive-fn-1.rs:28:17
    |
-LL |     let mut factorial: Option<Box<Fn(u32) -> u32 + 'static>> = None;
-   |                        ------------------------------------- type annotation requires that `factorial` is borrowed for `'static`
+LL |     let mut factorial: Option<Box<dyn Fn(u32) -> u32 + 'static>> = None;
+   |                        ----------------------------------------- type annotation requires that `factorial` is borrowed for `'static`
 LL | 
 LL |     let f = |x: u32| -> u32 {
    |             --------------- value captured here
@@ -43,8 +43,8 @@ LL | }
 error[E0506]: cannot assign to `factorial` because it is borrowed
   --> $DIR/unboxed-closures-failed-recursive-fn-1.rs:33:5
    |
-LL |     let mut factorial: Option<Box<Fn(u32) -> u32 + 'static>> = None;
-   |                        ------------------------------------- type annotation requires that `factorial` is borrowed for `'static`
+LL |     let mut factorial: Option<Box<dyn Fn(u32) -> u32 + 'static>> = None;
+   |                        ----------------------------------------- type annotation requires that `factorial` is borrowed for `'static`
 LL | 
 LL |     let f = |x: u32| -> u32 {
    |             --------------- borrow of `factorial` occurs here
index 0beead1ad92c3dab8e59458c2106ec53a062825a..6a707b2096d442ea2156bf49d9f579939c4a661b 100644 (file)
@@ -17,14 +17,14 @@ fn new(f: F) -> YCombinator<F,A,R> {
     }
 }
 
-impl<A,R,F : FnMut(&mut FnMut(A) -> R, A) -> R> FnMut<(A,)> for YCombinator<F,A,R> {
+impl<A,R,F : FnMut(&mut dyn FnMut(A) -> R, A) -> R> FnMut<(A,)> for YCombinator<F,A,R> {
     extern "rust-call" fn call_mut(&mut self, (arg,): (A,)) -> R {
         (self.func)(self, arg)
             //~^ ERROR cannot borrow `*self` as mutable more than once at a time
     }
 }
 
-impl<A,R,F : FnMut(&mut FnMut(A) -> R, A) -> R> FnOnce<(A,)> for YCombinator<F,A,R> {
+impl<A,R,F : FnMut(&mut dyn FnMut(A) -> R, A) -> R> FnOnce<(A,)> for YCombinator<F,A,R> {
     type Output = R;
     extern "rust-call" fn call_once(mut self, args: (A,)) -> R {
         self.call_mut(args)
@@ -33,7 +33,7 @@ extern "rust-call" fn call_once(mut self, args: (A,)) -> R {
 
 fn main() {
     let mut counter = 0;
-    let factorial = |recur: &mut FnMut(u32) -> u32, arg: u32| -> u32 {
+    let factorial = |recur: &mut dyn FnMut(u32) -> u32, arg: u32| -> u32 {
         counter += 1;
         if arg == 0 {1} else {arg * recur(arg-1)}
     };
index 614f7e49f87571946c9f9635fb33545051d4c38e..3d049cc5639c05b5931de1788a34517a678ec20d 100644 (file)
@@ -7,7 +7,7 @@ fn foo<'_> //~ ERROR cannot be used here
 trait Meh<'a> {}
 impl<'a> Meh<'a> for u8 {}
 
-fn meh() -> Box<for<'_> Meh<'_>> //~ ERROR cannot be used here
+fn meh() -> Box<dyn for<'_> Meh<'_>> //~ ERROR cannot be used here
 //~^ ERROR missing lifetime specifier
 {
   Box::new(5u8)
index 936e3ba55fea1738d04f7198c0f9987a93bca985..654f4285f655f90e88192c3dc8701f1ce423cefc 100644 (file)
@@ -5,10 +5,10 @@ LL | fn foo<'_>
    |        ^^ `'_` is a reserved lifetime name
 
 error[E0637]: `'_` cannot be used here
-  --> $DIR/underscore-lifetime-binders.rs:10:21
+  --> $DIR/underscore-lifetime-binders.rs:10:25
    |
-LL | fn meh() -> Box<for<'_> Meh<'_>>
-   |                     ^^ `'_` is a reserved lifetime name
+LL | fn meh() -> Box<dyn for<'_> Meh<'_>>
+   |                         ^^ `'_` is a reserved lifetime name
 
 error[E0106]: missing lifetime specifier
   --> $DIR/underscore-lifetime-binders.rs:2:17
@@ -17,10 +17,10 @@ LL | struct Baz<'a>(&'_ &'a u8);
    |                 ^^ expected lifetime parameter
 
 error[E0106]: missing lifetime specifier
-  --> $DIR/underscore-lifetime-binders.rs:10:29
+  --> $DIR/underscore-lifetime-binders.rs:10:33
    |
-LL | fn meh() -> Box<for<'_> Meh<'_>>
-   |                             ^^ help: consider giving it a 'static lifetime: `'static`
+LL | fn meh() -> Box<dyn for<'_> Meh<'_>>
+   |                                 ^^ help: consider giving it a 'static lifetime: `'static`
    |
    = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from
 
index 1c467a2421a2ada108a3b0e0dde96fa120f9dd8b..dd38a7190aa0e9d83b71c686a619097e7ff68404 100644 (file)
@@ -20,6 +20,6 @@ fn f(&self) {
 
 fn main() {
     let x = box Bar { x: 10 };
-    let y: Box<Foo> = x as Box<Foo>;
+    let y: Box<dyn Foo> = x as Box<dyn Foo>;
     let _z = y.clone(); //~ ERROR no method named `clone` found
 }
index 60bfb5cb6402ae9a4146f2d23df6a5a3cb6daf53..d589f5ae582c6689bf74b060bd25f501050b187b 100644 (file)
@@ -13,10 +13,10 @@ trait PathHelper2 {}
 trait PathHelper3 {}
 trait PathHelper4 {}
 
-struct Path1(PathHelper1);
-struct Path2(PathHelper2);
-struct Path3(PathHelper3);
-struct Path4(PathHelper4);
+struct Path1(dyn PathHelper1);
+struct Path2(dyn PathHelper2);
+struct Path3(dyn PathHelper3);
+struct Path4(dyn PathHelper4);
 
 enum E<W: ?Sized, X: ?Sized, Y: ?Sized, Z: ?Sized> {
     // parameter
@@ -50,13 +50,13 @@ enum E<W: ?Sized, X: ?Sized, Y: ?Sized, Z: ?Sized> {
     //~^ ERROR the size for values of type
 
     // plain trait
-    VM(Foo),
+    VM(dyn Foo),
     //~^ ERROR the size for values of type
-    VN{x: Bar},
+    VN{x: dyn Bar},
     //~^ ERROR the size for values of type
-    VO(isize, FooBar),
+    VO(isize, dyn FooBar),
     //~^ ERROR the size for values of type
-    VP{u: isize, x: BarFoo},
+    VP{u: isize, x: dyn BarFoo},
     //~^ ERROR the size for values of type
 
     // projected
index 9109366e4fcfdde30eb2e3e82f25711715672ce8..cdd5747d86b0f275b873a6d4072c5b58c8228bc2 100644 (file)
@@ -85,8 +85,8 @@ LL |     VH{u: isize, x: [u32]},
 error[E0277]: the size for values of type `(dyn Foo + 'static)` cannot be known at compilation time
   --> $DIR/unsized-enum2.rs:53:8
    |
-LL |     VM(Foo),
-   |        ^^^ doesn't have a size known at compile-time
+LL |     VM(dyn Foo),
+   |        ^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn Foo + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -95,8 +95,8 @@ LL |     VM(Foo),
 error[E0277]: the size for values of type `(dyn Bar + 'static)` cannot be known at compilation time
   --> $DIR/unsized-enum2.rs:55:8
    |
-LL |     VN{x: Bar},
-   |        ^^^^^^ doesn't have a size known at compile-time
+LL |     VN{x: dyn Bar},
+   |        ^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn Bar + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -105,8 +105,8 @@ LL |     VN{x: Bar},
 error[E0277]: the size for values of type `(dyn FooBar + 'static)` cannot be known at compilation time
   --> $DIR/unsized-enum2.rs:57:15
    |
-LL |     VO(isize, FooBar),
-   |               ^^^^^^ doesn't have a size known at compile-time
+LL |     VO(isize, dyn FooBar),
+   |               ^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn FooBar + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
@@ -115,8 +115,8 @@ LL |     VO(isize, FooBar),
 error[E0277]: the size for values of type `(dyn BarFoo + 'static)` cannot be known at compilation time
   --> $DIR/unsized-enum2.rs:59:18
    |
-LL |     VP{u: isize, x: BarFoo},
-   |                  ^^^^^^^^^ doesn't have a size known at compile-time
+LL |     VP{u: isize, x: dyn BarFoo},
+   |                  ^^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn BarFoo + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
index 2e465ee896268da4fee8b319df6324b8cdceadb3..76487ef1c14093d604ebe1ba72d7727e7e410ec1 100644 (file)
@@ -13,10 +13,10 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
 }
 
 struct List {
-    list: Vec<Box<ToString+'static>> }
+    list: Vec<Box<dyn ToString + 'static>> }
 
 impl List {
-    fn push(&mut self, n: Box<ToString+'static>) {
+    fn push(&mut self, n: Box<dyn ToString + 'static>) {
         self.list.push(n);
     }
 }
index 8b5ecbe56ff2d496d550b61ceb1db0ce8b251a3b..69818aedd154c1e51df059859fe2ba56b0068f3b 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/variance-contravariant-arg-object.rs:14:5
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
@@ -12,7 +12,7 @@ LL |     v
 error: lifetime may not live long enough
   --> $DIR/variance-contravariant-arg-object.rs:22:5
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
index 27e5675dcde87656607f75f6b9e553754bce07c2..947f4cd8b8f4d0e886991d7e2a9842c2a2a4d976 100644 (file)
@@ -7,15 +7,15 @@ trait Get<T> : 'static {
     fn get(&self, t: T);
 }
 
-fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
-                                -> Box<Get<&'min i32>>
+fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
+                                -> Box<dyn Get<&'min i32>>
     where 'max : 'min
 {
     v //~ ERROR mismatched types
 }
 
-fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
-                                   -> Box<Get<&'max i32>>
+fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
+                                   -> Box<dyn Get<&'max i32>>
     where 'max : 'min
 {
     // Previously OK:
index beac05e04a8e37023557509ca3eccd8b77a887b4..263c849e19981378337f3bcf9f0ec5d6decee194 100644 (file)
@@ -9,12 +9,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 10:21...
   --> $DIR/variance-contravariant-arg-object.rs:10:21
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 10:27
   --> $DIR/variance-contravariant-arg-object.rs:10:27
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                           ^^^^
 
 error[E0308]: mismatched types
@@ -28,12 +28,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 17:21...
   --> $DIR/variance-contravariant-arg-object.rs:17:21
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 17:27
   --> $DIR/variance-contravariant-arg-object.rs:17:27
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                           ^^^^
 
 error: aborting due to 2 previous errors
index acf9f2e060ce90708649194bd1a5cf234799f317..63ab7fe96512d237c35036de0f8782893ff013e8 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/variance-covariant-arg-object.rs:15:5
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
@@ -12,7 +12,7 @@ LL |     v
 error: lifetime may not live long enough
   --> $DIR/variance-covariant-arg-object.rs:22:5
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
index 4b371841654f26968554e25c39ee57b9a27d0f86..7cbf65ae3d924be9a5d21ebf525f6c1cc0c7c708 100644 (file)
@@ -7,16 +7,16 @@ trait Get<T> : 'static {
     fn get(&self) -> T;
 }
 
-fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
-                                -> Box<Get<&'min i32>>
+fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
+                                -> Box<dyn Get<&'min i32>>
     where 'max : 'min
 {
     // Previously OK, now an error as traits are invariant.
     v //~ ERROR mismatched types
 }
 
-fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
-                                   -> Box<Get<&'max i32>>
+fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
+                                   -> Box<dyn Get<&'max i32>>
     where 'max : 'min
 {
     v //~ ERROR mismatched types
index cdcc7a6fd55a68f70c7310cabe9dd9a5d2735f39..94f80c2b657f5247680121d67ba531f9a44e14f0 100644 (file)
@@ -9,12 +9,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 10:21...
   --> $DIR/variance-covariant-arg-object.rs:10:21
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 10:27
   --> $DIR/variance-covariant-arg-object.rs:10:27
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                           ^^^^
 
 error[E0308]: mismatched types
@@ -28,12 +28,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 18:21...
   --> $DIR/variance-covariant-arg-object.rs:18:21
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 18:27
   --> $DIR/variance-covariant-arg-object.rs:18:27
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                           ^^^^
 
 error: aborting due to 2 previous errors
index 3c1ee7fc707f8cea6c40150b384492bba3693a40..fe2f35b63b57d258e95639297ff6b1d52bdecca6 100644 (file)
@@ -1,7 +1,7 @@
 error: lifetime may not live long enough
   --> $DIR/variance-invariant-arg-object.rs:11:5
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
@@ -12,7 +12,7 @@ LL |     v
 error: lifetime may not live long enough
   --> $DIR/variance-invariant-arg-object.rs:18:5
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ----  ---- lifetime `'max` defined here
    |                     |
    |                     lifetime `'min` defined here
index 91f5982e5339f62f90bee124c1437718e8161372..886d263c45768652ae9b5cf3aa67dfd17984c150 100644 (file)
@@ -4,15 +4,15 @@ trait Get<T> : 'static {
     fn get(&self, t: T) -> T;
 }
 
-fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
-                                -> Box<Get<&'min i32>>
+fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
+                                -> Box<dyn Get<&'min i32>>
     where 'max : 'min
 {
     v //~ ERROR mismatched types
 }
 
-fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
-                                   -> Box<Get<&'max i32>>
+fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
+                                   -> Box<dyn Get<&'max i32>>
     where 'max : 'min
 {
     v //~ ERROR mismatched types
index e2ee35de1a2780f64337d252623e7fcbdd5f623e..50a8697d4392f64f02332d714e5bddc1281d11b1 100644 (file)
@@ -9,12 +9,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 7:21...
   --> $DIR/variance-invariant-arg-object.rs:7:21
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 7:27
   --> $DIR/variance-invariant-arg-object.rs:7:27
    |
-LL | fn get_min_from_max<'min, 'max>(v: Box<Get<&'max i32>>)
+LL | fn get_min_from_max<'min, 'max>(v: Box<dyn Get<&'max i32>>)
    |                           ^^^^
 
 error[E0308]: mismatched types
@@ -28,12 +28,12 @@ LL |     v
 note: the lifetime 'min as defined on the function body at 14:21...
   --> $DIR/variance-invariant-arg-object.rs:14:21
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                     ^^^^
 note: ...does not necessarily outlive the lifetime 'max as defined on the function body at 14:27
   --> $DIR/variance-invariant-arg-object.rs:14:27
    |
-LL | fn get_max_from_min<'min, 'max, G>(v: Box<Get<&'min i32>>)
+LL | fn get_max_from_min<'min, 'max, G>(v: Box<dyn Get<&'min i32>>)
    |                           ^^^^
 
 error: aborting due to 2 previous errors
index 12af7ae8c5b8a36e29445b4cea37e080ad3ae435..14e11f681b1002ec2a8237ef513bc39475489148 100644 (file)
@@ -9,7 +9,7 @@
 // get an invariant result for `'a`.
 #[rustc_variance]
 struct Foo<'a> { //~ ERROR [o]
-    x: Box<Fn(i32) -> &'a i32 + 'static>
+    x: Box<dyn Fn(i32) -> &'a i32 + 'static>
 }
 
 fn main() {
index be94a727a8d16eaee02dca2b906bc3b2e58da45b..d97d222e711adc1536c22a229741c94042713c45 100644 (file)
@@ -2,7 +2,7 @@ error[E0208]: [o]
   --> $DIR/variance-object-types.rs:11:1
    |
 LL | / struct Foo<'a> {
-LL | |     x: Box<Fn(i32) -> &'a i32 + 'static>
+LL | |     x: Box<dyn Fn(i32) -> &'a i32 + 'static>
 LL | | }
    | |_^
 
index ada93b7f6efc765e7311856054720e410e6cac82..ec3c973bc76395eba6e90c8250503e3707f4c19f 100644 (file)
@@ -12,7 +12,7 @@
 
 #[rustc_variance]
 struct TOption<'a> { //~ ERROR [-]
-    v: Option<Box<T + 'a>>,
+    v: Option<Box<dyn T + 'a>>,
 }
 
 fn main() { }
index 503c087fb4d38952649cca0176e829a14e444fcc..fb0fab1950cef5437e9742f49ab7aa881affaf99 100644 (file)
@@ -2,7 +2,7 @@ error[E0208]: [-]
   --> $DIR/variance-trait-object-bound.rs:14:1
    |
 LL | / struct TOption<'a> {
-LL | |     v: Option<Box<T + 'a>>,
+LL | |     v: Option<Box<dyn T + 'a>>,
 LL | | }
    | |_^
 
index 5cbda10fbdedadab23218ce8190eda8a98f941ab..d1814dd97a0ad819b512aa9a823b6b73c391d1e1 100644 (file)
@@ -36,8 +36,8 @@ trait Setter<A> {
 
 #[rustc_variance]
 struct TestObject<A, R> { //~ ERROR [o, o]
-    n: Box<Setter<A>+Send>,
-    m: Box<Getter<R>+Send>,
+    n: Box<dyn Setter<A>+Send>,
+    m: Box<dyn Getter<R>+Send>,
 }
 
 fn main() {}
index 8e3e0515aec022ecc5ac1dcc25dc460bcb34c789..5cffdffc7f2d42196a807a8ace4f20f7a6e0442a 100644 (file)
@@ -37,8 +37,8 @@ error[E0208]: [o, o]
   --> $DIR/variance-types-bounds.rs:38:1
    |
 LL | / struct TestObject<A, R> {
-LL | |     n: Box<Setter<A>+Send>,
-LL | |     m: Box<Getter<R>+Send>,
+LL | |     n: Box<dyn Setter<A>+Send>,
+LL | |     m: Box<dyn Getter<R>+Send>,
 LL | | }
    | |_^
 
index 858a75ab1ab5a836c1319affb0c62f30ef447e63..1ad2fd1edb3b8a6da4e33e3cdf131d4b3fbd9851 100644 (file)
@@ -11,7 +11,7 @@ struct MustBeCopy<T:Copy> {
 
 struct Foo<T> {
     // needs T: 'static
-    x: Object<&'static T> //~ ERROR E0310
+    x: dyn Object<&'static T> //~ ERROR E0310
 }
 
 
index cc06b9243f70799cfa3ee1afd74098fd75a732bc..c461da76a25762a191d93f5119e30f04c9201034 100644 (file)
@@ -4,14 +4,14 @@ error[E0310]: the parameter type `T` may not live long enough
 LL | struct Foo<T> {
    |            - help: consider adding an explicit lifetime bound `T: 'static`...
 LL |     // needs T: 'static
-LL |     x: Object<&'static T>
-   |     ^^^^^^^^^^^^^^^^^^^^^
+LL |     x: dyn Object<&'static T>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: ...so that the reference type `&'static T` does not outlive the data it points at
   --> $DIR/wf-in-obj-type-static.rs:14:5
    |
-LL |     x: Object<&'static T>
-   |     ^^^^^^^^^^^^^^^^^^^^^
+LL |     x: dyn Object<&'static T>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
index fad1da199ea910d8e39b7e5156ea3b89f7084152..170fad55f8f65b8786267bedaa8a55f203bd1f1f 100644 (file)
@@ -8,7 +8,7 @@ struct MustBeCopy<T:Copy> {
 
 struct Bar<T> {
     // needs T: Copy
-    x: Object<MustBeCopy<T>> //~ ERROR E0277
+    x: dyn Object<MustBeCopy<T>> //~ ERROR E0277
 }
 
 fn main() { }
index 94b3de78898a746b5542d6fa8d961ce1449191f8..2c85dd042e7ba15555d4f821f39995b3c1da0a34 100644 (file)
@@ -1,8 +1,8 @@
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
   --> $DIR/wf-in-obj-type-trait.rs:11:5
    |
-LL |     x: Object<MustBeCopy<T>>
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `T`
+LL |     x: dyn Object<MustBeCopy<T>>
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `T`
    |
    = help: consider adding a `where T: std::marker::Copy` bound
 note: required by `MustBeCopy`
index 08f68f6c004fae40fbcee9c787306289042e9217..42e6917551fd973b211a6b2701c17a94379bf109 100644 (file)
@@ -6,5 +6,5 @@ trait A {
 }
 
 fn main() {
-    let _x: &A; //~ ERROR E0038
+    let _x: &dyn A; //~ ERROR E0038
 }
index 87e8105d4aff5edce5fa4a75629fb9573d75617e..3b264ecd580ecb77367676784835ec90a120b735 100644 (file)
@@ -1,8 +1,8 @@
 error[E0038]: the trait `A` cannot be made into an object
   --> $DIR/wf-object-safe.rs:9:13
    |
-LL |     let _x: &A;
-   |             ^^ the trait `A` cannot be made into an object
+LL |     let _x: &dyn A;
+   |             ^^^^^^ the trait `A` cannot be made into an object
    |
    = note: method `foo` references the `Self` type in its arguments or return type
 
index ac95cbab1f73eff276d895877fa5f7739d9195e8..85a332e244ff0f1dca05c15a6096c644a55f0474 100644 (file)
@@ -16,7 +16,7 @@ struct Foo<'a,T> {
 trait Baz<T> { }
 
 impl<'a, T> Trait<'a, T> for u32 {
-    type Out = &'a Baz<T>; //~ ERROR `T` may not live long enough
+    type Out = &'a dyn Baz<T>; //~ ERROR `T` may not live long enough
 }
 
 fn main() { }
index 8649506c870d7c8ef1a986104ea9dc271f3919a8..f1cf514e6b298c711df26e179c620b8863743f15 100644 (file)
@@ -17,14 +17,14 @@ error[E0309]: the parameter type `T` may not live long enough
    |
 LL | impl<'a, T> Trait<'a, T> for u32 {
    |          - help: consider adding an explicit lifetime bound `T: 'a`...
-LL |     type Out = &'a Baz<T>;
-   |     ^^^^^^^^^^^^^^^^^^^^^^
+LL |     type Out = &'a dyn Baz<T>;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 note: ...so that the reference type `&'a (dyn Baz<T> + 'a)` does not outlive the data it points at
   --> $DIR/wf-outlives-ty-in-fn-or-trait.rs:19:5
    |
-LL |     type Out = &'a Baz<T>;
-   |     ^^^^^^^^^^^^^^^^^^^^^^
+LL |     type Out = &'a dyn Baz<T>;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to 2 previous errors
 
index 4c46a77ae2916080dd03fd6ee48a5cab2ac67937..0d426386768c8f450a1488c476e8597cf6f92980 100644 (file)
@@ -2,10 +2,10 @@ trait Trait1<'a> {}
 trait Trait2<'a, 'b> {}
 
 fn f() where
-    for<'a> Trait1<'a>: Trait1<'a>, // OK
-    (for<'a> Trait1<'a>): Trait1<'a>,
+    for<'a> dyn Trait1<'a>: Trait1<'a>, // OK
+    (dyn for<'a> Trait1<'a>): Trait1<'a>,
     //~^ ERROR use of undeclared lifetime name `'a`
-    for<'a> for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
+    for<'a> dyn for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
     //~^ ERROR use of undeclared lifetime name `'b`
     //~| ERROR nested quantification of lifetimes
 {}
index babf8efc23f3569604b4483dba99f40ab536f7d8..0081ae07163b33b4fcb56a7cd7b67c5e60561f06 100644 (file)
@@ -1,20 +1,20 @@
 error[E0261]: use of undeclared lifetime name `'a`
-  --> $DIR/where-lifetime-resolution.rs:6:34
+  --> $DIR/where-lifetime-resolution.rs:6:38
    |
-LL |     (for<'a> Trait1<'a>): Trait1<'a>,
-   |                                  ^^ undeclared lifetime
+LL |     (dyn for<'a> Trait1<'a>): Trait1<'a>,
+   |                                      ^^ undeclared lifetime
 
 error[E0316]: nested quantification of lifetimes
-  --> $DIR/where-lifetime-resolution.rs:8:13
+  --> $DIR/where-lifetime-resolution.rs:8:17
    |
-LL |     for<'a> for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
-   |             ^^^^^^^^^^^^^^^^^^^^^^
+LL |     for<'a> dyn for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
+   |                 ^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0261]: use of undeclared lifetime name `'b`
-  --> $DIR/where-lifetime-resolution.rs:8:48
+  --> $DIR/where-lifetime-resolution.rs:8:52
    |
-LL |     for<'a> for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
-   |                                                ^^ undeclared lifetime
+LL |     for<'a> dyn for<'b> Trait2<'a, 'b>: Trait2<'a, 'b>,
+   |                                                    ^^ undeclared lifetime
 
 error: aborting due to 3 previous errors
 
index 46e64911ad43c519c61d22afef7f82625dd9c4a8..fb33fad08e8f08c032b443bab0df299ce22fe61b 160000 (submodule)
@@ -1 +1 @@
-Subproject commit 46e64911ad43c519c61d22afef7f82625dd9c4a8
+Subproject commit fb33fad08e8f08c032b443bab0df299ce22fe61b