Skip to content

Detect type mismatch due to loop that might never iterate with 3 or more return statements #100285

Closed
@lyming2007

Description

@lyming2007

Given the following code:

fn foo(n: i32) -> i32 {
    for i in 0..0 {
       if n < 0 {
        return i;
        } else if n < 10 {
          return 1;
        } else if n < 20 {
          return 2;
        } else if n < 30 {
          return 3;
        } else if n < 40 {
          return 4;
        } else {
          return 5;
        }

    }
}

fn main() {}

The current output is:

error[E0308]: mismatched types
  --> main.rs:2:5
   |
1  |   fn foo(n: i32) -> i32 {
   |                     --- expected `i32` because of return type
2  | /     for i in 0..0 {
3  | |        if n < 0 {
4  | |         return i;
5  | |         } else if n < 10 {
...  |
16 | |
17 | |     }
   | |_____^ expected `i32`, found `()`
   |
note: the function expects a value to always be returned, but loops might run zero times
  --> main.rs:2:5
   |
2  |     for i in 0..0 {
   |     ^^^^^^^^^^^^^ this might have zero elements to iterate on
3  |        if n < 0 {
4  |         return i;
   |         -------- if the loop doesn't execute, this value would never get returned
5  |         } else if n < 10 {
6  |           return 1;
   |           -------- if the loop doesn't execute, this value would never get returned
7  |         } else if n < 20 {
8  |           return 2;
   |           -------- if the loop doesn't execute, this value would never get returned
9  |         } else if n < 30 {
10 |           return 3;
   |           -------- if the loop doesn't execute, this value would never get returned
11 |         } else if n < 40 {
12 |           return 4;
   |           -------- if the loop doesn't execute, this value would never get returned
13 |         } else {
14 |           return 5;
   |           -------- if the loop doesn't execute, this value would never get returned
   = help: return a value for the case when the loop has zero elements to iterate on, or consider changing the return type to account for that possibility

error: aborting due to previous error

Ideally the output should look like:

error[E0308]: mismatched types
  --> main.rs:2:5
   |
1  |   fn foo(n: i32) -> i32 {
   |                     --- expected `i32` because of return type
2  | /     for i in 0..0 {
3  | |        if n < 0 {
4  | |         return i;
5  | |         } else if n < 10 {
...  |
16 | |
17 | |     }
   | |_____^ expected `i32`, found `()`
   |
note: the function expects a value to always be returned, but loops might run zero times
  --> main.rs:2:5
   |
2  |     for i in 0..0 {
   |     ^^^^^^^^^^^^^ this might have zero elements to iterate on
3  |        if n < 0 {
4  |         return i;
   |         -------- if the loop doesn't execute, this value would never get returned
5  |         } else if n < 10 {
6  |           return 1;
   |           -------- if the loop doesn't execute, this value would never get returned
7  |         } else if n < 20 {
8  |           return 2;
   |           -------- if the loop doesn't execute, this value would never get returned
9  |         } else if n < 30 {
10 |           return 3;
   |           -------- if the loop doesn't execute, this value would never get returned
   = note: if the loop doesn't execute, 2 other values would never get returned 
   = help: return a value for the case when the loop has zero elements to iterate on, or consider changing the return type to account for that possibility

error: aborting due to previous error

Metadata

Metadata

Assignees

Labels

A-diagnosticsArea: Messages for errors, warnings, and lintsD-verboseDiagnostics: Too much output caused by a single piece of incorrect code.T-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions