Skip to content

Commit

Permalink
Auto merge of #42264 - GuillaumeGomez:new-error-codes, r=Susurrus
Browse files Browse the repository at this point in the history
New error codes

Part of #42229.
  • Loading branch information
bors committed May 29, 2017
2 parents 5de0092 + 2969137 commit cb7c60f
Show file tree
Hide file tree
Showing 80 changed files with 344 additions and 185 deletions.
25 changes: 13 additions & 12 deletions src/librustc_borrowck/borrowck/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -701,7 +701,7 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
fn bckerr_to_diag(&self, err: &BckError<'tcx>) -> DiagnosticBuilder<'a> {
let span = err.span.clone();

let msg = match err.code {
match err.code {
err_mutbl => {
let descr = match err.cmt.note {
mc::NoteClosureEnv(_) | mc::NoteUpvarRef(_) => {
Expand All @@ -725,10 +725,11 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {

match err.cause {
MutabilityViolation => {
format!("cannot assign to {}", descr)
struct_span_err!(self.tcx.sess, span, E0594, "cannot assign to {}", descr)
}
BorrowViolation(euv::ClosureCapture(_)) => {
format!("closure cannot assign to {}", descr)
struct_span_err!(self.tcx.sess, span, E0595,
"closure cannot assign to {}", descr)
}
BorrowViolation(euv::OverloadedOperator) |
BorrowViolation(euv::AddrOf) |
Expand All @@ -737,7 +738,8 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
BorrowViolation(euv::AutoUnsafe) |
BorrowViolation(euv::ForLoop) |
BorrowViolation(euv::MatchDiscriminant) => {
format!("cannot borrow {} as mutable", descr)
struct_span_err!(self.tcx.sess, span, E0596,
"cannot borrow {} as mutable", descr)
}
BorrowViolation(euv::ClosureInvocation) => {
span_bug!(err.span,
Expand All @@ -752,17 +754,16 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
format!("`{}`", self.loan_path_to_string(&lp))
}
};
format!("{} does not live long enough", msg)
struct_span_err!(self.tcx.sess, span, E0597, "{} does not live long enough", msg)
}
err_borrowed_pointer_too_short(..) => {
let descr = self.cmt_to_path_or_string(&err.cmt);
format!("lifetime of {} is too short to guarantee \
its contents can be safely reborrowed",
descr)
struct_span_err!(self.tcx.sess, span, E0598,
"lifetime of {} is too short to guarantee \
its contents can be safely reborrowed",
descr)
}
};

self.struct_span_err(span, &msg)
}
}

pub fn report_aliasability_violation(&self,
Expand Down Expand Up @@ -1169,7 +1170,7 @@ before rustc 1.16, this temporary lived longer - see issue #39283 \
if kind == ty::ClosureKind::Fn {
db.span_help(self.tcx.hir.span(upvar_id.closure_expr_id),
"consider changing this closure to take \
self by mutable reference");
self by mutable reference");
}
}
_ => {
Expand Down
54 changes: 54 additions & 0 deletions src/librustc_borrowck/diagnostics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1114,9 +1114,63 @@ fn main() {
```
"##,

E0596: r##"
This error occurs because you tried to mutably borrow a non-mutable variable.
Example of erroneous code:
```compile_fail,E0596
let x = 1;
let y = &mut x; // error: cannot borrow mutably
```
In here, `x` isn't mutable, so when we try to mutably borrow it in `y`, it
fails. To fix this error, you need to make `x` mutable:
```
let mut x = 1;
let y = &mut x; // ok!
```
"##,

E0597: r##"
This error occurs because a borrow was made inside a variable which has a
greater lifetime than the borrowed one.
Example of erroneous code:
```compile_fail,E0597
struct Foo<'a> {
x: Option<&'a u32>,
}
let mut x = Foo { x: None };
let y = 0;
x.x = Some(&y); // error: `y` does not live long enough
```
In here, `x` is created before `y` and therefore has a greater lifetime. Always
keep in mind that values in a scope are dropped in the opposite order they are
created. So to fix the previous example, just make the `y` lifetime greater than
the `x`'s one:
```
struct Foo<'a> {
x: Option<&'a u32>,
}
let y = 0;
let mut x = Foo { x: None };
x.x = Some(&y);
```
"##,

}

register_diagnostics! {
// E0385, // {} in an aliasable location
E0524, // two closures require unique access to `..` at the same time
E0594, // cannot assign to {}
E0595, // closure cannot assign to {}
E0598, // lifetime of {} is too short to guarantee its contents can be...
}
27 changes: 15 additions & 12 deletions src/librustc_typeck/check/method/suggest.rs
Original file line number Diff line number Diff line change
Expand Up @@ -165,18 +165,21 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
.. }) => {
let tcx = self.tcx;

let mut err = self.type_error_struct(span,
|actual| {
format!("no {} named `{}` found for type `{}` in the current scope",
if mode == Mode::MethodCall {
"method"
} else {
"associated item"
},
item_name,
actual)
},
rcvr_ty);
let actual = self.resolve_type_vars_if_possible(&rcvr_ty);
let mut err = if !actual.references_error() {
struct_span_err!(tcx.sess, span, E0599,
"no {} named `{}` found for type `{}` in the \
current scope",
if mode == Mode::MethodCall {
"method"
} else {
"associated item"
},
item_name,
self.ty_to_string(actual))
} else {
self.tcx.sess.diagnostic().struct_dummy()
};

// If the method name is the name of a field with a function or closure type,
// give a helping note that it has to be called as (x.f)(...).
Expand Down
10 changes: 6 additions & 4 deletions src/librustc_typeck/check/op.rs
Original file line number Diff line number Diff line change
Expand Up @@ -316,10 +316,12 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
match self.lookup_op_method(ex, operand_ty, vec![], mname, trait_did, operand_expr) {
Ok(t) => t,
Err(()) => {
self.type_error_message(ex.span, |actual| {
format!("cannot apply unary operator `{}` to type `{}`",
op_str, actual)
}, operand_ty);
let actual = self.resolve_type_vars_if_possible(&operand_ty);
if !actual.references_error() {
struct_span_err!(self.tcx.sess, ex.span, E0600,
"cannot apply unary operator `{}` to type `{}`",
op_str, actual).emit();
}
self.tcx.types.err
}
}
Expand Down
55 changes: 54 additions & 1 deletion src/librustc_typeck/diagnostics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4005,7 +4005,7 @@ details.
[issue #33685]: https://github.com/rust-lang/rust/issues/33685
"##,

E0582: r##"
E0582: r##"
A lifetime appears only in an associated-type binding,
and not in the input types to the trait.
Expand Down Expand Up @@ -4042,6 +4042,59 @@ details.
[issue #33685]: https://github.com/rust-lang/rust/issues/33685
"##,

E0599: r##"
```compile_fail,E0599
struct Mouth;
let x = Mouth;
x.chocolate(); // error: no method named `chocolate` found for type `Mouth`
// in the current scope
```
"##,

E0600: r##"
An unary operator was used on a type which doesn't implement it.
Example of erroneous code:
```compile_fail,E0600
enum Question {
Yes,
No,
}
!Question::Yes; // error: cannot apply unary operator `!` to type `Question`
```
In this case, `Question` would need to implement the `std::ops::Not` trait in
order to be able to use `!` on it. Let's implement it:
```
use std::ops::Not;
enum Question {
Yes,
No,
}
// We implement the `Not` trait on the enum.
impl Not for Question {
type Output = bool;
fn not(self) -> bool {
match self {
Question::Yes => false, // If the `Answer` is `Yes`, then it
// returns false.
Question::No => true, // And here we do the opposite.
}
}
}
assert_eq!(!Question::Yes, false);
assert_eq!(!Question::No, true);
```
"##,

}

register_diagnostics! {
Expand Down
14 changes: 14 additions & 0 deletions src/test/compile-fail/E0596.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

fn main() {
let x = 1;
let y = &mut x; //~ ERROR E0596
}
19 changes: 19 additions & 0 deletions src/test/compile-fail/E0597.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

struct Foo<'a> {
x: Option<&'a u32>,
}

fn main() {
let mut x = Foo { x: None };
let y = 0;
x.x = Some(&y);
} //~ `y` does not live long enough [E0597]
13 changes: 13 additions & 0 deletions src/test/compile-fail/E0600.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

fn main() {
!"a"; //~ ERROR E0600
}
2 changes: 1 addition & 1 deletion src/test/ui/codemap_tests/huge_multispan_highlight.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable local variable `x` as mutable
error[E0596]: cannot borrow immutable local variable `x` as mutable
--> $DIR/huge_multispan_highlight.rs:100:18
|
12 | let x = "foo";
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/codemap_tests/issue-28308.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot apply unary operator `!` to type `&'static str`
error[E0600]: cannot apply unary operator `!` to type `&'static str`
--> $DIR/issue-28308.rs:12:5
|
12 | assert!("foo");
Expand Down
4 changes: 2 additions & 2 deletions src/test/ui/did_you_mean/issue-31424.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable argument `self` as mutable
error[E0596]: cannot borrow immutable argument `self` as mutable
--> $DIR/issue-31424.rs:17:15
|
17 | (&mut self).bar();
Expand All @@ -7,7 +7,7 @@ error: cannot borrow immutable argument `self` as mutable
| try removing `&mut` here
| cannot reborrow mutably

error: cannot borrow immutable argument `self` as mutable
error[E0596]: cannot borrow immutable argument `self` as mutable
--> $DIR/issue-31424.rs:23:15
|
22 | fn bar(self: &mut Self) {
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/did_you_mean/issue-34126.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable argument `self` as mutable
error[E0596]: cannot borrow immutable argument `self` as mutable
--> $DIR/issue-34126.rs:16:23
|
16 | self.run(&mut self);
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/did_you_mean/issue-34337.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable local variable `key` as mutable
error[E0596]: cannot borrow immutable local variable `key` as mutable
--> $DIR/issue-34337.rs:16:14
|
16 | get(&mut key);
Expand Down
6 changes: 3 additions & 3 deletions src/test/ui/did_you_mean/issue-35937.stderr
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
error: cannot borrow immutable field `f.v` as mutable
error[E0596]: cannot borrow immutable field `f.v` as mutable
--> $DIR/issue-35937.rs:17:5
|
16 | let f = Foo { v: Vec::new() };
| - consider changing this to `mut f`
17 | f.v.push("cat".to_string());
| ^^^ cannot mutably borrow immutable field

error: cannot assign to immutable field `s.x`
error[E0594]: cannot assign to immutable field `s.x`
--> $DIR/issue-35937.rs:26:5
|
25 | let s = S { x: 42 };
| - consider changing this to `mut s`
26 | s.x += 1;
| ^^^^^^^^ cannot mutably borrow immutable field

error: cannot assign to immutable field `s.x`
error[E0594]: cannot assign to immutable field `s.x`
--> $DIR/issue-35937.rs:30:5
|
29 | fn bar(s: S) {
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/did_you_mean/issue-37139.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable local variable `x` as mutable
error[E0596]: cannot borrow immutable local variable `x` as mutable
--> $DIR/issue-37139.rs:22:23
|
22 | test(&mut x);
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/did_you_mean/issue-38147-2.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable borrowed content `*self.s` as mutable
error[E0596]: cannot borrow immutable borrowed content `*self.s` as mutable
--> $DIR/issue-38147-2.rs:17:9
|
12 | s: &'a String
Expand Down
2 changes: 1 addition & 1 deletion src/test/ui/did_you_mean/issue-38147-3.stderr
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
error: cannot borrow immutable borrowed content `*self.s` as mutable
error[E0596]: cannot borrow immutable borrowed content `*self.s` as mutable
--> $DIR/issue-38147-3.rs:17:9
|
12 | s: &'a String
Expand Down
Loading

0 comments on commit cb7c60f

Please sign in to comment.