]>
Commit | Line | Data |
---|---|---|
1a4d82fc JJ |
1 | // Copyright 2014 The Rust Project Developers. See the COPYRIGHT |
2 | // file at the top-level directory of this distribution and at | |
3 | // http://rust-lang.org/COPYRIGHT. | |
4 | // | |
5 | // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or | |
6 | // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license | |
7 | // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your | |
8 | // option. This file may not be copied, modified, or distributed | |
9 | // except according to those terms. | |
10 | ||
11 | #![allow(non_snake_case)] | |
12 | ||
9346a6ac AL |
13 | // Error messages for EXXXX errors. |
14 | // Each message should start and end with a new line, and be wrapped to 80 characters. | |
15 | // In vim you can `:set tw=80` and use `gq` to wrap paragraphs. Use `:set tw=0` to disable. | |
85aaf69f | 16 | register_long_diagnostics! { |
d9579d0f AL |
17 | E0020: r##" |
18 | This error indicates that an attempt was made to divide by zero (or take the | |
e9174d1e SL |
19 | remainder of a zero divisor) in a static or constant expression. Erroneous |
20 | code example: | |
21 | ||
7453a54e | 22 | ```compile_fail |
e9174d1e SL |
23 | const X: i32 = 42 / 0; |
24 | // error: attempted to divide by zero in a constant expression | |
25 | ``` | |
d9579d0f AL |
26 | "##, |
27 | ||
7453a54e | 28 | E0038: r##" |
c1a9b12d SL |
29 | Trait objects like `Box<Trait>` can only be constructed when certain |
30 | requirements are satisfied by the trait in question. | |
31 | ||
32 | Trait objects are a form of dynamic dispatch and use a dynamically sized type | |
33 | for the inner type. So, for a given trait `Trait`, when `Trait` is treated as a | |
34 | type, as in `Box<Trait>`, the inner type is 'unsized'. In such cases the boxed | |
35 | pointer is a 'fat pointer' that contains an extra pointer to a table of methods | |
36 | (among other things) for dynamic dispatch. This design mandates some | |
37 | restrictions on the types of traits that are allowed to be used in trait | |
38 | objects, which are collectively termed as 'object safety' rules. | |
39 | ||
40 | Attempting to create a trait object for a non object-safe trait will trigger | |
41 | this error. | |
42 | ||
43 | There are various rules: | |
44 | ||
45 | ### The trait cannot require `Self: Sized` | |
46 | ||
47 | When `Trait` is treated as a type, the type does not implement the special | |
48 | `Sized` trait, because the type does not have a known size at compile time and | |
49 | can only be accessed behind a pointer. Thus, if we have a trait like the | |
50 | following: | |
51 | ||
52 | ``` | |
53 | trait Foo where Self: Sized { | |
54 | ||
55 | } | |
56 | ``` | |
57 | ||
7453a54e | 58 | We cannot create an object of type `Box<Foo>` or `&Foo` since in this case |
c1a9b12d SL |
59 | `Self` would not be `Sized`. |
60 | ||
61 | Generally, `Self : Sized` is used to indicate that the trait should not be used | |
62 | as a trait object. If the trait comes from your own crate, consider removing | |
63 | this restriction. | |
64 | ||
65 | ### Method references the `Self` type in its arguments or return type | |
66 | ||
67 | This happens when a trait has a method like the following: | |
68 | ||
7453a54e | 69 | ```compile_fail |
c1a9b12d SL |
70 | trait Trait { |
71 | fn foo(&self) -> Self; | |
72 | } | |
73 | ||
74 | impl Trait for String { | |
75 | fn foo(&self) -> Self { | |
76 | "hi".to_owned() | |
77 | } | |
78 | } | |
79 | ||
80 | impl Trait for u8 { | |
81 | fn foo(&self) -> Self { | |
82 | 1 | |
83 | } | |
84 | } | |
85 | ``` | |
86 | ||
87 | (Note that `&self` and `&mut self` are okay, it's additional `Self` types which | |
7453a54e | 88 | cause this problem.) |
c1a9b12d SL |
89 | |
90 | In such a case, the compiler cannot predict the return type of `foo()` in a | |
91 | situation like the following: | |
92 | ||
7453a54e SL |
93 | ```compile_fail |
94 | trait Trait { | |
95 | fn foo(&self) -> Self; | |
96 | } | |
97 | ||
c1a9b12d SL |
98 | fn call_foo(x: Box<Trait>) { |
99 | let y = x.foo(); // What type is y? | |
100 | // ... | |
101 | } | |
102 | ``` | |
103 | ||
104 | If only some methods aren't object-safe, you can add a `where Self: Sized` bound | |
105 | on them to mark them as explicitly unavailable to trait objects. The | |
106 | functionality will still be available to all other implementers, including | |
107 | `Box<Trait>` which is itself sized (assuming you `impl Trait for Box<Trait>`). | |
108 | ||
109 | ``` | |
110 | trait Trait { | |
111 | fn foo(&self) -> Self where Self: Sized; | |
112 | // more functions | |
113 | } | |
114 | ``` | |
115 | ||
116 | Now, `foo()` can no longer be called on a trait object, but you will now be | |
117 | allowed to make a trait object, and that will be able to call any object-safe | |
118 | methods". With such a bound, one can still call `foo()` on types implementing | |
119 | that trait that aren't behind trait objects. | |
120 | ||
121 | ### Method has generic type parameters | |
122 | ||
123 | As mentioned before, trait objects contain pointers to method tables. So, if we | |
124 | have: | |
125 | ||
126 | ``` | |
127 | trait Trait { | |
128 | fn foo(&self); | |
129 | } | |
7453a54e | 130 | |
c1a9b12d SL |
131 | impl Trait for String { |
132 | fn foo(&self) { | |
133 | // implementation 1 | |
134 | } | |
135 | } | |
7453a54e | 136 | |
c1a9b12d SL |
137 | impl Trait for u8 { |
138 | fn foo(&self) { | |
139 | // implementation 2 | |
140 | } | |
141 | } | |
142 | // ... | |
143 | ``` | |
144 | ||
145 | At compile time each implementation of `Trait` will produce a table containing | |
146 | the various methods (and other items) related to the implementation. | |
147 | ||
148 | This works fine, but when the method gains generic parameters, we can have a | |
149 | problem. | |
150 | ||
151 | Usually, generic parameters get _monomorphized_. For example, if I have | |
152 | ||
153 | ``` | |
154 | fn foo<T>(x: T) { | |
155 | // ... | |
156 | } | |
157 | ``` | |
158 | ||
7453a54e | 159 | The machine code for `foo::<u8>()`, `foo::<bool>()`, `foo::<String>()`, or any |
c1a9b12d SL |
160 | other type substitution is different. Hence the compiler generates the |
161 | implementation on-demand. If you call `foo()` with a `bool` parameter, the | |
162 | compiler will only generate code for `foo::<bool>()`. When we have additional | |
163 | type parameters, the number of monomorphized implementations the compiler | |
164 | generates does not grow drastically, since the compiler will only generate an | |
165 | implementation if the function is called with unparametrized substitutions | |
166 | (i.e., substitutions where none of the substituted types are themselves | |
167 | parametrized). | |
168 | ||
169 | However, with trait objects we have to make a table containing _every_ object | |
170 | that implements the trait. Now, if it has type parameters, we need to add | |
171 | implementations for every type that implements the trait, and there could | |
172 | theoretically be an infinite number of types. | |
173 | ||
174 | For example, with: | |
175 | ||
176 | ``` | |
177 | trait Trait { | |
178 | fn foo<T>(&self, on: T); | |
179 | // more methods | |
180 | } | |
7453a54e | 181 | |
c1a9b12d SL |
182 | impl Trait for String { |
183 | fn foo<T>(&self, on: T) { | |
184 | // implementation 1 | |
185 | } | |
186 | } | |
7453a54e | 187 | |
c1a9b12d SL |
188 | impl Trait for u8 { |
189 | fn foo<T>(&self, on: T) { | |
190 | // implementation 2 | |
191 | } | |
192 | } | |
7453a54e | 193 | |
c1a9b12d SL |
194 | // 8 more implementations |
195 | ``` | |
196 | ||
197 | Now, if we have the following code: | |
198 | ||
7453a54e | 199 | ```ignore |
c1a9b12d SL |
200 | fn call_foo(thing: Box<Trait>) { |
201 | thing.foo(true); // this could be any one of the 8 types above | |
202 | thing.foo(1); | |
203 | thing.foo("hello"); | |
204 | } | |
205 | ``` | |
206 | ||
7453a54e | 207 | We don't just need to create a table of all implementations of all methods of |
c1a9b12d SL |
208 | `Trait`, we need to create such a table, for each different type fed to |
209 | `foo()`. In this case this turns out to be (10 types implementing `Trait`)*(3 | |
210 | types being fed to `foo()`) = 30 implementations! | |
211 | ||
212 | With real world traits these numbers can grow drastically. | |
213 | ||
214 | To fix this, it is suggested to use a `where Self: Sized` bound similar to the | |
215 | fix for the sub-error above if you do not intend to call the method with type | |
216 | parameters: | |
217 | ||
218 | ``` | |
219 | trait Trait { | |
220 | fn foo<T>(&self, on: T) where Self: Sized; | |
221 | // more methods | |
222 | } | |
223 | ``` | |
224 | ||
225 | If this is not an option, consider replacing the type parameter with another | |
226 | trait object (e.g. if `T: OtherTrait`, use `on: Box<OtherTrait>`). If the number | |
227 | of types you intend to feed to this method is limited, consider manually listing | |
228 | out the methods of different types. | |
229 | ||
230 | ### Method has no receiver | |
231 | ||
232 | Methods that do not take a `self` parameter can't be called since there won't be | |
7453a54e | 233 | a way to get a pointer to the method table for them. |
c1a9b12d SL |
234 | |
235 | ``` | |
236 | trait Foo { | |
237 | fn foo() -> u8; | |
238 | } | |
239 | ``` | |
240 | ||
241 | This could be called as `<Foo as Foo>::foo()`, which would not be able to pick | |
242 | an implementation. | |
243 | ||
244 | Adding a `Self: Sized` bound to these methods will generally make this compile. | |
245 | ||
246 | ``` | |
247 | trait Foo { | |
248 | fn foo() -> u8 where Self: Sized; | |
249 | } | |
250 | ``` | |
251 | ||
252 | ### The trait cannot use `Self` as a type parameter in the supertrait listing | |
253 | ||
254 | This is similar to the second sub-error, but subtler. It happens in situations | |
255 | like the following: | |
256 | ||
7453a54e | 257 | ```compile_fail |
c1a9b12d SL |
258 | trait Super<A> {} |
259 | ||
260 | trait Trait: Super<Self> { | |
261 | } | |
262 | ||
263 | struct Foo; | |
264 | ||
265 | impl Super<Foo> for Foo{} | |
266 | ||
267 | impl Trait for Foo {} | |
268 | ``` | |
269 | ||
270 | Here, the supertrait might have methods as follows: | |
271 | ||
272 | ``` | |
273 | trait Super<A> { | |
274 | fn get_a(&self) -> A; // note that this is object safe! | |
275 | } | |
276 | ``` | |
277 | ||
278 | If the trait `Foo` was deriving from something like `Super<String>` or | |
279 | `Super<T>` (where `Foo` itself is `Foo<T>`), this is okay, because given a type | |
280 | `get_a()` will definitely return an object of that type. | |
281 | ||
282 | However, if it derives from `Super<Self>`, even though `Super` is object safe, | |
283 | the method `get_a()` would return an object of unknown type when called on the | |
284 | function. `Self` type parameters let us make object safe traits no longer safe, | |
285 | so they are forbidden when specifying supertraits. | |
286 | ||
287 | There's no easy fix for this, generally code will need to be refactored so that | |
288 | you no longer need to derive from `Super<Self>`. | |
7453a54e SL |
289 | "##, |
290 | ||
291 | E0072: r##" | |
292 | When defining a recursive struct or enum, any use of the type being defined | |
293 | from inside the definition must occur behind a pointer (like `Box` or `&`). | |
294 | This is because structs and enums must have a well-defined size, and without | |
295 | the pointer the size of the type would need to be unbounded. | |
296 | ||
297 | Consider the following erroneous definition of a type for a list of bytes: | |
298 | ||
299 | ```compile_fail | |
300 | // error, invalid recursive struct type | |
301 | struct ListNode { | |
302 | head: u8, | |
303 | tail: Option<ListNode>, | |
304 | } | |
305 | ``` | |
306 | ||
307 | This type cannot have a well-defined size, because it needs to be arbitrarily | |
308 | large (since we would be able to nest `ListNode`s to any depth). Specifically, | |
309 | ||
310 | ```plain | |
311 | size of `ListNode` = 1 byte for `head` | |
312 | + 1 byte for the discriminant of the `Option` | |
313 | + size of `ListNode` | |
314 | ``` | |
315 | ||
316 | One way to fix this is by wrapping `ListNode` in a `Box`, like so: | |
317 | ||
318 | ``` | |
319 | struct ListNode { | |
320 | head: u8, | |
321 | tail: Option<Box<ListNode>>, | |
322 | } | |
323 | ``` | |
324 | ||
325 | This works because `Box` is a pointer, so its size is well-known. | |
326 | "##, | |
c1a9b12d | 327 | |
c1a9b12d SL |
328 | E0109: r##" |
329 | You tried to give a type parameter to a type which doesn't need it. Erroneous | |
330 | code example: | |
331 | ||
7453a54e | 332 | ```compile_fail |
c1a9b12d SL |
333 | type X = u32<i32>; // error: type parameters are not allowed on this type |
334 | ``` | |
335 | ||
336 | Please check that you used the correct type and recheck its definition. Perhaps | |
337 | it doesn't need the type parameter. | |
338 | ||
339 | Example: | |
340 | ||
341 | ``` | |
342 | type X = u32; // this compiles | |
343 | ``` | |
344 | ||
345 | Note that type parameters for enum-variant constructors go after the variant, | |
346 | not after the enum (Option::None::<u32>, not Option::<u32>::None). | |
347 | "##, | |
348 | ||
349 | E0110: r##" | |
350 | You tried to give a lifetime parameter to a type which doesn't need it. | |
351 | Erroneous code example: | |
352 | ||
7453a54e | 353 | ```compile_fail |
c1a9b12d SL |
354 | type X = u32<'static>; // error: lifetime parameters are not allowed on |
355 | // this type | |
356 | ``` | |
357 | ||
358 | Please check that the correct type was used and recheck its definition; perhaps | |
359 | it doesn't need the lifetime parameter. Example: | |
360 | ||
361 | ``` | |
362 | type X = u32; // ok! | |
363 | ``` | |
d9579d0f AL |
364 | "##, |
365 | ||
366 | E0133: r##" | |
7453a54e SL |
367 | Using unsafe functionality is potentially dangerous and disallowed by safety |
368 | checks. Examples: | |
e9174d1e | 369 | |
7453a54e SL |
370 | * Dereferencing raw pointers |
371 | * Calling functions via FFI | |
372 | * Calling functions marked unsafe | |
e9174d1e | 373 | |
7453a54e SL |
374 | These safety checks can be relaxed for a section of the code by wrapping the |
375 | unsafe instructions with an `unsafe` block. For instance: | |
d9579d0f AL |
376 | |
377 | ``` | |
378 | unsafe fn f() { return; } | |
379 | ||
380 | fn main() { | |
381 | unsafe { f(); } | |
382 | } | |
383 | ``` | |
384 | ||
c1a9b12d SL |
385 | See also https://doc.rust-lang.org/book/unsafe.html |
386 | "##, | |
387 | ||
388 | // This shouldn't really ever trigger since the repeated value error comes first | |
389 | E0136: r##" | |
390 | A binary can only have one entry point, and by default that entry point is the | |
391 | function `main()`. If there are multiple such functions, please rename one. | |
d9579d0f AL |
392 | "##, |
393 | ||
394 | E0137: r##" | |
395 | This error indicates that the compiler found multiple functions with the | |
396 | `#[main]` attribute. This is an error because there must be a unique entry | |
397 | point into a Rust program. | |
398 | "##, | |
399 | ||
c1a9b12d SL |
400 | E0138: r##" |
401 | This error indicates that the compiler found multiple functions with the | |
402 | `#[start]` attribute. This is an error because there must be a unique entry | |
403 | point into a Rust program. | |
404 | "##, | |
405 | ||
406 | // FIXME link this to the relevant turpl chapters for instilling fear of the | |
407 | // transmute gods in the user | |
408 | E0139: r##" | |
409 | There are various restrictions on transmuting between types in Rust; for example | |
410 | types being transmuted must have the same size. To apply all these restrictions, | |
411 | the compiler must know the exact types that may be transmuted. When type | |
412 | parameters are involved, this cannot always be done. | |
413 | ||
414 | So, for example, the following is not allowed: | |
415 | ||
7453a54e SL |
416 | ```compile_fail |
417 | struct Foo<T>(Vec<T>); | |
c1a9b12d SL |
418 | |
419 | fn foo<T>(x: Vec<T>) { | |
420 | // we are transmuting between Vec<T> and Foo<T> here | |
421 | let y: Foo<T> = unsafe { transmute(x) }; | |
422 | // do something with y | |
423 | } | |
424 | ``` | |
425 | ||
426 | In this specific case there's a good chance that the transmute is harmless (but | |
427 | this is not guaranteed by Rust). However, when alignment and enum optimizations | |
428 | come into the picture, it's quite likely that the sizes may or may not match | |
429 | with different type parameter substitutions. It's not possible to check this for | |
430 | _all_ possible types, so `transmute()` simply only accepts types without any | |
431 | unsubstituted type parameters. | |
432 | ||
433 | If you need this, there's a good chance you're doing something wrong. Keep in | |
434 | mind that Rust doesn't guarantee much about the layout of different structs | |
435 | (even two structs with identical declarations may have different layouts). If | |
436 | there is a solution that avoids the transmute entirely, try it instead. | |
437 | ||
438 | If it's possible, hand-monomorphize the code by writing the function for each | |
439 | possible type substitution. It's possible to use traits to do this cleanly, | |
440 | for example: | |
441 | ||
7453a54e SL |
442 | ```ignore |
443 | struct Foo<T>(Vec<T>); | |
444 | ||
c1a9b12d | 445 | trait MyTransmutableType { |
7453a54e | 446 | fn transmute(Vec<Self>) -> Foo<Self>; |
c1a9b12d SL |
447 | } |
448 | ||
449 | impl MyTransmutableType for u8 { | |
450 | fn transmute(x: Foo<u8>) -> Vec<u8> { | |
451 | transmute(x) | |
452 | } | |
453 | } | |
7453a54e | 454 | |
c1a9b12d SL |
455 | impl MyTransmutableType for String { |
456 | fn transmute(x: Foo<String>) -> Vec<String> { | |
457 | transmute(x) | |
458 | } | |
459 | } | |
7453a54e | 460 | |
c1a9b12d SL |
461 | // ... more impls for the types you intend to transmute |
462 | ||
463 | fn foo<T: MyTransmutableType>(x: Vec<T>) { | |
464 | let y: Foo<T> = <T as MyTransmutableType>::transmute(x); | |
465 | // do something with y | |
466 | } | |
467 | ``` | |
468 | ||
469 | Each impl will be checked for a size match in the transmute as usual, and since | |
470 | there are no unbound type parameters involved, this should compile unless there | |
471 | is a size mismatch in one of the impls. | |
472 | ||
473 | It is also possible to manually transmute: | |
474 | ||
7453a54e | 475 | ```ignore |
e9174d1e | 476 | ptr::read(&v as *const _ as *const SomeType) // `v` transmuted to `SomeType` |
c1a9b12d | 477 | ``` |
92a42be0 SL |
478 | |
479 | Note that this does not move `v` (unlike `transmute`), and may need a | |
480 | call to `mem::forget(v)` in case you want to avoid destructors being called. | |
c1a9b12d SL |
481 | "##, |
482 | ||
d9579d0f AL |
483 | E0152: r##" |
484 | Lang items are already implemented in the standard library. Unless you are | |
485 | writing a free-standing application (e.g. a kernel), you do not need to provide | |
486 | them yourself. | |
487 | ||
488 | You can build a free-standing crate by adding `#![no_std]` to the crate | |
489 | attributes: | |
490 | ||
491 | ``` | |
d9579d0f AL |
492 | #![no_std] |
493 | ``` | |
494 | ||
495 | See also https://doc.rust-lang.org/book/no-stdlib.html | |
496 | "##, | |
497 | ||
9cc50fc6 SL |
498 | E0229: r##" |
499 | An associated type binding was done outside of the type parameter declaration | |
500 | and `where` clause. Erroneous code example: | |
501 | ||
7453a54e | 502 | ```compile_fail |
9cc50fc6 SL |
503 | pub trait Foo { |
504 | type A; | |
505 | fn boo(&self) -> <Self as Foo>::A; | |
506 | } | |
507 | ||
508 | struct Bar; | |
509 | ||
510 | impl Foo for isize { | |
511 | type A = usize; | |
512 | fn boo(&self) -> usize { 42 } | |
513 | } | |
514 | ||
515 | fn baz<I>(x: &<I as Foo<A=Bar>>::A) {} | |
516 | // error: associated type bindings are not allowed here | |
517 | ``` | |
518 | ||
519 | To solve this error, please move the type bindings in the type parameter | |
520 | declaration: | |
521 | ||
7453a54e | 522 | ```ignore |
9cc50fc6 SL |
523 | fn baz<I: Foo<A=Bar>>(x: &<I as Foo>::A) {} // ok! |
524 | ``` | |
525 | ||
7453a54e | 526 | Or in the `where` clause: |
9cc50fc6 | 527 | |
7453a54e | 528 | ```ignore |
9cc50fc6 SL |
529 | fn baz<I>(x: &<I as Foo>::A) where I: Foo<A=Bar> {} |
530 | ``` | |
531 | "##, | |
532 | ||
62682a34 SL |
533 | E0261: r##" |
534 | When using a lifetime like `'a` in a type, it must be declared before being | |
535 | used. | |
536 | ||
537 | These two examples illustrate the problem: | |
538 | ||
7453a54e | 539 | ```compile_fail |
62682a34 SL |
540 | // error, use of undeclared lifetime name `'a` |
541 | fn foo(x: &'a str) { } | |
542 | ||
543 | struct Foo { | |
544 | // error, use of undeclared lifetime name `'a` | |
545 | x: &'a str, | |
546 | } | |
547 | ``` | |
548 | ||
549 | These can be fixed by declaring lifetime parameters: | |
550 | ||
551 | ``` | |
7453a54e | 552 | fn foo<'a>(x: &'a str) {} |
62682a34 SL |
553 | |
554 | struct Foo<'a> { | |
555 | x: &'a str, | |
556 | } | |
557 | ``` | |
558 | "##, | |
559 | ||
560 | E0262: r##" | |
561 | Declaring certain lifetime names in parameters is disallowed. For example, | |
562 | because the `'static` lifetime is a special built-in lifetime name denoting | |
563 | the lifetime of the entire program, this is an error: | |
564 | ||
7453a54e | 565 | ```compile_fail |
c1a9b12d | 566 | // error, invalid lifetime parameter name `'static` |
62682a34 SL |
567 | fn foo<'static>(x: &'static str) { } |
568 | ``` | |
569 | "##, | |
570 | ||
571 | E0263: r##" | |
572 | A lifetime name cannot be declared more than once in the same scope. For | |
573 | example: | |
574 | ||
7453a54e | 575 | ```compile_fail |
62682a34 SL |
576 | // error, lifetime name `'a` declared twice in the same scope |
577 | fn foo<'a, 'b, 'a>(x: &'a str, y: &'b str) { } | |
578 | ``` | |
579 | "##, | |
580 | ||
92a42be0 SL |
581 | E0264: r##" |
582 | An unknown external lang item was used. Erroneous code example: | |
583 | ||
7453a54e | 584 | ```compile_fail |
92a42be0 SL |
585 | #![feature(lang_items)] |
586 | ||
587 | extern "C" { | |
588 | #[lang = "cake"] // error: unknown external lang item: `cake` | |
589 | fn cake(); | |
590 | } | |
591 | ``` | |
592 | ||
593 | A list of available external lang items is available in | |
594 | `src/librustc/middle/weak_lang_items.rs`. Example: | |
595 | ||
596 | ``` | |
597 | #![feature(lang_items)] | |
598 | ||
599 | extern "C" { | |
600 | #[lang = "panic_fmt"] // ok! | |
601 | fn cake(); | |
602 | } | |
603 | ``` | |
604 | "##, | |
605 | ||
c1a9b12d SL |
606 | E0269: r##" |
607 | Functions must eventually return a value of their return type. For example, in | |
7453a54e | 608 | the following function: |
c1a9b12d | 609 | |
7453a54e | 610 | ```compile_fail |
c1a9b12d SL |
611 | fn foo(x: u8) -> u8 { |
612 | if x > 0 { | |
613 | x // alternatively, `return x` | |
614 | } | |
615 | // nothing here | |
616 | } | |
617 | ``` | |
618 | ||
7453a54e | 619 | If the condition is true, the value `x` is returned, but if the condition is |
c1a9b12d SL |
620 | false, control exits the `if` block and reaches a place where nothing is being |
621 | returned. All possible control paths must eventually return a `u8`, which is not | |
622 | happening here. | |
623 | ||
624 | An easy fix for this in a complicated function is to specify a default return | |
625 | value, if possible: | |
626 | ||
7453a54e | 627 | ```ignore |
c1a9b12d SL |
628 | fn foo(x: u8) -> u8 { |
629 | if x > 0 { | |
630 | x // alternatively, `return x` | |
631 | } | |
632 | // lots of other if branches | |
633 | 0 // return 0 if all else fails | |
634 | } | |
635 | ``` | |
636 | ||
637 | It is advisable to find out what the unhandled cases are and check for them, | |
638 | returning an appropriate value or panicking if necessary. | |
639 | "##, | |
640 | ||
641 | E0270: r##" | |
642 | Rust lets you define functions which are known to never return, i.e. are | |
643 | 'diverging', by marking its return type as `!`. | |
644 | ||
645 | For example, the following functions never return: | |
646 | ||
7453a54e | 647 | ```no_run |
c1a9b12d SL |
648 | fn foo() -> ! { |
649 | loop {} | |
650 | } | |
651 | ||
652 | fn bar() -> ! { | |
653 | foo() // foo() is diverging, so this will diverge too | |
654 | } | |
655 | ||
656 | fn baz() -> ! { | |
657 | panic!(); // this macro internally expands to a call to a diverging function | |
658 | } | |
c1a9b12d SL |
659 | ``` |
660 | ||
661 | Such functions can be used in a place where a value is expected without | |
7453a54e SL |
662 | returning a value of that type, for instance: |
663 | ||
664 | ```no_run | |
665 | fn foo() -> ! { | |
666 | loop {} | |
667 | } | |
668 | ||
669 | let x = 3; | |
c1a9b12d | 670 | |
c1a9b12d SL |
671 | let y = match x { |
672 | 1 => 1, | |
673 | 2 => 4, | |
674 | _ => foo() // diverging function called here | |
675 | }; | |
7453a54e | 676 | |
c1a9b12d SL |
677 | println!("{}", y) |
678 | ``` | |
679 | ||
680 | If the third arm of the match block is reached, since `foo()` doesn't ever | |
681 | return control to the match block, it is fine to use it in a place where an | |
682 | integer was expected. The `match` block will never finish executing, and any | |
683 | point where `y` (like the print statement) is needed will not be reached. | |
684 | ||
7453a54e | 685 | However, if we had a diverging function that actually does finish execution: |
c1a9b12d | 686 | |
7453a54e SL |
687 | ```ignore |
688 | fn foo() -> ! { | |
c1a9b12d SL |
689 | loop {break;} |
690 | } | |
691 | ``` | |
692 | ||
7453a54e SL |
693 | Then we would have an unknown value for `y` in the following code: |
694 | ||
695 | ```no_run | |
696 | fn foo() -> ! { | |
697 | loop {} | |
698 | } | |
699 | ||
700 | let x = 3; | |
c1a9b12d | 701 | |
c1a9b12d SL |
702 | let y = match x { |
703 | 1 => 1, | |
704 | 2 => 4, | |
705 | _ => foo() | |
706 | }; | |
7453a54e | 707 | |
c1a9b12d SL |
708 | println!("{}", y); |
709 | ``` | |
710 | ||
7453a54e SL |
711 | In the previous example, the print statement was never reached when the |
712 | wildcard match arm was hit, so we were okay with `foo()` not returning an | |
713 | integer that we could set to `y`. But in this example, `foo()` actually does | |
714 | return control, so the print statement will be executed with an uninitialized | |
715 | value. | |
c1a9b12d SL |
716 | |
717 | Obviously we cannot have functions which are allowed to be used in such | |
718 | positions and yet can return control. So, if you are defining a function that | |
7453a54e SL |
719 | returns `!`, make sure that there is no way for it to actually finish |
720 | executing. | |
d9579d0f AL |
721 | "##, |
722 | ||
723 | E0271: r##" | |
724 | This is because of a type mismatch between the associated type of some | |
725 | trait (e.g. `T::Bar`, where `T` implements `trait Quux { type Bar; }`) | |
726 | and another type `U` that is required to be equal to `T::Bar`, but is not. | |
727 | Examples follow. | |
728 | ||
729 | Here is a basic example: | |
730 | ||
7453a54e | 731 | ```compile_fail |
d9579d0f | 732 | trait Trait { type AssociatedType; } |
7453a54e | 733 | |
d9579d0f AL |
734 | fn foo<T>(t: T) where T: Trait<AssociatedType=u32> { |
735 | println!("in foo"); | |
736 | } | |
7453a54e | 737 | |
d9579d0f | 738 | impl Trait for i8 { type AssociatedType = &'static str; } |
7453a54e | 739 | |
d9579d0f AL |
740 | foo(3_i8); |
741 | ``` | |
742 | ||
743 | Here is that same example again, with some explanatory comments: | |
744 | ||
7453a54e | 745 | ```ignore |
d9579d0f AL |
746 | trait Trait { type AssociatedType; } |
747 | ||
748 | fn foo<T>(t: T) where T: Trait<AssociatedType=u32> { | |
749 | // ~~~~~~~~ ~~~~~~~~~~~~~~~~~~ | |
750 | // | | | |
751 | // This says `foo` can | | |
752 | // only be used with | | |
753 | // some type that | | |
754 | // implements `Trait`. | | |
755 | // | | |
756 | // This says not only must | |
757 | // `T` be an impl of `Trait` | |
758 | // but also that the impl | |
759 | // must assign the type `u32` | |
760 | // to the associated type. | |
761 | println!("in foo"); | |
762 | } | |
763 | ||
764 | impl Trait for i8 { type AssociatedType = &'static str; } | |
765 | ~~~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
766 | // | | | |
767 | // `i8` does have | | |
768 | // implementation | | |
769 | // of `Trait`... | | |
770 | // ... but it is an implementation | |
771 | // that assigns `&'static str` to | |
772 | // the associated type. | |
773 | ||
774 | foo(3_i8); | |
775 | // Here, we invoke `foo` with an `i8`, which does not satisfy | |
62682a34 | 776 | // the constraint `<i8 as Trait>::AssociatedType=u32`, and |
d9579d0f AL |
777 | // therefore the type-checker complains with this error code. |
778 | ``` | |
779 | ||
780 | Here is a more subtle instance of the same problem, that can | |
781 | arise with for-loops in Rust: | |
782 | ||
7453a54e | 783 | ```compile_fail |
d9579d0f AL |
784 | let vs: Vec<i32> = vec![1, 2, 3, 4]; |
785 | for v in &vs { | |
786 | match v { | |
7453a54e SL |
787 | 1 => {}, |
788 | _ => {}, | |
d9579d0f AL |
789 | } |
790 | } | |
791 | ``` | |
792 | ||
793 | The above fails because of an analogous type mismatch, | |
794 | though may be harder to see. Again, here are some | |
795 | explanatory comments for the same example: | |
796 | ||
7453a54e | 797 | ```ignore |
d9579d0f AL |
798 | { |
799 | let vs = vec![1, 2, 3, 4]; | |
800 | ||
801 | // `for`-loops use a protocol based on the `Iterator` | |
802 | // trait. Each item yielded in a `for` loop has the | |
9cc50fc6 | 803 | // type `Iterator::Item` -- that is, `Item` is the |
d9579d0f AL |
804 | // associated type of the concrete iterator impl. |
805 | for v in &vs { | |
806 | // ~ ~~~ | |
807 | // | | | |
808 | // | We borrow `vs`, iterating over a sequence of | |
809 | // | *references* of type `&Elem` (where `Elem` is | |
810 | // | vector's element type). Thus, the associated | |
811 | // | type `Item` must be a reference `&`-type ... | |
812 | // | | |
813 | // ... and `v` has the type `Iterator::Item`, as dictated by | |
814 | // the `for`-loop protocol ... | |
815 | ||
816 | match v { | |
817 | 1 => {} | |
818 | // ~ | |
819 | // | | |
820 | // ... but *here*, `v` is forced to have some integral type; | |
821 | // only types like `u8`,`i8`,`u16`,`i16`, et cetera can | |
822 | // match the pattern `1` ... | |
823 | ||
824 | _ => {} | |
825 | } | |
826 | ||
827 | // ... therefore, the compiler complains, because it sees | |
828 | // an attempt to solve the equations | |
829 | // `some integral-type` = type-of-`v` | |
830 | // = `Iterator::Item` | |
831 | // = `&Elem` (i.e. `some reference type`) | |
832 | // | |
833 | // which cannot possibly all be true. | |
834 | ||
835 | } | |
836 | } | |
837 | ``` | |
838 | ||
839 | To avoid those issues, you have to make the types match correctly. | |
840 | So we can fix the previous examples like this: | |
841 | ||
842 | ``` | |
843 | // Basic Example: | |
844 | trait Trait { type AssociatedType; } | |
7453a54e | 845 | |
d9579d0f AL |
846 | fn foo<T>(t: T) where T: Trait<AssociatedType = &'static str> { |
847 | println!("in foo"); | |
848 | } | |
7453a54e | 849 | |
d9579d0f | 850 | impl Trait for i8 { type AssociatedType = &'static str; } |
7453a54e | 851 | |
d9579d0f AL |
852 | foo(3_i8); |
853 | ||
854 | // For-Loop Example: | |
855 | let vs = vec![1, 2, 3, 4]; | |
856 | for v in &vs { | |
857 | match v { | |
858 | &1 => {} | |
859 | _ => {} | |
860 | } | |
861 | } | |
862 | ``` | |
863 | "##, | |
864 | ||
c1a9b12d SL |
865 | E0272: r##" |
866 | The `#[rustc_on_unimplemented]` attribute lets you specify a custom error | |
867 | message for when a particular trait isn't implemented on a type placed in a | |
868 | position that needs that trait. For example, when the following code is | |
869 | compiled: | |
870 | ||
7453a54e | 871 | ```compile_fail |
c1a9b12d SL |
872 | fn foo<T: Index<u8>>(x: T){} |
873 | ||
874 | #[rustc_on_unimplemented = "the type `{Self}` cannot be indexed by `{Idx}`"] | |
54a0048b | 875 | trait Index<Idx> { /* ... */ } |
c1a9b12d SL |
876 | |
877 | foo(true); // `bool` does not implement `Index<u8>` | |
878 | ``` | |
879 | ||
7453a54e | 880 | There will be an error about `bool` not implementing `Index<u8>`, followed by a |
c1a9b12d SL |
881 | note saying "the type `bool` cannot be indexed by `u8`". |
882 | ||
7453a54e SL |
883 | As you can see, you can specify type parameters in curly braces for |
884 | substitution with the actual types (using the regular format string syntax) in | |
885 | a given situation. Furthermore, `{Self}` will substitute to the type (in this | |
886 | case, `bool`) that we tried to use. | |
c1a9b12d SL |
887 | |
888 | This error appears when the curly braces contain an identifier which doesn't | |
7453a54e SL |
889 | match with any of the type parameters or the string `Self`. This might happen |
890 | if you misspelled a type parameter, or if you intended to use literal curly | |
891 | braces. If it is the latter, escape the curly braces with a second curly brace | |
892 | of the same type; e.g. a literal `{` is `{{`. | |
c1a9b12d SL |
893 | "##, |
894 | ||
895 | E0273: r##" | |
896 | The `#[rustc_on_unimplemented]` attribute lets you specify a custom error | |
897 | message for when a particular trait isn't implemented on a type placed in a | |
898 | position that needs that trait. For example, when the following code is | |
899 | compiled: | |
900 | ||
7453a54e | 901 | ```compile_fail |
c1a9b12d SL |
902 | fn foo<T: Index<u8>>(x: T){} |
903 | ||
904 | #[rustc_on_unimplemented = "the type `{Self}` cannot be indexed by `{Idx}`"] | |
54a0048b | 905 | trait Index<Idx> { /* ... */ } |
c1a9b12d SL |
906 | |
907 | foo(true); // `bool` does not implement `Index<u8>` | |
908 | ``` | |
909 | ||
910 | there will be an error about `bool` not implementing `Index<u8>`, followed by a | |
911 | note saying "the type `bool` cannot be indexed by `u8`". | |
912 | ||
7453a54e SL |
913 | As you can see, you can specify type parameters in curly braces for |
914 | substitution with the actual types (using the regular format string syntax) in | |
915 | a given situation. Furthermore, `{Self}` will substitute to the type (in this | |
916 | case, `bool`) that we tried to use. | |
c1a9b12d SL |
917 | |
918 | This error appears when the curly braces do not contain an identifier. Please | |
919 | add one of the same name as a type parameter. If you intended to use literal | |
920 | braces, use `{{` and `}}` to escape them. | |
921 | "##, | |
922 | ||
923 | E0274: r##" | |
924 | The `#[rustc_on_unimplemented]` attribute lets you specify a custom error | |
925 | message for when a particular trait isn't implemented on a type placed in a | |
926 | position that needs that trait. For example, when the following code is | |
927 | compiled: | |
928 | ||
7453a54e | 929 | ```compile_fail |
c1a9b12d SL |
930 | fn foo<T: Index<u8>>(x: T){} |
931 | ||
932 | #[rustc_on_unimplemented = "the type `{Self}` cannot be indexed by `{Idx}`"] | |
54a0048b | 933 | trait Index<Idx> { /* ... */ } |
c1a9b12d SL |
934 | |
935 | foo(true); // `bool` does not implement `Index<u8>` | |
936 | ``` | |
937 | ||
938 | there will be an error about `bool` not implementing `Index<u8>`, followed by a | |
939 | note saying "the type `bool` cannot be indexed by `u8`". | |
940 | ||
941 | For this to work, some note must be specified. An empty attribute will not do | |
942 | anything, please remove the attribute or add some helpful note for users of the | |
943 | trait. | |
944 | "##, | |
945 | ||
946 | E0275: r##" | |
947 | This error occurs when there was a recursive trait requirement that overflowed | |
7453a54e SL |
948 | before it could be evaluated. Often this means that there is unbounded |
949 | recursion in resolving some type bounds. | |
c1a9b12d | 950 | |
7453a54e | 951 | For example, in the following code: |
c1a9b12d | 952 | |
7453a54e | 953 | ```compile_fail |
c1a9b12d SL |
954 | trait Foo {} |
955 | ||
956 | struct Bar<T>(T); | |
957 | ||
958 | impl<T> Foo for T where Bar<T>: Foo {} | |
959 | ``` | |
960 | ||
7453a54e SL |
961 | To determine if a `T` is `Foo`, we need to check if `Bar<T>` is `Foo`. However, |
962 | to do this check, we need to determine that `Bar<Bar<T>>` is `Foo`. To | |
963 | determine this, we check if `Bar<Bar<Bar<T>>>` is `Foo`, and so on. This is | |
964 | clearly a recursive requirement that can't be resolved directly. | |
c1a9b12d SL |
965 | |
966 | Consider changing your trait bounds so that they're less self-referential. | |
967 | "##, | |
968 | ||
969 | E0276: r##" | |
970 | This error occurs when a bound in an implementation of a trait does not match | |
971 | the bounds specified in the original trait. For example: | |
972 | ||
7453a54e | 973 | ```compile_fail |
c1a9b12d | 974 | trait Foo { |
7453a54e | 975 | fn foo<T>(x: T); |
c1a9b12d SL |
976 | } |
977 | ||
978 | impl Foo for bool { | |
7453a54e | 979 | fn foo<T>(x: T) where T: Copy {} |
c1a9b12d SL |
980 | } |
981 | ``` | |
982 | ||
983 | Here, all types implementing `Foo` must have a method `foo<T>(x: T)` which can | |
984 | take any type `T`. However, in the `impl` for `bool`, we have added an extra | |
985 | bound that `T` is `Copy`, which isn't compatible with the original trait. | |
986 | ||
987 | Consider removing the bound from the method or adding the bound to the original | |
988 | method definition in the trait. | |
989 | "##, | |
990 | ||
991 | E0277: r##" | |
992 | You tried to use a type which doesn't implement some trait in a place which | |
993 | expected that trait. Erroneous code example: | |
994 | ||
7453a54e | 995 | ```compile_fail |
c1a9b12d SL |
996 | // here we declare the Foo trait with a bar method |
997 | trait Foo { | |
998 | fn bar(&self); | |
999 | } | |
1000 | ||
1001 | // we now declare a function which takes an object implementing the Foo trait | |
1002 | fn some_func<T: Foo>(foo: T) { | |
1003 | foo.bar(); | |
1004 | } | |
1005 | ||
1006 | fn main() { | |
1007 | // we now call the method with the i32 type, which doesn't implement | |
1008 | // the Foo trait | |
54a0048b | 1009 | some_func(5i32); // error: the trait bound `i32 : Foo` is not satisfied |
c1a9b12d SL |
1010 | } |
1011 | ``` | |
1012 | ||
1013 | In order to fix this error, verify that the type you're using does implement | |
1014 | the trait. Example: | |
1015 | ||
1016 | ``` | |
1017 | trait Foo { | |
1018 | fn bar(&self); | |
1019 | } | |
1020 | ||
1021 | fn some_func<T: Foo>(foo: T) { | |
1022 | foo.bar(); // we can now use this method since i32 implements the | |
1023 | // Foo trait | |
1024 | } | |
1025 | ||
1026 | // we implement the trait on the i32 type | |
1027 | impl Foo for i32 { | |
1028 | fn bar(&self) {} | |
1029 | } | |
1030 | ||
1031 | fn main() { | |
1032 | some_func(5i32); // ok! | |
1033 | } | |
1034 | ``` | |
54a0048b SL |
1035 | |
1036 | Or in a generic context, an erroneous code example would look like: | |
1037 | ```compile_fail | |
1038 | fn some_func<T>(foo: T) { | |
1039 | println!("{:?}", foo); // error: the trait `core::fmt::Debug` is not | |
1040 | // implemented for the type `T` | |
1041 | } | |
1042 | ||
1043 | fn main() { | |
1044 | // We now call the method with the i32 type, | |
1045 | // which *does* implement the Debug trait. | |
1046 | some_func(5i32); | |
1047 | } | |
1048 | ``` | |
1049 | ||
1050 | Note that the error here is in the definition of the generic function: Although | |
1051 | we only call it with a parameter that does implement `Debug`, the compiler | |
1052 | still rejects the function: It must work with all possible input types. In | |
1053 | order to make this example compile, we need to restrict the generic type we're | |
1054 | accepting: | |
1055 | ``` | |
1056 | use std::fmt; | |
1057 | ||
1058 | // Restrict the input type to types that implement Debug. | |
1059 | fn some_func<T: fmt::Debug>(foo: T) { | |
1060 | println!("{:?}", foo); | |
1061 | } | |
1062 | ||
1063 | fn main() { | |
1064 | // Calling the method is still fine, as i32 implements Debug. | |
1065 | some_func(5i32); | |
1066 | ||
1067 | // This would fail to compile now: | |
1068 | // struct WithoutDebug; | |
1069 | // some_func(WithoutDebug); | |
1070 | } | |
1071 | ||
1072 | Rust only looks at the signature of the called function, as such it must | |
1073 | already specify all requirements that will be used for every type parameter. | |
1074 | ``` | |
1075 | ||
c1a9b12d SL |
1076 | "##, |
1077 | ||
e9174d1e SL |
1078 | E0281: r##" |
1079 | You tried to supply a type which doesn't implement some trait in a location | |
1080 | which expected that trait. This error typically occurs when working with | |
1081 | `Fn`-based types. Erroneous code example: | |
1082 | ||
7453a54e | 1083 | ```compile_fail |
e9174d1e SL |
1084 | fn foo<F: Fn()>(x: F) { } |
1085 | ||
1086 | fn main() { | |
1087 | // type mismatch: the type ... implements the trait `core::ops::Fn<(_,)>`, | |
1088 | // but the trait `core::ops::Fn<()>` is required (expected (), found tuple | |
1089 | // [E0281] | |
1090 | foo(|y| { }); | |
1091 | } | |
1092 | ``` | |
1093 | ||
1094 | The issue in this case is that `foo` is defined as accepting a `Fn` with no | |
1095 | arguments, but the closure we attempted to pass to it requires one argument. | |
1096 | "##, | |
1097 | ||
d9579d0f AL |
1098 | E0282: r##" |
1099 | This error indicates that type inference did not result in one unique possible | |
1100 | type, and extra information is required. In most cases this can be provided | |
1101 | by adding a type annotation. Sometimes you need to specify a generic type | |
1102 | parameter manually. | |
1103 | ||
1104 | A common example is the `collect` method on `Iterator`. It has a generic type | |
1105 | parameter with a `FromIterator` bound, which for a `char` iterator is | |
1106 | implemented by `Vec` and `String` among others. Consider the following snippet | |
1107 | that reverses the characters of a string: | |
1108 | ||
7453a54e | 1109 | ```compile_fail |
d9579d0f AL |
1110 | let x = "hello".chars().rev().collect(); |
1111 | ``` | |
1112 | ||
1113 | In this case, the compiler cannot infer what the type of `x` should be: | |
1114 | `Vec<char>` and `String` are both suitable candidates. To specify which type to | |
1115 | use, you can use a type annotation on `x`: | |
1116 | ||
1117 | ``` | |
1118 | let x: Vec<char> = "hello".chars().rev().collect(); | |
1119 | ``` | |
1120 | ||
1121 | It is not necessary to annotate the full type. Once the ambiguity is resolved, | |
1122 | the compiler can infer the rest: | |
1123 | ||
1124 | ``` | |
1125 | let x: Vec<_> = "hello".chars().rev().collect(); | |
1126 | ``` | |
1127 | ||
1128 | Another way to provide the compiler with enough information, is to specify the | |
1129 | generic type parameter: | |
1130 | ||
1131 | ``` | |
1132 | let x = "hello".chars().rev().collect::<Vec<char>>(); | |
1133 | ``` | |
1134 | ||
1135 | Again, you need not specify the full type if the compiler can infer it: | |
1136 | ||
1137 | ``` | |
1138 | let x = "hello".chars().rev().collect::<Vec<_>>(); | |
1139 | ``` | |
1140 | ||
1141 | Apart from a method or function with a generic type parameter, this error can | |
1142 | occur when a type parameter of a struct or trait cannot be inferred. In that | |
1143 | case it is not always possible to use a type annotation, because all candidates | |
1144 | have the same return type. For instance: | |
1145 | ||
7453a54e | 1146 | ```compile_fail |
d9579d0f | 1147 | struct Foo<T> { |
7453a54e | 1148 | num: T, |
d9579d0f AL |
1149 | } |
1150 | ||
1151 | impl<T> Foo<T> { | |
1152 | fn bar() -> i32 { | |
1153 | 0 | |
1154 | } | |
1155 | ||
1156 | fn baz() { | |
1157 | let number = Foo::bar(); | |
1158 | } | |
1159 | } | |
1160 | ``` | |
1161 | ||
1162 | This will fail because the compiler does not know which instance of `Foo` to | |
1163 | call `bar` on. Change `Foo::bar()` to `Foo::<T>::bar()` to resolve the error. | |
1164 | "##, | |
1165 | ||
9cc50fc6 SL |
1166 | E0283: r##" |
1167 | This error occurs when the compiler doesn't have enough information | |
1168 | to unambiguously choose an implementation. | |
1169 | ||
1170 | For example: | |
1171 | ||
7453a54e | 1172 | ```compile_fail |
9cc50fc6 SL |
1173 | trait Generator { |
1174 | fn create() -> u32; | |
1175 | } | |
1176 | ||
1177 | struct Impl; | |
7453a54e | 1178 | |
9cc50fc6 SL |
1179 | impl Generator for Impl { |
1180 | fn create() -> u32 { 1 } | |
1181 | } | |
1182 | ||
1183 | struct AnotherImpl; | |
7453a54e | 1184 | |
9cc50fc6 SL |
1185 | impl Generator for AnotherImpl { |
1186 | fn create() -> u32 { 2 } | |
1187 | } | |
1188 | ||
1189 | fn main() { | |
1190 | let cont: u32 = Generator::create(); | |
1191 | // error, impossible to choose one of Generator trait implementation | |
1192 | // Impl or AnotherImpl? Maybe anything else? | |
1193 | } | |
1194 | ``` | |
1195 | ||
1196 | To resolve this error use the concrete type: | |
1197 | ||
1198 | ``` | |
7453a54e SL |
1199 | trait Generator { |
1200 | fn create() -> u32; | |
1201 | } | |
1202 | ||
1203 | struct AnotherImpl; | |
1204 | ||
1205 | impl Generator for AnotherImpl { | |
1206 | fn create() -> u32 { 2 } | |
1207 | } | |
1208 | ||
9cc50fc6 SL |
1209 | fn main() { |
1210 | let gen1 = AnotherImpl::create(); | |
1211 | ||
1212 | // if there are multiple methods with same name (different traits) | |
1213 | let gen2 = <AnotherImpl as Generator>::create(); | |
1214 | } | |
1215 | ``` | |
1216 | "##, | |
1217 | ||
d9579d0f AL |
1218 | E0296: r##" |
1219 | This error indicates that the given recursion limit could not be parsed. Ensure | |
1220 | that the value provided is a positive integer between quotes, like so: | |
1221 | ||
1222 | ``` | |
1223 | #![recursion_limit="1000"] | |
1224 | ``` | |
85aaf69f SL |
1225 | "##, |
1226 | ||
d9579d0f AL |
1227 | E0308: r##" |
1228 | This error occurs when the compiler was unable to infer the concrete type of a | |
c1a9b12d | 1229 | variable. It can occur for several cases, the most common of which is a |
d9579d0f AL |
1230 | mismatch in the expected type that the compiler inferred for a variable's |
1231 | initializing expression, and the actual type explicitly assigned to the | |
1232 | variable. | |
1233 | ||
1234 | For example: | |
1235 | ||
7453a54e | 1236 | ```compile_fail |
d9579d0f AL |
1237 | let x: i32 = "I am not a number!"; |
1238 | // ~~~ ~~~~~~~~~~~~~~~~~~~~ | |
1239 | // | | | |
1240 | // | initializing expression; | |
1241 | // | compiler infers type `&str` | |
1242 | // | | |
1243 | // type `i32` assigned to variable `x` | |
1244 | ``` | |
9cc50fc6 SL |
1245 | |
1246 | Another situation in which this occurs is when you attempt to use the `try!` | |
1247 | macro inside a function that does not return a `Result<T, E>`: | |
1248 | ||
7453a54e | 1249 | ```compile_fail |
9cc50fc6 SL |
1250 | use std::fs::File; |
1251 | ||
1252 | fn main() { | |
1253 | let mut f = try!(File::create("foo.txt")); | |
1254 | } | |
1255 | ``` | |
1256 | ||
1257 | This code gives an error like this: | |
1258 | ||
1259 | ```text | |
1260 | <std macros>:5:8: 6:42 error: mismatched types: | |
1261 | expected `()`, | |
1262 | found `core::result::Result<_, _>` | |
1263 | (expected (), | |
1264 | found enum `core::result::Result`) [E0308] | |
1265 | ``` | |
1266 | ||
1267 | `try!` returns a `Result<T, E>`, and so the function must. But `main()` has | |
1268 | `()` as its return type, hence the error. | |
d9579d0f AL |
1269 | "##, |
1270 | ||
1271 | E0309: r##" | |
1272 | Types in type definitions have lifetimes associated with them that represent | |
1273 | how long the data stored within them is guaranteed to be live. This lifetime | |
1274 | must be as long as the data needs to be alive, and missing the constraint that | |
1275 | denotes this will cause this error. | |
1276 | ||
7453a54e | 1277 | ```compile_fail |
d9579d0f AL |
1278 | // This won't compile because T is not constrained, meaning the data |
1279 | // stored in it is not guaranteed to last as long as the reference | |
1280 | struct Foo<'a, T> { | |
1281 | foo: &'a T | |
1282 | } | |
7453a54e | 1283 | ``` |
d9579d0f | 1284 | |
7453a54e SL |
1285 | This will compile, because it has the constraint on the type parameter: |
1286 | ||
1287 | ``` | |
d9579d0f AL |
1288 | struct Foo<'a, T: 'a> { |
1289 | foo: &'a T | |
1290 | } | |
1291 | ``` | |
1292 | "##, | |
1293 | ||
1294 | E0310: r##" | |
1295 | Types in type definitions have lifetimes associated with them that represent | |
1296 | how long the data stored within them is guaranteed to be live. This lifetime | |
1297 | must be as long as the data needs to be alive, and missing the constraint that | |
1298 | denotes this will cause this error. | |
1299 | ||
7453a54e | 1300 | ```compile_fail |
d9579d0f AL |
1301 | // This won't compile because T is not constrained to the static lifetime |
1302 | // the reference needs | |
1303 | struct Foo<T> { | |
1304 | foo: &'static T | |
1305 | } | |
1306 | ||
7453a54e | 1307 | This will compile, because it has the constraint on the type parameter: |
62682a34 SL |
1308 | |
1309 | ``` | |
7453a54e SL |
1310 | struct Foo<T: 'static> { |
1311 | foo: &'static T | |
62682a34 SL |
1312 | } |
1313 | ``` | |
62682a34 SL |
1314 | "##, |
1315 | ||
1316 | E0398: r##" | |
7453a54e SL |
1317 | In Rust 1.3, the default object lifetime bounds are expected to change, as |
1318 | described in RFC #1156 [1]. You are getting a warning because the compiler | |
1319 | thinks it is possible that this change will cause a compilation error in your | |
1320 | code. It is possible, though unlikely, that this is a false alarm. | |
1321 | ||
1322 | The heart of the change is that where `&'a Box<SomeTrait>` used to default to | |
1323 | `&'a Box<SomeTrait+'a>`, it now defaults to `&'a Box<SomeTrait+'static>` (here, | |
1324 | `SomeTrait` is the name of some trait type). Note that the only types which are | |
1325 | affected are references to boxes, like `&Box<SomeTrait>` or | |
1326 | `&[Box<SomeTrait>]`. More common types like `&SomeTrait` or `Box<SomeTrait>` | |
1327 | are unaffected. | |
1328 | ||
1329 | To silence this warning, edit your code to use an explicit bound. Most of the | |
1330 | time, this means that you will want to change the signature of a function that | |
1331 | you are calling. For example, if the error is reported on a call like `foo(x)`, | |
1332 | and `foo` is defined as follows: | |
1333 | ||
1334 | ```ignore | |
62682a34 SL |
1335 | fn foo(arg: &Box<SomeTrait>) { ... } |
1336 | ``` | |
1337 | ||
7453a54e | 1338 | You might change it to: |
62682a34 | 1339 | |
7453a54e | 1340 | ```ignore |
62682a34 SL |
1341 | fn foo<'a>(arg: &Box<SomeTrait+'a>) { ... } |
1342 | ``` | |
1343 | ||
7453a54e SL |
1344 | This explicitly states that you expect the trait object `SomeTrait` to contain |
1345 | references (with a maximum lifetime of `'a`). | |
62682a34 SL |
1346 | |
1347 | [1]: https://github.com/rust-lang/rfcs/pull/1156 | |
b039eaaf SL |
1348 | "##, |
1349 | ||
92a42be0 SL |
1350 | E0452: r##" |
1351 | An invalid lint attribute has been given. Erroneous code example: | |
b039eaaf | 1352 | |
7453a54e | 1353 | ```compile_fail |
92a42be0 | 1354 | #![allow(foo = "")] // error: malformed lint attribute |
b039eaaf SL |
1355 | ``` |
1356 | ||
92a42be0 SL |
1357 | Lint attributes only accept a list of identifiers (where each identifier is a |
1358 | lint name). Ensure the attribute is of this form: | |
1359 | ||
1360 | ``` | |
1361 | #![allow(foo)] // ok! | |
1362 | // or: | |
1363 | #![allow(foo, foo2)] // ok! | |
1364 | ``` | |
b039eaaf SL |
1365 | "##, |
1366 | ||
b039eaaf SL |
1367 | E0496: r##" |
1368 | A lifetime name is shadowing another lifetime name. Erroneous code example: | |
1369 | ||
7453a54e | 1370 | ```compile_fail |
b039eaaf SL |
1371 | struct Foo<'a> { |
1372 | a: &'a i32, | |
1373 | } | |
1374 | ||
1375 | impl<'a> Foo<'a> { | |
1376 | fn f<'a>(x: &'a i32) { // error: lifetime name `'a` shadows a lifetime | |
1377 | // name that is already in scope | |
1378 | } | |
1379 | } | |
1380 | ``` | |
1381 | ||
1382 | Please change the name of one of the lifetimes to remove this error. Example: | |
1383 | ||
b039eaaf SL |
1384 | ``` |
1385 | struct Foo<'a> { | |
1386 | a: &'a i32, | |
1387 | } | |
1388 | ||
1389 | impl<'a> Foo<'a> { | |
1390 | fn f<'b>(x: &'b i32) { // ok! | |
1391 | } | |
1392 | } | |
1393 | ||
1394 | fn main() { | |
1395 | } | |
1396 | ``` | |
1397 | "##, | |
1398 | ||
1399 | E0497: r##" | |
1400 | A stability attribute was used outside of the standard library. Erroneous code | |
1401 | example: | |
1402 | ||
7453a54e | 1403 | ```compile_fail |
b039eaaf SL |
1404 | #[stable] // error: stability attributes may not be used outside of the |
1405 | // standard library | |
1406 | fn foo() {} | |
1407 | ``` | |
1408 | ||
1409 | It is not possible to use stability attributes outside of the standard library. | |
1410 | Also, for now, it is not possible to write deprecation messages either. | |
1411 | "##, | |
9346a6ac | 1412 | |
54a0048b SL |
1413 | E0512: r##" |
1414 | Transmute with two differently sized types was attempted. Erroneous code | |
1415 | example: | |
1416 | ||
1417 | ```compile_fail | |
1418 | fn takes_u8(_: u8) {} | |
1419 | ||
1420 | fn main() { | |
1421 | unsafe { takes_u8(::std::mem::transmute(0u16)); } | |
1422 | // error: transmute called with differently sized types | |
1423 | } | |
1424 | ``` | |
1425 | ||
1426 | Please use types with same size or use the expected type directly. Example: | |
1427 | ||
1428 | ``` | |
1429 | fn takes_u8(_: u8) {} | |
1430 | ||
1431 | fn main() { | |
1432 | unsafe { takes_u8(::std::mem::transmute(0i8)); } // ok! | |
1433 | // or: | |
1434 | unsafe { takes_u8(0u8); } // ok! | |
1435 | } | |
1436 | ``` | |
1437 | "##, | |
1438 | ||
92a42be0 | 1439 | E0517: r##" |
7453a54e SL |
1440 | This error indicates that a `#[repr(..)]` attribute was placed on an |
1441 | unsupported item. | |
92a42be0 SL |
1442 | |
1443 | Examples of erroneous code: | |
1444 | ||
7453a54e | 1445 | ```compile_fail |
92a42be0 SL |
1446 | #[repr(C)] |
1447 | type Foo = u8; | |
1448 | ||
1449 | #[repr(packed)] | |
1450 | enum Foo {Bar, Baz} | |
1451 | ||
1452 | #[repr(u8)] | |
1453 | struct Foo {bar: bool, baz: bool} | |
1454 | ||
1455 | #[repr(C)] | |
1456 | impl Foo { | |
7453a54e | 1457 | // ... |
92a42be0 SL |
1458 | } |
1459 | ``` | |
1460 | ||
7453a54e SL |
1461 | * The `#[repr(C)]` attribute can only be placed on structs and enums. |
1462 | * The `#[repr(packed)]` and `#[repr(simd)]` attributes only work on structs. | |
1463 | * The `#[repr(u8)]`, `#[repr(i16)]`, etc attributes only work on enums. | |
92a42be0 SL |
1464 | |
1465 | These attributes do not work on typedefs, since typedefs are just aliases. | |
1466 | ||
1467 | Representations like `#[repr(u8)]`, `#[repr(i64)]` are for selecting the | |
7453a54e SL |
1468 | discriminant size for C-like enums (when there is no associated data, e.g. |
1469 | `enum Color {Red, Blue, Green}`), effectively setting the size of the enum to | |
1470 | the size of the provided type. Such an enum can be cast to a value of the same | |
1471 | type as well. In short, `#[repr(u8)]` makes the enum behave like an integer | |
1472 | with a constrained set of allowed values. | |
92a42be0 SL |
1473 | |
1474 | Only C-like enums can be cast to numerical primitives, so this attribute will | |
1475 | not apply to structs. | |
1476 | ||
1477 | `#[repr(packed)]` reduces padding to make the struct size smaller. The | |
7453a54e SL |
1478 | representation of enums isn't strictly defined in Rust, and this attribute |
1479 | won't work on enums. | |
92a42be0 SL |
1480 | |
1481 | `#[repr(simd)]` will give a struct consisting of a homogenous series of machine | |
1482 | types (i.e. `u8`, `i32`, etc) a representation that permits vectorization via | |
1483 | SIMD. This doesn't make much sense for enums since they don't consist of a | |
1484 | single list of data. | |
1485 | "##, | |
1486 | ||
1487 | E0518: r##" | |
7453a54e SL |
1488 | This error indicates that an `#[inline(..)]` attribute was incorrectly placed |
1489 | on something other than a function or method. | |
92a42be0 SL |
1490 | |
1491 | Examples of erroneous code: | |
1492 | ||
7453a54e | 1493 | ```compile_fail |
92a42be0 SL |
1494 | #[inline(always)] |
1495 | struct Foo; | |
1496 | ||
1497 | #[inline(never)] | |
1498 | impl Foo { | |
7453a54e | 1499 | // ... |
92a42be0 SL |
1500 | } |
1501 | ``` | |
1502 | ||
1503 | `#[inline]` hints the compiler whether or not to attempt to inline a method or | |
1504 | function. By default, the compiler does a pretty good job of figuring this out | |
1505 | itself, but if you feel the need for annotations, `#[inline(always)]` and | |
1506 | `#[inline(never)]` can override or force the compiler's decision. | |
1507 | ||
1508 | If you wish to apply this attribute to all methods in an impl, manually annotate | |
1509 | each method; it is not possible to annotate the entire impl with an `#[inline]` | |
1510 | attribute. | |
1511 | "##, | |
1512 | ||
54a0048b SL |
1513 | E0522: r##" |
1514 | The lang attribute is intended for marking special items that are built-in to | |
1515 | Rust itself. This includes special traits (like `Copy` and `Sized`) that affect | |
1516 | how the compiler behaves, as well as special functions that may be automatically | |
1517 | invoked (such as the handler for out-of-bounds accesses when indexing a slice). | |
1518 | Erroneous code example: | |
1519 | ||
1520 | ```compile_fail | |
1521 | #![feature(lang_items)] | |
1522 | ||
1523 | #[lang = "cookie"] | |
1524 | fn cookie() -> ! { // error: definition of an unknown language item: `cookie` | |
1525 | loop {} | |
1526 | } | |
1527 | ``` | |
1528 | "##, | |
1529 | ||
85aaf69f | 1530 | } |
1a4d82fc | 1531 | |
d9579d0f | 1532 | |
1a4d82fc | 1533 | register_diagnostics! { |
7453a54e | 1534 | // E0006 // merged with E0005 |
c1a9b12d SL |
1535 | // E0134, |
1536 | // E0135, | |
85aaf69f SL |
1537 | E0278, // requirement is not satisfied |
1538 | E0279, // requirement is not satisfied | |
1539 | E0280, // requirement is not satisfied | |
85aaf69f | 1540 | E0284, // cannot resolve type |
7453a54e | 1541 | // E0285, // overflow evaluation builtin bounds |
7453a54e SL |
1542 | // E0300, // unexpanded macro |
1543 | // E0304, // expected signed integer constant | |
1544 | // E0305, // expected constant | |
85aaf69f SL |
1545 | E0311, // thing may not live long enough |
1546 | E0312, // lifetime of reference outlives lifetime of borrowed content | |
1547 | E0313, // lifetime of borrowed pointer outlives lifetime of captured variable | |
1548 | E0314, // closure outlives stack frame | |
1549 | E0315, // cannot invoke closure outside of its lifetime | |
c34b1796 | 1550 | E0316, // nested quantification of lifetimes |
b039eaaf | 1551 | E0453, // overruled by outer forbid |
b039eaaf SL |
1552 | E0473, // dereference of reference outside its lifetime |
1553 | E0474, // captured variable `..` does not outlive the enclosing closure | |
1554 | E0475, // index of slice outside its lifetime | |
1555 | E0476, // lifetime of the source pointer does not outlive lifetime bound... | |
1556 | E0477, // the type `..` does not fulfill the required lifetime... | |
1557 | E0478, // lifetime bound not satisfied | |
1558 | E0479, // the type `..` (provided as the value of a type parameter) is... | |
1559 | E0480, // lifetime of method receiver does not outlive the method call | |
1560 | E0481, // lifetime of function argument does not outlive the function call | |
1561 | E0482, // lifetime of return value does not outlive the function call | |
1562 | E0483, // lifetime of operand does not outlive the operation | |
1563 | E0484, // reference is not valid at the time of borrow | |
1564 | E0485, // automatically reference is not valid at the time of borrow | |
1565 | E0486, // type of expression contains references that are not valid during... | |
1566 | E0487, // unsafe use of destructor: destructor might be called while... | |
1567 | E0488, // lifetime of variable does not enclose its declaration | |
1568 | E0489, // type/lifetime parameter not in scope here | |
1569 | E0490, // a value of type `..` is borrowed for too long | |
1570 | E0491, // in type `..`, reference has a longer lifetime than the data it... | |
b039eaaf | 1571 | E0495, // cannot infer an appropriate lifetime due to conflicting requirements |
1a4d82fc | 1572 | } |