Function no_std_compat::intrinsics::const_eval_select
source · pub const fn const_eval_select<ARG, F, G, RET>(
_arg: ARG,
_called_in_const: F,
_called_at_rt: G,
) -> RET
core_intrinsics
)Expand description
Selects which function to call depending on the context.
If this function is evaluated at compile-time, then a call to this
intrinsic will be replaced with a call to called_in_const
. It gets
replaced with a call to called_at_rt
otherwise.
This function is safe to call, but note the stability concerns below.
§Type Requirements
The two functions must be both function items. They cannot be function
pointers or closures. The first function must be a const fn
.
arg
will be the tupled arguments that will be passed to either one of
the two functions, therefore, both functions must accept the same type of
arguments. Both functions must return RET.
§Stability concerns
Rust has not yet decided that const fn
are allowed to tell whether
they run at compile-time or at runtime. Therefore, when using this
intrinsic anywhere that can be reached from stable, it is crucial that
the end-to-end behavior of the stable const fn
is the same for both
modes of execution. (Here, Undefined Behavior is considered “the same”
as any other behavior, so if the function exhibits UB at runtime then
it may do whatever it wants at compile-time.)
Here is an example of how this could cause a problem:
#![feature(const_eval_select)]
#![feature(core_intrinsics)]
use std::intrinsics::const_eval_select;
// Standard library
pub const fn inconsistent() -> i32 {
fn runtime() -> i32 { 1 }
const fn compiletime() -> i32 { 2 }
// ⚠ This code violates the required equivalence of `compiletime`
// and `runtime`.
const_eval_select((), compiletime, runtime)
}
// User Crate
const X: i32 = inconsistent();
let x = inconsistent();
assert_eq!(x, X);
Currently such an assertion would always succeed; until Rust decides otherwise, that principle should not be violated.