Change to resolve and update compiler and libs for uses.
[breaking-change]
Enum variants are now in both the value and type namespaces. This means that
if you have a variant with the same name as a type in scope in a module, you
will get a name clash and thus an error. The solution is to either rename the
type or the variant.
Part of issue #16640. I am leaving this issue open to handle parsing of
higher-rank lifetimes in traits.
This change breaks code that used unboxed closures:
* Instead of `F:|&: int| -> int`, write `F:Fn(int) -> int`.
* Instead of `F:|&mut: int| -> int`, write `F:FnMut(int) -> int`.
* Instead of `F:|: int| -> int`, write `F:FnOnce(int) -> int`.
[breaking-change]
This breaks code that looked like:
mymacro!(static::foo);
... where `mymacro!` expects a path or expression. Change such macros to
not accept keywords followed by `::`.
Closes#17298.
[breaking-change]
The implementation essentially desugars during type collection and AST
type conversion time into the parameter scheme we have now. Only fully
qualified names--e.g. `<T as Foo>::Bar`--are supported.
Recursive items are currently detected in the `check_const` pass which runs after type checking. This means a recursive static item used as an array length will cause type checking to blow the stack. This PR separates the recursion check out into a separate pass which is run before type checking.
Closes issue #17252
r? @nick29581
lifetime bounds. This doesn't really cause any difficulties, because
we already had to accommodate the fact that multiple implicit bounds
could accumulate. Object types still require precisely one lifetime
bound. This is a pre-step towards generalized where clauses (once you
have lifetime bounds in where clauses, it is harder to restrict them
to exactly one).
This patch does not make many functional changes, but does a lot of restructuring towards the goals of #5527. This is the biggest patch, basically, that should enable most of the other patches in a relatively straightforward way.
Major changes:
- Do not track impls through trans, instead recompute as needed.
- Isolate trait matching code into its own module, carefully structure to distinguish various phases (selection vs confirmation vs fulfillment)
- Consider where clauses in their more general form
- Integrate checking of builtin bounds into the trait matching process, rather than doing it separately in kind.rs (important for opt-in builtin bounds)
What is not included:
- Where clauses are still not generalized. This should be a straightforward follow-up patch.
- Caching. I did not include much caching. I have plans for various kinds of caching we can do. Should be straightforward. Preliminary perf measurements suggested that this branch keeps compilation times roughly what they are.
- Method resolution. The initial algorithm I proposed for #5527 does not work as well as I hoped. I have a revised plan which is much more similar to what we do today.
- Deref vs deref-mut. The initial fix I had worked great for autoderef, but not for explicit deref.
- Permitting blanket impls to overlap with specific impls. Initial plan to consider all nested obligations before considering an impl to match caused many compilation errors. We have a revised plan but it is not implemented here, should be a relatively straightforward extension.
This adds ‘help’ diagnostic messages to rustc. This is used for anything that
provides help to the user, particularly the `--explain` messages that were
previously integrated into the relevant error message.
type they provide an implementation for.
This breaks code like:
mod foo {
struct Foo { ... }
}
impl foo::Foo {
...
}
Change this code to:
mod foo {
struct Foo { ... }
impl Foo {
...
}
}
Additionally, if you used the I/O path extension methods `stat`,
`lstat`, `exists`, `is_file`, or `is_dir`, note that these methods have
been moved to the the `std::io::fs::PathExtensions` trait. This breaks
code like:
fn is_it_there() -> bool {
Path::new("/foo/bar/baz").exists()
}
Change this code to:
use std::io::fs::PathExtensions;
fn is_it_there() -> bool {
Path::new("/foo/bar/baz").exists()
}
Closes#17059.
RFC #155.
[breaking-change]
Avoid ever constructing cyclic types in the first place, rather than detecting them in resolve. This simplifies logic elsewhere in the compiler, in particular on the trait reform branch.
r? @pnkfelix or @pcwalton
cc #5527
This allows code to access the fields of tuples and tuple structs:
let x = (1i, 2i);
assert_eq!(x.1, 2);
struct Point(int, int);
let origin = Point(0, 0);
assert_eq!(origin.0, 0);
assert_eq!(origin.1, 0);
instead of prefix `..`.
This breaks code that looked like:
match foo {
[ first, ..middle, last ] => { ... }
}
Change this code to:
match foo {
[ first, middle.., last ] => { ... }
}
RFC #55.
Closes#16967.
[breaking-change]
This breaks code that uses the `..xs` form anywhere but at the end of a
slice. For example:
match foo {
[ 1, ..xs, 2 ]
[ ..xs, 1, 2 ]
}
Add the `#![feature(advanced_slice_patterns)]` gate to reenable the
syntax.
RFC #54.
Closes#16951.
[breaking-change]
itself.
This breaks code like:
for &x in my_vector.iter() {
my_vector[2] = "wibble";
...
}
Change this code to not invalidate iterators. For example:
for i in range(0, my_vector.len()) {
my_vector[2] = "wibble";
...
}
The `for-loop-does-not-borrow-iterators` test for #8372 was incorrect
and has been removed.
Closes#16820.
[breaking-change]
This code used to produce an ICE on the definition of trait Bar
with the following message:
Type parameter out of range when substituting in region 'a (root
type=fn(Self) -> 'astr) (space=FnSpace, index=0)
Closes#16218.
- Ensures the propagated negation sign is properly utilized during type
checking.
- Removed redundant type checking, specifically regarding the out of bounds checking
on a bounded type.
- Closes#16684
closes#16800
r? @nikomatsakis - I'm not 100% sure this is the right approach, it is kind of ad-hoc. The trouble is we don't have any intrinsic notion of which types are sized and which are not, we only have the Sized bound, so I have nothing to validate the Sized bound against.
Not sure if this is addressing the root cause or just patching up a symptom. Also not sure if I should be adding a diagnostic code for this.
Fixes#16750Fixes#15812
This adds support for lint groups to the compiler. Lint groups are a way of
grouping a number of lints together under one name. For example, this also
defines a default lint for naming conventions, named `bad_style`. Writing
`#[allow(bad_style)]` is equivalent to writing
`#[allow(non_camel_case_types, non_snake_case, non_uppercase_statics)]`. These
lint groups can also be defined as a compiler plugin using the new
`Registry::register_lint_group` method.
This also adds two built-in lint groups, `bad_style` and `unused`. The contents
of these groups can be seen by running `rustc -W help`.
This unifies the `non_snake_case_functions` and `uppercase_variables` lints
into one lint, `non_snake_case`. It also now checks for non-snake-case modules.
This also extends the non-camel-case types lint to check type parameters, and
merges the `non_uppercase_pattern_statics` lint into the
`non_uppercase_statics` lint.
Because the `uppercase_variables` lint is now part of the `non_snake_case`
lint, all non-snake-case variables that start with lowercase characters (such
as `fooBar`) will now trigger the `non_snake_case` lint.
New code should be updated to use the new `non_snake_case` lint instead of the
previous `non_snake_case_functions` and `uppercase_variables` lints. All use of
the `non_uppercase_pattern_statics` should be replaced with the
`non_uppercase_statics` lint. Any code that previously contained non-snake-case
module or variable names should be updated to use snake case names or disable
the `non_snake_case` lint. Any code with non-camel-case type parameters should
be changed to use camel case or disable the `non_camel_case_types` lint.
[breaking-change]
The inference scheme proposed in <http://smallcultfollowing.com/babysteps/blog/2014/07/09/an-experimental-new-type-inference-scheme-for-rust/>.
This is theoretically a [breaking-change]. It is possible that you may encounter type checking errors, particularly related to closures or functions with higher-ranked lifetimes or object types. Adding more explicit type annotations should help the problem. However, I have not been able to make an example that *actually* successfully compiles with the older scheme and fails with the newer scheme.
f? @pcwalton, @pnkfelix
This squashes the
> `for` loop expression has type `[type error]` which does not implement
> the `Iterator` trait
message that one received when writing `for ... in x` where was
previously found to have a type error.
Fixes#16042.
For review. Not sure about the link_attrs stuff. Will work on converting all the tests.
extern crate "foobar" as foo;
extern crate foobar as foo;
Implements remaining part of RFC #47.
Addresses issue #16461.
Removed link_attrs from rust.md, they don't appear to be supported by
the parser.
[breaking-change]
1. The internal layout for traits has changed from (vtable, data) to (data, vtable). If you were relying on this in unsafe transmutes, you might get some very weird and apparently unrelated errors. You should not be doing this! Prefer not to do this at all, but if you must, you should use raw::TraitObject rather than hardcoding rustc's internal representation into your code.
2. The minimal type of reference-to-vec-literals (e.g., `&[1, 2, 3]`) is now a fixed size vec (e.g., `&[int, ..3]`) where it used to be an unsized vec (e.g., `&[int]`). If you want the unszied type, you must explicitly give the type (e.g., `let x: &[_] = &[1, 2, 3]`). Note in particular where multiple blocks must have the same type (e.g., if and else clauses, vec elements), the compiler will not coerce to the unsized type without a hint. E.g., `[&[1], &[1, 2]]` used to be a valid expression of type '[&[int]]'. It no longer type checks since the first element now has type `&[int, ..1]` and the second has type &[int, ..2]` which are incompatible.
3. The type of blocks (including functions) must be coercible to the expected type (used to be a subtype). Mostly this makes things more flexible and not less (in particular, in the case of coercing function bodies to the return type). However, in some rare cases, this is less flexible. TBH, I'm not exactly sure of the exact effects. I think the change causes us to resolve inferred type variables slightly earlier which might make us slightly more restrictive. Possibly it only affects blocks with unreachable code. E.g., `if ... { fail!(); "Hello" }` used to type check, it no longer does. The fix is to add a semicolon after the string.
The privacy pass of the compiler was previously not taking into account the
privacy of foreign items, or bindings to external functions. This commit fixes
this oversight by encoding the visibility of foreign items into the metadata for
each crate.
Any code relying on this will start to fail to compile and the bindings must be
marked with `pub` to indicate that they can be used externally.
Closes#16725
[breaking-change]
Implements remaining part of RFC #47.
Addresses issue #16461.
Removed link_attrs from rust.md, they don't appear to be supported by
the parser.
Changed all the tests to use the new extern crate syntax
Change pretty printer to use 'as' syntax
int/uint aren't considered FFI safe, replace them with the actual type they
represent (i64/u64 or i32/u32). This is a breaking change, but at most a cast
to `uint` or `int` needs to be added.
[breaking-change]
As of RFC 18, struct layout is undefined. Opting into a C-compatible struct
layout is now down with #[repr(C)]. For consistency, specifying a packed
layout is now also down with #[repr(packed)]. Both can be specified.
To fix errors caused by this, just add #[repr(C)] to the structs, and change
#[packed] to #[repr(packed)]
Closes#14309
[breaking-change]
declared with the same name in the same scope.
This breaks several common patterns. First are unused imports:
use foo::bar;
use baz::bar;
Change this code to the following:
use baz::bar;
Second, this patch breaks globs that import names that are shadowed by
subsequent imports. For example:
use foo::*; // including `bar`
use baz::bar;
Change this code to remove the glob:
use foo::{boo, quux};
use baz::bar;
Or qualify all uses of `bar`:
use foo::{boo, quux};
use baz;
... baz::bar ...
Finally, this patch breaks code that, at top level, explicitly imports
`std` and doesn't disable the prelude.
extern crate std;
Because the prelude imports `std` implicitly, there is no need to
explicitly import it; just remove such directives.
The old behavior can be opted into via the `import_shadowing` feature
gate. Use of this feature gate is discouraged.
This implements RFC #116.
Closes#16464.
[breaking-change]
These `where` clauses are accepted everywhere generics are currently
accepted and desugar during type collection to the type parameter bounds
we have today.
A new keyword, `where`, has been added. Therefore, this is a breaking
change. Change uses of `where` to other identifiers.
[breaking-change]
r? @nikomatsakis (or whoever)
These `where` clauses are accepted everywhere generics are currently
accepted and desugar during type collection to the type parameter bounds
we have today.
A new keyword, `where`, has been added. Therefore, this is a breaking
change. Change uses of `where` to other identifiers.
[breaking-change]
This patch primarily does two things: (1) it prevents lifetimes from
leaking out of unboxed closures; (2) it allows unboxed closure type
notation, call notation, and construction notation to construct closures
matching any of the three traits.
This breaks code that looked like:
let mut f;
{
let x = &5i;
f = |&mut:| *x + 10;
}
Change this code to avoid having a reference escape. For example:
{
let x = &5i;
let mut f; // <-- move here to avoid dangling reference
f = |&mut:| *x + 10;
}
I believe this is enough to consider unboxed closures essentially
implemented. Further issues (for example, higher-rank lifetimes) should
be filed as followups.
Closes#14449.
[breaking-change]
This fixes borrow checking for closures. Code like this will break:
struct Foo {
x: int,
}
pub fn main() {
let mut this = &mut Foo {
x: 1,
};
let r = || {
let p = &this.x;
&mut this.x;
};
r()
}
Change this code to not take multiple mutable references to the same value. For
example:
struct Foo {
x: int,
}
pub fn main() {
let mut this = &mut Foo {
x: 1,
};
let r = || {
&mut this.x;
};
r()
}
Closes#16361.
[breaking-change]
r? @nikomatsakis
`for` loop heads.
This breaks code like:
let x = Some(box 1i);
for &a in x.iter() {
}
Change this code to obey the borrow checking rules. For example:
let x = Some(box 1i);
for &ref a in x.iter() {
}
Closes#16205.
[breaking-change]
r? @nikomatsakis
`for` loop heads.
This breaks code like:
let x = Some(box 1i);
for &a in x.iter() {
}
Change this code to obey the borrow checking rules. For example:
let x = Some(box 1i);
for &ref a in x.iter() {
}
Closes#16205.
[breaking-change]
Previously the stability lint considered cross-crate items only. That's appropriate for unstable and experimental levels, but not for deprecation.
In addition to changing the lint, this PR takes care of the fallout: a number of deprecated items that were being used throughout libstd.
Closes#16409
Due to deny(deprecated), this is a:
[breaking-change]
This fixes borrow checking for closures. Code like this will break:
struct Foo {
x: int,
}
pub fn main() {
let mut this = &mut Foo {
x: 1,
};
let r = || {
let p = &this.x;
&mut this.x;
};
r()
}
Change this code to not take multiple mutable references to the same value. For
example:
struct Foo {
x: int,
}
pub fn main() {
let mut this = &mut Foo {
x: 1,
};
let r = || {
&mut this.x;
};
r()
}
Closes#16361.
[breaking-change]
Previously the lint considered cross-crate items only. That's
appropriate for unstable and experimental levels, but not for
deprecation.
Closes#16409
Due to deny(deprecation), this is a:
[breaking-change]
The fail macro defines some function/static items internally, which got
a dead_code warning when `fail!()` is used inside a dead function. This
is ugly and unnecessarily reveals implementation details, so the
warnings can be squashed.
Fixes#16192.
The fail macro defines some function/static items internally, which got
a dead_code warning when `fail!()` is used inside a dead function. This
is ugly and unnecessarily reveals implementation details, so the
warnings can be squashed.
Fixes#16192.
This requires avoiding `quote_...!` for constructing the parts of the
__test module, since that stringifies and reinterns the idents, losing
the special gensym'd nature of them. (#15962.)
This leaves the `Share` trait at `std::kinds` via a `#[deprecated]` `pub use`
statement, but the `NoShare` struct is no longer part of `std::kinds::marker`
due to #12660 (the build cannot bootstrap otherwise).
All code referencing the `Share` trait should now reference the `Sync` trait,
and all code referencing the `NoShare` type should now reference the `NoSync`
type. The functionality and meaning of this trait have not changed, only the
naming.
Closes#16281
[breaking-change]
This leaves the `Share` trait at `std::kinds` via a `#[deprecated]` `pub use`
statement, but the `NoShare` struct is no longer part of `std::kinds::marker`
due to #12660 (the build cannot bootstrap otherwise).
All code referencing the `Share` trait should now reference the `Sync` trait,
and all code referencing the `NoShare` type should now reference the `NoSync`
type. The functionality and meaning of this trait have not changed, only the
naming.
Closes#16281
[breaking-change]
This requires avoiding `quote_...!` for constructing the parts of the
__test module, since that stringifies and reinterns the idents, losing
the special gensym'd nature of them. (#15962.)
meaning `'b outlives 'a`. Syntax currently does nothing but is needed for full
fix to #5763. To use this syntax, the issue_5763_bootstrap feature guard is
required.
This commit stabilizes the `std::sync::atomics` module, renaming it to
`std::sync::atomic` to match library precedent elsewhere, and tightening
up behavior around incorrect memory ordering annotations.
The vast majority of the module is now `stable`. However, the
`AtomicOption` type has been deprecated, since it is essentially unused
and is not truly a primitive atomic type. It will eventually be replaced
by a higher-level abstraction like MVars.
Due to deprecations, this is a:
[breaking-change]
Generic extern functions written in Rust have their names mangled, as well as their internal clownshoe __rust_abi functions. This allows e.g. specific monomorphizations of these functions to be used as callbacks.
Closes#12502.
The `type_overflow` lint, doesn't catch the overflow for `i64` because
the overflow happens earlier in the parse phase when the `u64` as biggest
possible int gets casted to `i64` , without checking the for overflows.
We can't lint in the parse phase, so a refactoring of the `LitInt` type
was necessary.
The types `LitInt`, `LitUint` and `LitIntUnsuffixed` where merged to one
type `LitInt` which stores it's value as `u64`. An additional parameter was
added which indicate the signedness of the type and the sign of the value.
This commit stabilizes the `std::sync::atomics` module, renaming it to
`std::sync::atomic` to match library precedent elsewhere, and tightening
up behavior around incorrect memory ordering annotations.
The vast majority of the module is now `stable`. However, the
`AtomicOption` type has been deprecated, since it is essentially unused
and is not truly a primitive atomic type. It will eventually be replaced
by a higher-level abstraction like MVars.
Due to deprecations, this is a:
[breaking-change]
This is an alternative to upgrading the way rvalues are handled in the
borrow check. Making rvalues handled more like lvalues in the borrow
check caused numerous problems related to double mutable borrows and
rvalue scopes. Rather than come up with more borrow check rules to try
to solve these problems, I decided to just forbid pattern bindings after
`@`. This affected fewer than 10 lines of code in the compiler and
libraries.
This breaks code like:
match x {
y @ z => { ... }
}
match a {
b @ Some(c) => { ... }
}
Change this code to use nested `match` or `let` expressions. For
example:
match x {
y => {
let z = y;
...
}
}
match a {
Some(c) => {
let b = Some(c);
...
}
}
Closes#14587.
[breaking-change]
Remove the ability of the borrow checker to determine that repeated
dereferences of a Box<T> refer to the same memory object. This will
usually require one of two workarounds:
1) The interior of a Box<T> will sometimes need to be moved / borrowed
into a temporary before moving / borrowing individual derived paths.
2) A `ref x` pattern will have to be replaced with a `box ref x`
pattern.
Fixes#16094.
[breaking-change]
the CFG for match statements.
There were two bugs in issue #14684. One was simply that the borrow
check didn't know about the correct CFG for match statements: the
pattern must be a predecessor of the guard. This disallows the bad
behavior if there are bindings in the pattern. But it isn't enough to
prevent the memory safety problem, because of wildcards; thus, this
patch introduces a more restrictive rule, which disallows assignments
and mutable borrows inside guards outright.
I discussed this with Niko and we decided this was the best plan of
action.
This breaks code that performs mutable borrows in pattern guards. Most
commonly, the code looks like this:
impl Foo {
fn f(&mut self, ...) {}
fn g(&mut self, ...) {
match bar {
Baz if self.f(...) => { ... }
_ => { ... }
}
}
}
Change this code to not use a guard. For example:
impl Foo {
fn f(&mut self, ...) {}
fn g(&mut self, ...) {
match bar {
Baz => {
if self.f(...) {
...
} else {
...
}
}
_ => { ... }
}
}
}
Sometimes this can result in code duplication, but often it illustrates
a hidden memory safety problem.
Closes#14684.
[breaking-change]
r? @pnkfelix
This commit applies stability attributes to the contents of these modules,
summarized here:
* The `unit` and `bool` modules have become #[unstable] as they are purely meant
for documentation purposes and are candidates for removal.
* The `ty` module has been deprecated, and the inner `Unsafe` type has been
renamed to `UnsafeCell` and moved to the `cell` module. The `marker1` field
has been removed as the compiler now always infers `UnsafeCell` to be
invariant. The `new` method i stable, but the `value` field, `get` and
`unwrap` methods are all unstable.
* The `tuple` module has its name as stable, the naming of the `TupleN` traits
as stable while the methods are all #[unstable]. The other impls in the module
have appropriate stability for the corresponding trait.
* The `arc` module has received the exact same treatment as the `rc` module
previously did.
* The `any` module has its name as stable. The `Any` trait is also stable, with
a new private supertrait which now contains the `get_type_id` method. This is
to make the method a private implementation detail rather than a public-facing
detail.
The two extension traits in the module are marked #[unstable] as they will not
be necessary with DST. The `is` method is #[stable], the as_{mut,ref} methods
have been renamed to downcast_{mut,ref} and are #[unstable].
The extension trait `BoxAny` has been clarified as to why it is unstable as it
will not be necessary with DST.
This is a breaking change because the `marker1` field was removed from the
`UnsafeCell` type. To deal with this change, you can simply delete the field and
only specify the value of the `data` field in static initializers.
[breaking-change]
Rename and gensym the runtime on import, so that users
can't refer to the `native` crate.
This is unlikely to break code, but users should import the "native" crate directly.
[breaking-change]
cc @alexcrichton
the CFG for match statements.
There were two bugs in issue #14684. One was simply that the borrow
check didn't know about the correct CFG for match statements: the
pattern must be a predecessor of the guard. This disallows the bad
behavior if there are bindings in the pattern. But it isn't enough to
prevent the memory safety problem, because of wildcards; thus, this
patch introduces a more restrictive rule, which disallows assignments
and mutable borrows inside guards outright.
I discussed this with Niko and we decided this was the best plan of
action.
This breaks code that performs mutable borrows in pattern guards. Most
commonly, the code looks like this:
impl Foo {
fn f(&mut self, ...) {}
fn g(&mut self, ...) {
match bar {
Baz if self.f(...) => { ... }
_ => { ... }
}
}
}
Change this code to not use a guard. For example:
impl Foo {
fn f(&mut self, ...) {}
fn g(&mut self, ...) {
match bar {
Baz => {
if self.f(...) {
...
} else {
...
}
}
_ => { ... }
}
}
}
Sometimes this can result in code duplication, but often it illustrates
a hidden memory safety problem.
Closes#14684.
[breaking-change]
method calls are involved.
This breaks code like:
impl<T:Copy> Foo for T { ... }
fn take_param<T:Foo>(foo: &T) { ... }
fn main() {
let x = box 3i; // note no `Copy` bound
take_param(&x);
}
Change this code to not contain a type error. For example:
impl<T:Copy> Foo for T { ... }
fn take_param<T:Foo>(foo: &T) { ... }
fn main() {
let x = 3i; // satisfies `Copy` bound
take_param(&x);
}
Closes#15860.
[breaking-change]
r? @alexcrichton
method calls are involved.
This breaks code like:
impl<T:Copy> Foo for T { ... }
fn take_param<T:Foo>(foo: &T) { ... }
fn main() {
let x = box 3i; // note no `Copy` bound
take_param(&x);
}
Change this code to not contain a type error. For example:
impl<T:Copy> Foo for T { ... }
fn take_param<T:Foo>(foo: &T) { ... }
fn main() {
let x = 3i; // satisfies `Copy` bound
take_param(&x);
}
Closes#15860.
[breaking-change]
librustc: Stop desugaring `for` expressions and translate them directly.
This makes edge cases in which the `Iterator` trait was not in scope
and/or `Option` or its variants were not in scope work properly.
This breaks code that looks like:
struct MyStruct { ... }
impl MyStruct {
fn next(&mut self) -> Option<int> { ... }
}
for x in MyStruct { ... } { ... }
Change ad-hoc `next` methods like the above to implementations of the
`Iterator` trait. For example:
impl Iterator<int> for MyStruct {
fn next(&mut self) -> Option<int> { ... }
}
Closes#15392.
[breaking-change]
This makes edge cases in which the `Iterator` trait was not in scope
and/or `Option` or its variants were not in scope work properly.
This breaks code that looks like:
struct MyStruct { ... }
impl MyStruct {
fn next(&mut self) -> Option<int> { ... }
}
for x in MyStruct { ... } { ... }
Change ad-hoc `next` methods like the above to implementations of the
`Iterator` trait. For example:
impl Iterator<int> for MyStruct {
fn next(&mut self) -> Option<int> { ... }
}
Closes#15392.
[breaking-change]
This implements RFC 39. Omitted lifetimes in return values will now be
inferred to more useful defaults, and an error is reported if a lifetime
in a return type is omitted and one of the two lifetime elision rules
does not specify what it should be.
This primarily breaks two uncommon code patterns. The first is this:
unsafe fn get_foo_out_of_thin_air() -> &Foo {
...
}
This should be changed to:
unsafe fn get_foo_out_of_thin_air() -> &'static Foo {
...
}
The second pattern that needs to be changed is this:
enum MaybeBorrowed<'a> {
Borrowed(&'a str),
Owned(String),
}
fn foo() -> MaybeBorrowed {
Owned(format!("hello world"))
}
Change code like this to:
enum MaybeBorrowed<'a> {
Borrowed(&'a str),
Owned(String),
}
fn foo() -> MaybeBorrowed<'static> {
Owned(format!("hello world"))
}
Closes#15552.
[breaking-change]
r? @nick29581
This is accomplished by rewriting static expressions into equivalent patterns.
This way, patterns referencing static variables can both participate
in exhaustiveness analysis as well as be compiled down into the appropriate
branch of the decision trees that match expressions are codegened to.
Fixes#6533.
Fixes#13626.
Fixes#13731.
Fixes#14576.
Fixes#15393.
This implements RFC 39. Omitted lifetimes in return values will now be
inferred to more useful defaults, and an error is reported if a lifetime
in a return type is omitted and one of the two lifetime elision rules
does not specify what it should be.
This primarily breaks two uncommon code patterns. The first is this:
unsafe fn get_foo_out_of_thin_air() -> &Foo {
...
}
This should be changed to:
unsafe fn get_foo_out_of_thin_air() -> &'static Foo {
...
}
The second pattern that needs to be changed is this:
enum MaybeBorrowed<'a> {
Borrowed(&'a str),
Owned(String),
}
fn foo() -> MaybeBorrowed {
Owned(format!("hello world"))
}
Change code like this to:
enum MaybeBorrowed<'a> {
Borrowed(&'a str),
Owned(String),
}
fn foo() -> MaybeBorrowed<'static> {
Owned(format!("hello world"))
}
Closes#15552.
[breaking-change]
The first is to require that `#[crate_name]` and `--crate-name` always match (if both are specified). The second is to fix parallel compilation in cargo by mixing in `-C extra-filename` into the temporary outputs of the compiler.
When invoking the compiler in parallel, the intermediate output of the object
files and bytecode can stomp over one another if two crates with the same name
are being compiled.
The output file is already being disambiguated with `-C extra-filename`, so this
commit alters the naming of the temporary files to also mix in the extra
filename to ensure that file names don't clash.
This is accomplished by rewriting static expressions into equivalent patterns.
This way, patterns referencing static variables can both participate
in exhaustiveness analysis as well as be compiled down into the appropriate
branch of the decision trees that match expressions are codegened to.
Fixes#6533.
Fixes#13626.
Fixes#13731.
Fixes#14576.
Fixes#15393.
Part of the original discussions around the `--crate-name` flag brought up that
mass confusion can arise when the flag specifies a different name than is
contained in the crate.
The current primary use case of the `--crate-name` flag is through cargo and
not requiring a `#[crate_name]` attribute, but if the `#[crate_name]` attribute
is specified it will likely go awry when the two names deviate from one another.
This commit requires that if both are provided they both match to prevent this
confusion.
Importing from types was disallowed in #6462. Flag was set for paths whether it is a module or a type. Type flag was set when impl was seen. The problem is, for cross-crate situations, when reexport is involved, it is possible that impl is seen too late because metadata is loaded lazily.
Fix#15664.
This small patch causes the stability lint to bail out when traversing
any AST produced via a macro expansion. Ultimately, we would like to
lint the contents of the macro at the place where the macro is defined,
but regardless we should not be linting it at the use site.
Closes#15703
except where trait objects are involved.
Part of issue #15349, though I'm leaving it open for trait objects.
Cross borrowing for trait objects remains because it is needed until we
have DST.
This will break code like:
fn foo(x: &int) { ... }
let a = box 3i;
foo(a);
Change this code to:
fn foo(x: &int) { ... }
let a = box 3i;
foo(&*a);
[breaking-change]
This makes two changes to region inference: (1) it allows region
inference to relate early-bound regions; and (2) it allows regions to be
related before variance runs. The former is needed because there is no
relation between the two regions before region substitution happens,
while the latter is needed because type collection has to run before
variance. We assume that, before variance is inferred, that lifetimes
are invariant. This is a conservative overapproximation.
This relates to #13885. This does not remove `~self` from the language
yet, however.
[breaking-change]
This small patch causes the stability lint to bail out when traversing
any AST produced via a macro expansion. Ultimately, we would like to
lint the contents of the macro at the place where the macro is defined,
but regardless we should not be linting it at the use site.
Closes#15703
Closes#15525
The important bit of this are the changes from line 445 in mem_categorization.rs. Most of the other changes are about adding an Implicit PointerKind, and this is only necessary for getting a decent error message :-s An alternative would have been to add an implciti/explicit flag to cat_deref, which could be mostly ignored and so would mean much fewer changes. However, the implicit state would only be valid if the PointerKind was BorrowedPtr, so it felt like it ought to be another kind of PointerKind. I still don't know which is the better design.
This PR is the outcome of the library stabilization meeting for the
`liballoc::owned` and `libcore::cell` modules.
Aside from the stability attributes, there are a few breaking changes:
* The `owned` modules is now named `boxed`, to better represent its
contents. (`box` was unavailable, since it's a keyword.) This will
help avoid the misconception that `Box` plays a special role wrt
ownership.
* The `AnyOwnExt` extension trait is renamed to `BoxAny`, and its `move`
method is renamed to `downcast`, in both cases to improve clarity.
* The recently-added `AnySendOwnExt` extension trait is removed; it was
not being used and is unnecessary.
[breaking-change]
This PR is the outcome of the library stabilization meeting for the
`liballoc::owned` and `libcore::cell` modules.
Aside from the stability attributes, there are a few breaking changes:
* The `owned` modules is now named `boxed`, to better represent its
contents. (`box` was unavailable, since it's a keyword.) This will
help avoid the misconception that `Box` plays a special role wrt
ownership.
* The `AnyOwnExt` extension trait is renamed to `BoxAny`, and its `move`
method is renamed to `downcast`, in both cases to improve clarity.
* The recently-added `AnySendOwnExt` extension trait is removed; it was
not being used and is unnecessary.
[breaking-change]
* Don't warn about `#[crate_name]` if `--crate-name` is specified
* Don't warn about non camel case identifiers on `#[repr(C)]` structs
* Switch `mode` to `mode_t` in libc.
This is a continuation of @brson's work from https://github.com/rust-lang/rust/pull/12144.
This implements the minimal scaffolding that allows mapping diagnostic messages to alpha-numeric codes, which could improve the searchability of errors. In addition, there's a new compiler option, `--explain {code}` which takes an error code and prints out a somewhat detailed explanation of the error. Example:
```rust
fn f(x: Option<bool>) {
match x {
Some(true) | Some(false) => (),
None => (),
Some(true) => ()
}
}
```
```shell
[~/rust]$ ./build/x86_64-apple-darwin/stage2/bin/rustc ./diagnostics.rs --crate-type dylib
diagnostics.rs:5:3: 5:13 error: unreachable pattern [E0001] (pass `--explain E0001` to see a detailed explanation)
diagnostics.rs:5 Some(true) => ()
^~~~~~~~~~
error: aborting due to previous error
[~/rust]$ ./build/x86_64-apple-darwin/stage2/bin/rustc --explain E0001
This error suggests that the expression arm corresponding to the noted pattern
will never be reached as for all possible values of the expression being matched,
one of the preceeding patterns will match.
This means that perhaps some of the preceeding patterns are too general, this
one is too specific or the ordering is incorrect.
```
I've refrained from migrating many errors to actually use the new macros as it can be done in an incremental fashion but if we're happy with the approach, it'd be good to do all of them sooner rather than later.
Originally, I was going to make libdiagnostics a separate crate but that's posing some interesting challenges with semi-circular dependencies. In particular, librustc would have a plugin-phase dependency on libdiagnostics, which itself depends on librustc. Per my conversation with @alexcrichton, it seems like the snapshotting process would also have to change. So for now the relevant modules from libdiagnostics are included using `#[path = ...] mod`.
C structs predominately do not use camel case identifiers, and we have a clear
indicator for what's a C struct now, so excuse all of them from this stylistic
lint.
Similar to the stability attributes, a type annotated with `#[must_use =
"informative snippet"]` will print the normal warning message along with
"informative snippet". This allows the type author to provide some
guidance about why the type should be used.
---
It can be a little unintuitive that something like `v.iter().map(|x|
println!("{}", x));` does nothing: the majority of the iterator adaptors
are lazy and do not execute anything until something calls `next`, e.g.
a `for` loop, `collect`, `fold`, etc.
The majority of such errors can be seen by someone writing something
like the above, i.e. just calling an iterator adaptor and doing nothing
with it (and doing this is certainly useless), so we can co-opt the
`must_use` lint, using the message functionality to give a hint to the
reason why.
Fixes#14666.
Similar to the stability attributes, a type annotated with `#[must_use =
"informative snippet"]` will print the normal warning message along with
"informative snippet". This allows the type author to provide some
guidance about why the type should be used.
This updates https://github.com/rust-lang/rust/pull/15075.
Rename `ToStr::to_str` to `ToString::to_string`. The naive renaming ends up with two `to_string` functions defined on strings in the prelude (the other defined via `collections::str::StrAllocating`). To remedy this I removed `StrAllocating::to_string`, making all conversions from `&str` to `String` go through `Show`. This has a measurable impact on the speed of this conversion, but the sense I get from others is that it's best to go ahead and unify `to_string` and address performance for all `to_string` conversions in `core::fmt`. `String::from_str(...)` still works as a manual fast-path.
Note that the patch was done with a script, and ended up renaming a number of other `*_to_str` functions, particularly inside of rustc. All the ones I saw looked correct, and I didn't notice any additional API breakage.
Closes#15046.
closes#13367
[breaking-change] Use `Sized?` to indicate a dynamically sized type parameter or trait (used to be `type`). E.g.,
```
trait Tr for Sized? {}
fn foo<Sized? X: Share>(x: X) {}
```
This will break code that looks like:
struct Foo {
...
}
mod Foo {
...
}
Change this code to:
struct Foo {
...
}
impl Foo {
...
}
Or rename the module.
Closes#15205.
[breaking-change]
r? @nick29581
This will break code that used the old `Index` trait. Change this code
to use the new `Index` traits. For reference, here are their signatures:
pub trait Index<Index,Result> {
fn index<'a>(&'a self, index: &Index) -> &'a Result;
}
pub trait IndexMut<Index,Result> {
fn index_mut<'a>(&'a mut self, index: &Index) -> &'a mut Result;
}
Closes#6515.
[breaking-change]
r? @nick29581
This will break code that used the old `Index` trait. Change this code
to use the new `Index` traits. For reference, here are their signatures:
pub trait Index<Index,Result> {
fn index<'a>(&'a self, index: &Index) -> &'a Result;
}
pub trait IndexMut<Index,Result> {
fn index_mut<'a>(&'a mut self, index: &Index) -> &'a mut Result;
}
Closes#6515.
[breaking-change]
This will break code that looks like:
struct Foo {
...
}
mod Foo {
...
}
Change this code to:
struct Foo {
...
}
impl Foo {
...
}
Or rename the module.
Closes#15205.
[breaking-change]
This was parsed by the parser but completely ignored; not even stored in
the AST!
This breaks code that looks like:
static X: &'static [u8] = &'static [1, 2, 3];
Change this code to the shorter:
static X: &'static [u8] = &[1, 2, 3];
Closes#15312.
[breaking-change]
parameters.
This can break code that mistakenly used type parameters in place of
`Self`. For example, this will break:
trait Foo {
fn bar<X>(u: X) -> Self {
u
}
}
Change this code to not contain a type error. For example:
trait Foo {
fn bar<X>(_: X) -> Self {
self
}
}
Closes#15172.
[breaking-change]
r? @alexcrichton
This can break code that looked like:
struct S<T> {
val: T,
}
trait Gettable<T> {
...
}
impl<T: Copy> Gettable<T> for S<T> {
...
}
let t: Box<S<String>> = box S {
val: "one".to_string(),
};
let a = t as Box<Gettable<String>>;
// ^ note no `Copy` bound
Change this code to:
impl<T> Gettable<T> for S<T> {
// ^ remove `Copy` bound
...
}
Closes#14061.
[breaking-change]
with the corresponding trait parameter bounds.
This is a version of the patch in PR #12611 by Florian Hahn, modified to
address Niko's feedback.
It does not address the issue of duplicate type parameter bounds, nor
does it address the issue of implementation-defined methods that contain
*fewer* bounds than the trait, because Niko's review indicates that this
should not be necessary (and indeed I believe it is not). A test has
been added to ensure that this works.
This will break code like:
trait Foo {
fn bar<T:Baz>();
}
impl Foo for Boo {
fn bar<T:Baz + Quux>() { ... }
// ^~~~ ERROR
}
This will be rejected because the implementation requires *more* bounds
than the trait. It can be fixed by either adding the missing bound to
the trait:
trait Foo {
fn bar<T:Baz + Quux>();
// ^~~~
}
impl Foo for Boo {
fn bar<T:Baz + Quux>() { ... } // OK
}
Or by removing the bound from the impl:
trait Foo {
fn bar<T:Baz>();
}
impl Foo for Boo {
fn bar<T:Baz>() { ... } // OK
// ^ remove Quux
}
This patch imports the relevant tests from #2687, as well as the test
case in #5886, which is fixed as well by this patch.
Closes#2687.
Closes#5886.
[breaking-change]
r? @pnkfelix
parameters.
This can break code that mistakenly used type parameters in place of
`Self`. For example, this will break:
trait Foo {
fn bar<X>(u: X) -> Self {
u
}
}
Change this code to not contain a type error. For example:
trait Foo {
fn bar<X>(_: X) -> Self {
self
}
}
Closes#15172.
[breaking-change]
Slice patterns are different from the rest in that a single slice pattern
does not have a distinct constructor if it contains a variable-length subslice
pattern. For example, the pattern [a, b, ..tail] can match a slice of length 2, 3, 4
and so on.
As a result, the decision tree for exhaustiveness and redundancy analysis should
explore each of those constructors separately to determine if the pattern could be useful
when specialized for any of them.
with the corresponding trait parameter bounds.
This is a version of the patch in PR #12611 by Florian Hahn, modified to
address Niko's feedback.
It does not address the issue of duplicate type parameter bounds, nor
does it address the issue of implementation-defined methods that contain
*fewer* bounds than the trait, because Niko's review indicates that this
should not be necessary (and indeed I believe it is not). A test has
been added to ensure that this works.
This will break code like:
trait Foo {
fn bar<T:Baz>();
}
impl Foo for Boo {
fn bar<T:Baz + Quux>() { ... }
// ^~~~ ERROR
}
This will be rejected because the implementation requires *more* bounds
than the trait. It can be fixed by either adding the missing bound to
the trait:
trait Foo {
fn bar<T:Baz + Quux>();
// ^~~~
}
impl Foo for Boo {
fn bar<T:Baz + Quux>() { ... } // OK
}
Or by removing the bound from the impl:
trait Foo {
fn bar<T:Baz>();
}
impl Foo for Boo {
fn bar<T:Baz>() { ... } // OK
// ^ remove Quux
}
This patch imports the relevant tests from #2687, as well as the test
case in #5886, which is fixed as well by this patch.
Closes#2687.
Closes#5886.
[breaking-change]
Being able to index into the bytes of a string encourages
poor UTF-8 hygiene. To get a view of `&[u8]` from either
a `String` or `&str` slice, use the `as_bytes()` method.
Closes#12710.
[breaking-change]
I ended up altering the semantics of Json's PartialOrd implementation.
It used to be the case that Null < Null, but I can't think of any reason
for an ordering other than the default one so I just switched it over to
using the derived implementation.
This also fixes broken `PartialOrd` implementations for `Vec` and
`TreeMap`.
RFC: 0028-partial-cmp
floating point numbers for real.
This will break code that looks like:
let mut x = 0;
while ... {
x += 1;
}
println!("{}", x);
Change that code to:
let mut x = 0i;
while ... {
x += 1;
}
println!("{}", x);
Closes#15201.
[breaking-change]
This change registers new snapshots, allowing `*T` to be removed from the language. This is a large breaking change, and it is recommended that if compiler errors are seen that any FFI calls are audited to determine whether they should be actually taking `*mut T`.
I believe that #5781 got fixed by the DST work. It duplicated the
variance inference work in #12828. Therefore, all that is left in #5781
is adding a test.
Closes#5781.
r? @huonw
This can break code that looked like:
impl Foo for Box<Any> {
fn f(&self) { ... }
}
let x: Box<Any + Send> = ...;
x.f();
Change such code to:
impl Foo for Box<Any> {
fn f(&self) { ... }
}
let x: Box<Any> = ...;
x.f();
That is, upcast before calling methods.
This is a conservative solution to #5781. A more proper treatment (see
the xfail'd `trait-contravariant-self.rs`) would take variance into
account. This change fixes the soundness hole.
Some library changes had to be made to make this work. In particular,
`Box<Any>` is no longer showable, and only `Box<Any+Send>` is showable.
Eventually, this restriction can be lifted; for now, it does not prove
too onerous, because `Any` is only used for propagating the result of
task failure.
This patch also adds a test for the variance inference work in #12828,
which accidentally landed as part of DST.
Closes#5781.
[breaking-change]
Since procs do not have lifetime bounds, we must do this to maintain
safety.
This can break code that incorrectly captured references in procedure
types. Change such code to not do this, perhaps with a trait object
instead.
A better solution would be to add higher-rank lifetime support to procs.
However, this would be a lot of work for a feature we want to remove in
favor of unboxed closures. The corresponding "real fix" is #15067.
Closes#14036.
[breaking-change]
It turns out that bindings introduced by 'for' loops were not treated hygienically. The fix for this is to make the 'for' expansion more like a macro; rather than expanding sub-pieces and then assembling them, we need to rewrite the for and then call expand again on the whole thing.
This PR includes a test and the fix.
It also contains a number of other things:
- unit tests for other forms of hygiene (currently ignored)
- a fix for the isaac.rs macro that (it turned out) was relying on capturing
- other miscellaneous cleanup and comments