E3060
E3060 — A task that can fail, used in a way that could lose its failure. A task whose body givesResult<T, E>can fail, and itsjoin()gives theT. When the task failed, the join leaves thetasksblock, and the block gives theErr. So the task needs a handle,let h = spawn { .. };, and a join in its own block that always runs after thespawn. The block must give aResult<U, E>with the sameE.
What the compiler reports
Error[E3060] at {{.*}}.vx:[[@LINE+3]]:5: this task can fail with 'i32', so it needs a handle that the `tasks` block joins: `let h = spawn { .. };` and then `h.join()`
The fragments the test suite holds the compiler to. An ellipsis marks text the test does not constrain; the emitted message also carries a source location.
A program that triggers it
//
// Part of the Vx Project, under the Apache License v2.0 with LLVM Exceptions.
// See LICENSE for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
// A `return` in a task gives the value of the task, so it must have the type of the last value
// of the task. A `?` in a task makes a task that can fail, so the task needs a handle.
//
import core::result;
fn plus(n : i32) -> Result<i32, i32> {
return Result<i32, i32>::Ok(n + 1);
}
fn return_of_another_type(c : bool) -> bool {
let r = tasks {
let h = spawn {
if c {
return 1;
}
true
};
h.join()
};
return r;
}
fn question_mark_in_a_task_with_no_handle(n : i32) -> void {
tasks {
spawn {
plus(n)?;
};
}
}
fn main() -> i32 {
return 0;
}
From tests/frontend/fail/tasks_that_end_early_in_a_wrong_way.vx, which asserts this diagnostic on every commit.
Related
A tour of VxThe chapter covering the rule this code enforces.
All diagnosticsEvery code the compiler can emit, grouped by stage.
E3059An
extern declaration of malloc, calloc, realloc, aligned_alloc or free whose type is not C's. The compiler calls these functions too, and it can share only a declaration of C's type. A size is a 64-bit integer: usize, i64 or u64. A pointer is a raw pointer to host memory. free returns nothing.
E3061An impl of a trait does not write a method that the trait requires: one the trait declares with no default body. A call to that method would otherwise fail where it is called, with "method not found", though the fault is in the impl.