Auto merge of #77354 - ecstatic-morse:const-checking-moar-errors, r=oli-obk

Overhaul const-checking diagnostics

The primary purpose of this PR was to remove `NonConstOp::STOPS_CONST_CHECKING`, which causes any additional errors found by the const-checker to be silenced. I used this flag to preserve diagnostic parity with `qualify_min_const_fn.rs`, which has since been removed.

However, simply removing the flag caused a deluge of errors in some cases, since an error would be emitted any time a local or temporary had a wrong type. To remedy this, I added an alternative system (`DiagnosticImportance`) to silence additional error messages that were likely to distract the user from the underlying issue. When an error of the highest importance occurs, all less important errors are silenced. When no error of the highest importance occurs, all less important errors are emitted after checking is complete. Following the suggestions from the important error is usually enough to fix the less important errors, so this should lead to better UX most of the time.

There's also some unrelated diagnostics improvements in this PR isolated in their own commits. Splitting them out would be possible, but a bit of a pain. This isn't as tidy as some of my other PRs, but it should *only* affect diagnostics, never whether or not something passes const-checking. Note that there are a few trivial exceptions to this, like banning `Yield` in all const-contexts, not just `const fn`.

As always, meant to be reviewed commit-by-commit.

r? `@oli-obk`
This commit is contained in:
bors 2020-10-01 07:38:47 +00:00
commit fc42fb8e70
58 changed files with 594 additions and 607 deletions

View File

@ -18,7 +18,6 @@ E0010: include_str!("./error_codes/E0010.md"),
E0013: include_str!("./error_codes/E0013.md"),
E0014: include_str!("./error_codes/E0014.md"),
E0015: include_str!("./error_codes/E0015.md"),
E0019: include_str!("./error_codes/E0019.md"),
E0023: include_str!("./error_codes/E0023.md"),
E0025: include_str!("./error_codes/E0025.md"),
E0026: include_str!("./error_codes/E0026.md"),
@ -463,6 +462,7 @@ E0776: include_str!("./error_codes/E0776.md"),
;
// E0006, // merged with E0005
// E0008, // cannot bind by-move into a pattern guard
// E0019, merged into E0015
// E0035, merged into E0087/E0089
// E0036, merged into E0087/E0089
// E0068,

View File

@ -1,36 +0,0 @@
A function call isn't allowed in the const's initialization expression
because the expression's value must be known at compile-time.
Erroneous code example:
```compile_fail,E0019
#![feature(box_syntax)]
fn main() {
struct MyOwned;
static STATIC11: Box<MyOwned> = box MyOwned; // error!
}
```
Remember: you can't use a function call inside a const's initialization
expression! However, you can totally use it anywhere else:
```
enum Test {
V1
}
impl Test {
fn func(&self) -> i32 {
12
}
}
fn main() {
const FOO: Test = Test::V1;
FOO.func(); // here is good
let x = FOO.func(); // or even here!
}
```

View File

@ -670,7 +670,7 @@ impl Atom for Local {
}
/// Classifies locals into categories. See `Body::local_kind`.
#[derive(PartialEq, Eq, Debug, HashStable)]
#[derive(Clone, Copy, PartialEq, Eq, Debug, HashStable)]
pub enum LocalKind {
/// User-declared variable binding.
Var,

View File

@ -57,6 +57,16 @@ impl ConstCx<'mir, 'tcx> {
&& self.tcx.features().staged_api
&& is_const_stable_const_fn(self.tcx, self.def_id.to_def_id())
}
/// Returns the function signature of the item being const-checked if it is a `fn` or `const fn`.
pub fn fn_sig(&self) -> Option<&'tcx hir::FnSig<'tcx>> {
// Get this from the HIR map instead of a query to avoid cycle errors.
//
// FIXME: Is this still an issue?
let hir_map = self.tcx.hir();
let hir_id = hir_map.local_def_id_to_hir_id(self.def_id);
hir_map.fn_sig_by_hir_id(hir_id)
}
}
/// Returns `true` if this `DefId` points to one of the official `panic` lang items.

View File

@ -1,8 +1,9 @@
//! Concrete error types for all operations which may be invalid in a certain const context.
use rustc_errors::{struct_span_err, Applicability};
use rustc_errors::{struct_span_err, DiagnosticBuilder};
use rustc_hir as hir;
use rustc_hir::def_id::DefId;
use rustc_middle::mir;
use rustc_session::config::nightly_options;
use rustc_session::parse::feature_err;
use rustc_span::symbol::sym;
@ -10,49 +11,6 @@ use rustc_span::{Span, Symbol};
use super::ConstCx;
/// Emits an error and returns `true` if `op` is not allowed in the given const context.
pub fn non_const<O: NonConstOp>(ccx: &ConstCx<'_, '_>, op: O, span: Span) -> bool {
debug!("illegal_op: op={:?}", op);
let gate = match op.status_in_item(ccx) {
Status::Allowed => return false,
Status::Unstable(gate) if ccx.tcx.features().enabled(gate) => {
let unstable_in_stable = ccx.is_const_stable_const_fn()
&& !super::allow_internal_unstable(ccx.tcx, ccx.def_id.to_def_id(), gate);
if unstable_in_stable {
ccx.tcx.sess
.struct_span_err(
span,
&format!("const-stable function cannot use `#[feature({})]`", gate.as_str()),
)
.span_suggestion(
ccx.body.span,
"if it is not part of the public API, make this function unstably const",
concat!(r#"#[rustc_const_unstable(feature = "...", issue = "...")]"#, '\n').to_owned(),
Applicability::HasPlaceholders,
)
.note("otherwise `#[allow_internal_unstable]` can be used to bypass stability checks")
.emit();
}
return unstable_in_stable;
}
Status::Unstable(gate) => Some(gate),
Status::Forbidden => None,
};
if ccx.tcx.sess.opts.debugging_opts.unleash_the_miri_inside_of_you {
ccx.tcx.sess.miri_unleashed_feature(span, gate);
return false;
}
op.emit_error(ccx, span);
true
}
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub enum Status {
Allowed,
@ -60,63 +18,44 @@ pub enum Status {
Forbidden,
}
#[derive(Clone, Copy)]
pub enum DiagnosticImportance {
/// An operation that must be removed for const-checking to pass.
Primary,
/// An operation that causes const-checking to fail, but is usually a side-effect of a `Primary` operation elsewhere.
Secondary,
}
/// An operation that is not *always* allowed in a const context.
pub trait NonConstOp: std::fmt::Debug {
const STOPS_CONST_CHECKING: bool = false;
/// Returns an enum indicating whether this operation is allowed within the given item.
fn status_in_item(&self, _ccx: &ConstCx<'_, '_>) -> Status {
Status::Forbidden
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
let mut err = struct_span_err!(
ccx.tcx.sess,
span,
E0019,
"{} contains unimplemented expression type",
ccx.const_kind()
);
if let Status::Unstable(gate) = self.status_in_item(ccx) {
if !ccx.tcx.features().enabled(gate) && nightly_options::is_nightly_build() {
err.help(&format!("add `#![feature({})]` to the crate attributes to enable", gate));
}
}
if ccx.tcx.sess.teach(&err.get_code().unwrap()) {
err.note(
"A function call isn't allowed in the const's initialization expression \
because the expression's value must be known at compile-time.",
);
err.note(
"Remember: you can't use a function call inside a const's initialization \
expression! However, you can use it anywhere else.",
);
}
err.emit();
fn importance(&self) -> DiagnosticImportance {
DiagnosticImportance::Primary
}
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx>;
}
#[derive(Debug)]
pub struct Abort;
impl NonConstOp for Abort {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
mcf_status_in_item(ccx)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(ccx, span, "abort is not stable in const fn")
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
mcf_build_error(ccx, span, "abort is not stable in const fn")
}
}
#[derive(Debug)]
pub struct FloatingPointOp;
impl NonConstOp for FloatingPointOp {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
if ccx.const_kind() == hir::ConstContext::ConstFn {
Status::Unstable(sym::const_fn_floating_point_arithmetic)
@ -125,28 +64,13 @@ impl NonConstOp for FloatingPointOp {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_fn_floating_point_arithmetic,
span,
&format!("floating point arithmetic is not allowed in {}s", ccx.const_kind()),
)
.emit();
}
}
#[derive(Debug)]
pub struct NonPrimitiveOp;
impl NonConstOp for NonPrimitiveOp {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
mcf_status_in_item(ccx)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(ccx, span, "only int, `bool` and `char` operations are stable in const fn")
}
}
@ -154,10 +78,8 @@ impl NonConstOp for NonPrimitiveOp {
#[derive(Debug)]
pub struct FnCallIndirect;
impl NonConstOp for FnCallIndirect {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
let mut err =
ccx.tcx.sess.struct_span_err(span, "function pointers are not allowed in const fn");
err.emit();
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
ccx.tcx.sess.struct_span_err(span, "function pointers are not allowed in const fn")
}
}
@ -165,16 +87,15 @@ impl NonConstOp for FnCallIndirect {
#[derive(Debug)]
pub struct FnCallNonConst(pub DefId);
impl NonConstOp for FnCallNonConst {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
let mut err = struct_span_err!(
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
struct_span_err!(
ccx.tcx.sess,
span,
E0015,
"calls in {}s are limited to constant functions, \
tuple structs and tuple variants",
ccx.const_kind(),
);
err.emit();
)
}
}
@ -185,7 +106,7 @@ impl NonConstOp for FnCallNonConst {
pub struct FnCallUnstable(pub DefId, pub Option<Symbol>);
impl NonConstOp for FnCallUnstable {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let FnCallUnstable(def_id, feature) = *self;
let mut err = ccx.tcx.sess.struct_span_err(
@ -203,15 +124,14 @@ impl NonConstOp for FnCallUnstable {
));
}
}
err.emit();
err
}
}
#[derive(Debug)]
pub struct FnPtrCast;
impl NonConstOp for FnPtrCast {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
if ccx.const_kind() != hir::ConstContext::ConstFn {
Status::Allowed
@ -220,37 +140,32 @@ impl NonConstOp for FnPtrCast {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_fn_fn_ptr_basics,
span,
&format!("function pointer casts are not allowed in {}s", ccx.const_kind()),
)
.emit()
}
}
#[derive(Debug)]
pub struct Generator;
impl NonConstOp for Generator {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
// FIXME: This means generator-only MIR is only forbidden in const fn. This is for
// compatibility with the old code. Such MIR should be forbidden everywhere.
mcf_status_in_item(ccx)
fn status_in_item(&self, _: &ConstCx<'_, '_>) -> Status {
Status::Forbidden
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(ccx, span, "const fn generators are unstable");
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
ccx.tcx.sess.struct_span_err(span, "Generators and `async` functions cannot be `const`")
}
}
#[derive(Debug)]
pub struct HeapAllocation;
impl NonConstOp for HeapAllocation {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = struct_span_err!(
ccx.tcx.sess,
span,
@ -267,38 +182,48 @@ impl NonConstOp for HeapAllocation {
be done at compile time.",
);
}
err.emit();
err
}
}
#[derive(Debug)]
pub struct InlineAsm;
impl NonConstOp for InlineAsm {}
impl NonConstOp for InlineAsm {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
struct_span_err!(
ccx.tcx.sess,
span,
E0015,
"inline assembly is not allowed in {}s",
ccx.const_kind()
)
}
}
#[derive(Debug)]
pub struct LiveDrop {
pub dropped_at: Option<Span>,
}
impl NonConstOp for LiveDrop {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
let mut diagnostic = struct_span_err!(
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = struct_span_err!(
ccx.tcx.sess,
span,
E0493,
"destructors cannot be evaluated at compile-time"
);
diagnostic.span_label(span, format!("{}s cannot evaluate destructors", ccx.const_kind()));
err.span_label(span, format!("{}s cannot evaluate destructors", ccx.const_kind()));
if let Some(span) = self.dropped_at {
diagnostic.span_label(span, "value is dropped here");
err.span_label(span, "value is dropped here");
}
diagnostic.emit();
err
}
}
#[derive(Debug)]
pub struct CellBorrow;
impl NonConstOp for CellBorrow {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
struct_span_err!(
ccx.tcx.sess,
span,
@ -306,7 +231,6 @@ impl NonConstOp for CellBorrow {
"cannot borrow a constant which may contain \
interior mutability, create a static instead"
)
.emit();
}
}
@ -322,7 +246,7 @@ impl NonConstOp for MutBorrow {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = if ccx.const_kind() == hir::ConstContext::ConstFn {
feature_err(
&ccx.tcx.sess.parse_sess,
@ -353,7 +277,7 @@ impl NonConstOp for MutBorrow {
static mut or a global UnsafeCell.",
);
}
err.emit();
err
}
}
@ -370,14 +294,13 @@ impl NonConstOp for MutAddressOf {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_mut_refs,
span,
&format!("`&raw mut` is not allowed in {}s", ccx.const_kind()),
)
.emit();
}
}
@ -387,6 +310,20 @@ impl NonConstOp for MutDeref {
fn status_in_item(&self, _: &ConstCx<'_, '_>) -> Status {
Status::Unstable(sym::const_mut_refs)
}
fn importance(&self) -> DiagnosticImportance {
// Usually a side-effect of a `MutBorrow` somewhere.
DiagnosticImportance::Secondary
}
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_mut_refs,
span,
&format!("mutation through a reference is not allowed in {}s", ccx.const_kind()),
)
}
}
#[derive(Debug)]
@ -396,21 +333,20 @@ impl NonConstOp for Panic {
Status::Unstable(sym::const_panic)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_panic,
span,
&format!("panicking in {}s is unstable", ccx.const_kind()),
)
.emit();
}
}
#[derive(Debug)]
pub struct RawPtrComparison;
impl NonConstOp for RawPtrComparison {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = ccx
.tcx
.sess
@ -419,7 +355,7 @@ impl NonConstOp for RawPtrComparison {
"see issue #53020 <https://github.com/rust-lang/rust/issues/53020> \
for more information",
);
err.emit();
err
}
}
@ -430,14 +366,13 @@ impl NonConstOp for RawPtrDeref {
Status::Unstable(sym::const_raw_ptr_deref)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_raw_ptr_deref,
span,
&format!("dereferencing raw pointers in {}s is unstable", ccx.const_kind(),),
)
.emit();
}
}
@ -448,14 +383,13 @@ impl NonConstOp for RawPtrToIntCast {
Status::Unstable(sym::const_raw_ptr_to_usize_cast)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_raw_ptr_to_usize_cast,
span,
&format!("casting pointers to integers in {}s is unstable", ccx.const_kind(),),
)
.emit();
}
}
@ -471,7 +405,7 @@ impl NonConstOp for StaticAccess {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = struct_span_err!(
ccx.tcx.sess,
span,
@ -489,7 +423,7 @@ impl NonConstOp for StaticAccess {
);
err.help("To fix this, the value can be extracted to a `const` and then used.");
}
err.emit();
err
}
}
@ -497,7 +431,7 @@ impl NonConstOp for StaticAccess {
#[derive(Debug)]
pub struct ThreadLocalAccess;
impl NonConstOp for ThreadLocalAccess {
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
struct_span_err!(
ccx.tcx.sess,
span,
@ -505,15 +439,12 @@ impl NonConstOp for ThreadLocalAccess {
"thread-local statics cannot be \
accessed at compile-time"
)
.emit();
}
}
#[derive(Debug)]
pub struct Transmute;
impl NonConstOp for Transmute {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
if ccx.const_kind() != hir::ConstContext::ConstFn {
Status::Allowed
@ -522,15 +453,15 @@ impl NonConstOp for Transmute {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
feature_err(
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
let mut err = feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_fn_transmute,
span,
&format!("`transmute` is not allowed in {}s", ccx.const_kind()),
)
.note("`transmute` is only allowed in constants and statics for now")
.emit();
);
err.note("`transmute` is only allowed in constants and statics for now");
err
}
}
@ -546,14 +477,13 @@ impl NonConstOp for UnionAccess {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_fn_union,
span,
"unions in const fn are unstable",
)
.emit();
}
}
@ -567,12 +497,12 @@ impl NonConstOp for UnsizingCast {
mcf_status_in_item(ccx)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
mcf_build_error(
ccx,
span,
"unsizing casts to types besides slices are not allowed in const fn",
);
)
}
}
@ -581,29 +511,42 @@ pub mod ty {
use super::*;
#[derive(Debug)]
pub struct MutRef;
pub struct MutRef(pub mir::LocalKind);
impl NonConstOp for MutRef {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, _ccx: &ConstCx<'_, '_>) -> Status {
Status::Unstable(sym::const_mut_refs)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn importance(&self) -> DiagnosticImportance {
match self.0 {
mir::LocalKind::Var | mir::LocalKind::Temp => DiagnosticImportance::Secondary,
mir::LocalKind::ReturnPointer | mir::LocalKind::Arg => {
DiagnosticImportance::Primary
}
}
}
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_mut_refs,
span,
&format!("mutable references are not allowed in {}s", ccx.const_kind()),
)
.emit()
}
}
#[derive(Debug)]
pub struct FnPtr;
pub struct FnPtr(pub mir::LocalKind);
impl NonConstOp for FnPtr {
const STOPS_CONST_CHECKING: bool = true;
fn importance(&self) -> DiagnosticImportance {
match self.0 {
mir::LocalKind::Var | mir::LocalKind::Temp => DiagnosticImportance::Secondary,
mir::LocalKind::ReturnPointer | mir::LocalKind::Arg => {
DiagnosticImportance::Primary
}
}
}
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
if ccx.const_kind() != hir::ConstContext::ConstFn {
@ -613,46 +556,50 @@ pub mod ty {
}
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_fn_fn_ptr_basics,
span,
&format!("function pointers cannot appear in {}s", ccx.const_kind()),
)
.emit()
}
}
#[derive(Debug)]
pub struct ImplTrait;
impl NonConstOp for ImplTrait {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
mcf_status_in_item(ccx)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(ccx, span, "`impl Trait` in const fn is unstable");
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
mcf_build_error(ccx, span, "`impl Trait` in const fn is unstable")
}
}
#[derive(Debug)]
pub struct TraitBound;
pub struct TraitBound(pub mir::LocalKind);
impl NonConstOp for TraitBound {
const STOPS_CONST_CHECKING: bool = true;
fn importance(&self) -> DiagnosticImportance {
match self.0 {
mir::LocalKind::Var | mir::LocalKind::Temp => DiagnosticImportance::Secondary,
mir::LocalKind::ReturnPointer | mir::LocalKind::Arg => {
DiagnosticImportance::Primary
}
}
}
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
mcf_status_in_item(ccx)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
mcf_emit_error(
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
mcf_build_error(
ccx,
span,
"trait bounds other than `Sized` on const fn parameters are unstable",
);
)
}
}
@ -660,20 +607,17 @@ pub mod ty {
#[derive(Debug)]
pub struct TraitBoundNotConst;
impl NonConstOp for TraitBoundNotConst {
const STOPS_CONST_CHECKING: bool = true;
fn status_in_item(&self, _: &ConstCx<'_, '_>) -> Status {
Status::Unstable(sym::const_trait_bound_opt_out)
}
fn emit_error(&self, ccx: &ConstCx<'_, '_>, span: Span) {
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
feature_err(
&ccx.tcx.sess.parse_sess,
sym::const_trait_bound_opt_out,
span,
"`?const Trait` syntax is unstable",
)
.emit()
}
}
}
@ -686,12 +630,12 @@ fn mcf_status_in_item(ccx: &ConstCx<'_, '_>) -> Status {
}
}
fn mcf_emit_error(ccx: &ConstCx<'_, '_>, span: Span, msg: &str) {
struct_span_err!(ccx.tcx.sess, span, E0723, "{}", msg)
.note(
"see issue #57563 <https://github.com/rust-lang/rust/issues/57563> \
fn mcf_build_error(ccx: &ConstCx<'_, 'tcx>, span: Span, msg: &str) -> DiagnosticBuilder<'tcx> {
let mut err = struct_span_err!(ccx.tcx.sess, span, E0723, "{}", msg);
err.note(
"see issue #57563 <https://github.com/rust-lang/rust/issues/57563> \
for more information",
)
.help("add `#![feature(const_fn)]` to the crate attributes to enable")
.emit();
);
err.help("add `#![feature(const_fn)]` to the crate attributes to enable");
err
}

View File

@ -4,7 +4,7 @@ use rustc_middle::mir::{self, BasicBlock, Location};
use rustc_middle::ty::TyCtxt;
use rustc_span::Span;
use super::ops;
use super::ops::{self, NonConstOp};
use super::qualifs::{NeedsDrop, Qualif};
use super::validation::Qualifs;
use super::ConstCx;
@ -56,7 +56,7 @@ impl std::ops::Deref for CheckLiveDrops<'mir, 'tcx> {
impl CheckLiveDrops<'mir, 'tcx> {
fn check_live_drop(&self, span: Span) {
ops::non_const(self.ccx, ops::LiveDrop { dropped_at: None }, span);
ops::LiveDrop { dropped_at: None }.build_error(self.ccx, span).emit();
}
}

View File

@ -1,8 +1,8 @@
//! The `Visitor` responsible for actually checking a `mir::Body` for invalid operations.
use rustc_errors::struct_span_err;
use rustc_hir::{self as hir, LangItem};
use rustc_hir::{def_id::DefId, HirId};
use rustc_errors::{struct_span_err, Applicability, Diagnostic};
use rustc_hir::def_id::DefId;
use rustc_hir::{self as hir, HirId, LangItem};
use rustc_infer::infer::TyCtxtInferExt;
use rustc_middle::mir::visit::{MutatingUseContext, NonMutatingUseContext, PlaceContext, Visitor};
use rustc_middle::mir::*;
@ -11,13 +11,14 @@ use rustc_middle::ty::subst::GenericArgKind;
use rustc_middle::ty::{
self, adjustment::PointerCast, Instance, InstanceDef, Ty, TyCtxt, TypeAndMut,
};
use rustc_span::{sym, Span};
use rustc_span::{sym, Span, Symbol};
use rustc_trait_selection::traits::error_reporting::InferCtxtExt;
use rustc_trait_selection::traits::{self, TraitEngine};
use std::mem;
use std::ops::Deref;
use super::ops::{self, NonConstOp};
use super::ops::{self, NonConstOp, Status};
use super::qualifs::{self, CustomEq, HasMutInterior, NeedsDrop};
use super::resolver::FlowSensitiveAnalysis;
use super::{is_lang_panic_fn, ConstCx, Qualif};
@ -180,7 +181,8 @@ pub struct Validator<'mir, 'tcx> {
/// The span of the current statement.
span: Span,
const_checking_stopped: bool,
error_emitted: bool,
secondary_errors: Vec<Diagnostic>,
}
impl Deref for Validator<'mir, 'tcx> {
@ -197,13 +199,21 @@ impl Validator<'mir, 'tcx> {
span: ccx.body.span,
ccx,
qualifs: Default::default(),
const_checking_stopped: false,
error_emitted: false,
secondary_errors: Vec::new(),
}
}
pub fn check_body(&mut self) {
let ConstCx { tcx, body, def_id, .. } = *self.ccx;
// `async` functions cannot be `const fn`. This is checked during AST lowering, so there's
// no need to emit duplicate errors here.
if is_async_fn(self.ccx) || body.generator_kind.is_some() {
tcx.sess.delay_span_bug(body.span, "`async` functions cannot be `const fn`");
return;
}
// The local type and predicate checks are not free and only relevant for `const fn`s.
if self.const_kind() == hir::ConstContext::ConstFn {
// Prevent const trait methods from being annotated as `stable`.
@ -223,20 +233,21 @@ impl Validator<'mir, 'tcx> {
self.check_item_predicates();
for local in &body.local_decls {
if local.internal {
for (idx, local) in body.local_decls.iter_enumerated() {
// Handle the return place below.
if idx == RETURN_PLACE || local.internal {
continue;
}
self.span = local.source_info.span;
self.check_local_or_return_ty(local.ty);
self.check_local_or_return_ty(local.ty, idx);
}
// impl trait is gone in MIR, so check the return type of a const fn by its signature
// instead of the type of the return place.
self.span = body.local_decls[RETURN_PLACE].source_info.span;
let return_ty = tcx.fn_sig(def_id).output();
self.check_local_or_return_ty(return_ty.skip_binder());
self.check_local_or_return_ty(return_ty.skip_binder(), RETURN_PLACE);
}
self.visit_body(&body);
@ -250,6 +261,17 @@ impl Validator<'mir, 'tcx> {
let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
check_return_ty_is_sync(tcx, &body, hir_id);
}
// If we got through const-checking without emitting any "primary" errors, emit any
// "secondary" errors if they occurred.
let secondary_errors = mem::take(&mut self.secondary_errors);
if !self.error_emitted {
for error in secondary_errors {
self.tcx.sess.diagnostic().emit_diagnostic(&error);
}
} else {
assert!(self.tcx.sess.has_errors());
}
}
pub fn qualifs_in_return_place(&mut self) -> ConstQualifs {
@ -264,15 +286,38 @@ impl Validator<'mir, 'tcx> {
/// Emits an error at the given `span` if an expression cannot be evaluated in the current
/// context.
pub fn check_op_spanned<O: NonConstOp>(&mut self, op: O, span: Span) {
// HACK: This is for strict equivalence with the old `qualify_min_const_fn` pass, which
// only emitted one error per function. It should be removed and the test output updated.
if self.const_checking_stopped {
let gate = match op.status_in_item(self.ccx) {
Status::Allowed => return,
Status::Unstable(gate) if self.tcx.features().enabled(gate) => {
let unstable_in_stable = self.ccx.is_const_stable_const_fn()
&& !super::allow_internal_unstable(self.tcx, self.def_id.to_def_id(), gate);
if unstable_in_stable {
emit_unstable_in_stable_error(self.ccx, span, gate);
}
return;
}
Status::Unstable(gate) => Some(gate),
Status::Forbidden => None,
};
if self.tcx.sess.opts.debugging_opts.unleash_the_miri_inside_of_you {
self.tcx.sess.miri_unleashed_feature(span, gate);
return;
}
let err_emitted = ops::non_const(self.ccx, op, span);
if err_emitted && O::STOPS_CONST_CHECKING {
self.const_checking_stopped = true;
let mut err = op.build_error(self.ccx, span);
assert!(err.is_error());
match op.importance() {
ops::DiagnosticImportance::Primary => {
self.error_emitted = true;
err.emit();
}
ops::DiagnosticImportance::Secondary => err.buffer(&mut self.secondary_errors),
}
}
@ -284,7 +329,9 @@ impl Validator<'mir, 'tcx> {
self.check_op_spanned(ops::StaticAccess, span)
}
fn check_local_or_return_ty(&mut self, ty: Ty<'tcx>) {
fn check_local_or_return_ty(&mut self, ty: Ty<'tcx>, local: Local) {
let kind = self.body.local_kind(local);
for ty in ty.walk() {
let ty = match ty.unpack() {
GenericArgKind::Type(ty) => ty,
@ -295,20 +342,20 @@ impl Validator<'mir, 'tcx> {
};
match *ty.kind() {
ty::Ref(_, _, hir::Mutability::Mut) => self.check_op(ops::ty::MutRef),
ty::Ref(_, _, hir::Mutability::Mut) => self.check_op(ops::ty::MutRef(kind)),
ty::Opaque(..) => self.check_op(ops::ty::ImplTrait),
ty::FnPtr(..) => self.check_op(ops::ty::FnPtr),
ty::FnPtr(..) => self.check_op(ops::ty::FnPtr(kind)),
ty::Dynamic(preds, _) => {
for pred in preds.iter() {
match pred.skip_binder() {
ty::ExistentialPredicate::AutoTrait(_)
| ty::ExistentialPredicate::Projection(_) => {
self.check_op(ops::ty::TraitBound)
self.check_op(ops::ty::TraitBound(kind))
}
ty::ExistentialPredicate::Trait(trait_ref) => {
if Some(trait_ref.def_id) != self.tcx.lang_items().sized_trait() {
self.check_op(ops::ty::TraitBound)
self.check_op(ops::ty::TraitBound(kind))
}
}
}
@ -353,15 +400,19 @@ impl Validator<'mir, 'tcx> {
let def = generics.type_param(p, tcx);
let span = tcx.def_span(def.def_id);
// These are part of the function signature, so treat them like
// arguments when determining importance.
let kind = LocalKind::Arg;
if constness == hir::Constness::Const {
self.check_op_spanned(ops::ty::TraitBound, span);
self.check_op_spanned(ops::ty::TraitBound(kind), span);
} else if !tcx.features().const_fn
|| self.ccx.is_const_stable_const_fn()
{
// HACK: We shouldn't need the conditional above, but trait
// bounds on containing impl blocks are wrongly being marked as
// "not-const".
self.check_op_spanned(ops::ty::TraitBound, span);
self.check_op_spanned(ops::ty::TraitBound(kind), span);
}
}
// other kinds of bounds are either tautologies
@ -877,3 +928,31 @@ fn place_as_reborrow(
fn is_int_bool_or_char(ty: Ty<'_>) -> bool {
ty.is_bool() || ty.is_integral() || ty.is_char()
}
fn is_async_fn(ccx: &ConstCx<'_, '_>) -> bool {
ccx.fn_sig().map_or(false, |sig| sig.header.asyncness == hir::IsAsync::Async)
}
fn emit_unstable_in_stable_error(ccx: &ConstCx<'_, '_>, span: Span, gate: Symbol) {
let attr_span = ccx.fn_sig().map_or(ccx.body.span, |sig| sig.span.shrink_to_lo());
ccx.tcx
.sess
.struct_span_err(
span,
&format!("const-stable function cannot use `#[feature({})]`", gate.as_str()),
)
.span_suggestion(
attr_span,
"if it is not part of the public API, make this function unstably const",
concat!(r#"#[rustc_const_unstable(feature = "...", issue = "...")]"#, '\n').to_owned(),
Applicability::HasPlaceholders,
)
.span_suggestion(
attr_span,
"otherwise `#[allow_internal_unstable]` can be used to bypass stability checks",
format!("#[allow_internal_unstable({})]\n", gate),
Applicability::MaybeIncorrect,
)
.emit();
}

View File

@ -6,6 +6,8 @@ const fn f(x: usize) -> usize {
let mut sum = 0;
for i in 0..x {
//~^ ERROR mutable references
//~| ERROR calls in constant functions
//~| ERROR calls in constant functions
//~| ERROR E0080
//~| ERROR E0744
sum += i;

View File

@ -3,4 +3,3 @@
pub const async fn x() {}
//~^ ERROR functions cannot be both `const` and `async`
//~| ERROR `impl Trait` in const fn is unstable

View File

@ -7,15 +7,5 @@ LL | pub const async fn x() {}
| | `async` because of this
| `const` because of this
error[E0723]: `impl Trait` in const fn is unstable
--> $DIR/no-const-async.rs:4:24
|
LL | pub const async fn x() {}
| ^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error: aborting due to previous error
error: aborting due to 2 previous errors
For more information about this error, try `rustc --explain E0723`.

View File

@ -78,7 +78,6 @@ struct MyOwned;
static STATIC11: Box<MyOwned> = box MyOwned;
//~^ ERROR allocations are not allowed in statics
//~| ERROR static contains unimplemented expression type
static mut STATIC12: UnsafeStruct = UnsafeStruct;
@ -93,16 +92,12 @@ static mut STATIC14: SafeStruct = SafeStruct {
static STATIC15: &'static [Box<MyOwned>] = &[
box MyOwned, //~ ERROR allocations are not allowed in statics
//~| ERROR contains unimplemented expression
box MyOwned, //~ ERROR allocations are not allowed in statics
//~| ERROR contains unimplemented expression
];
static STATIC16: (&'static Box<MyOwned>, &'static Box<MyOwned>) = (
&box MyOwned, //~ ERROR allocations are not allowed in statics
//~| ERROR contains unimplemented expression
&box MyOwned, //~ ERROR allocations are not allowed in statics
//~| ERROR contains unimplemented expression
);
static mut STATIC17: SafeEnum = SafeEnum::Variant1;
@ -110,11 +105,9 @@ static mut STATIC17: SafeEnum = SafeEnum::Variant1;
static STATIC19: Box<isize> =
box 3;
//~^ ERROR allocations are not allowed in statics
//~| ERROR contains unimplemented expression
pub fn main() {
let y = { static x: Box<isize> = box 3; x };
//~^ ERROR allocations are not allowed in statics
//~| ERROR cannot move out of static item
//~| ERROR contains unimplemented expression
}

View File

@ -15,92 +15,44 @@ error[E0010]: allocations are not allowed in statics
LL | static STATIC11: Box<MyOwned> = box MyOwned;
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:79:37
|
LL | static STATIC11: Box<MyOwned> = box MyOwned;
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0015]: calls in statics are limited to constant functions, tuple structs and tuple variants
--> $DIR/check-static-values-constraints.rs:90:32
--> $DIR/check-static-values-constraints.rs:89:32
|
LL | field2: SafeEnum::Variant4("str".to_string())
| ^^^^^^^^^^^^^^^^^
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:94:5
|
LL | box MyOwned,
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:95:5
|
LL | box MyOwned,
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:95:9
|
LL | box MyOwned,
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:97:5
|
LL | box MyOwned,
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:97:9
|
LL | box MyOwned,
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:102:6
--> $DIR/check-static-values-constraints.rs:99:6
|
LL | &box MyOwned,
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:102:10
|
LL | &box MyOwned,
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:104:6
--> $DIR/check-static-values-constraints.rs:100:6
|
LL | &box MyOwned,
| ^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:104:10
|
LL | &box MyOwned,
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:111:5
--> $DIR/check-static-values-constraints.rs:106:5
|
LL | box 3;
| ^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:111:9
|
LL | box 3;
| ^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0507]: cannot move out of static item `x`
--> $DIR/check-static-values-constraints.rs:116:45
--> $DIR/check-static-values-constraints.rs:110:45
|
LL | let y = { static x: Box<isize> = box 3; x };
| ^
@ -109,20 +61,12 @@ LL | let y = { static x: Box<isize> = box 3; x };
| help: consider borrowing here: `&x`
error[E0010]: allocations are not allowed in statics
--> $DIR/check-static-values-constraints.rs:116:38
--> $DIR/check-static-values-constraints.rs:110:38
|
LL | let y = { static x: Box<isize> = box 3; x };
| ^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/check-static-values-constraints.rs:116:42
|
LL | let y = { static x: Box<isize> = box 3; x };
| ^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to 10 previous errors
error: aborting due to 17 previous errors
Some errors have detailed explanations: E0010, E0015, E0019, E0493, E0507.
Some errors have detailed explanations: E0010, E0015, E0493, E0507.
For more information about an error, try `rustc --explain E0010`.

View File

@ -2,8 +2,6 @@ const WRITE: () = unsafe {
*std::ptr::null_mut() = 0;
//~^ ERROR dereferencing raw pointers in constants is unstable
//~| HELP add `#![feature(const_raw_ptr_deref)]` to the crate attributes to enable
//~| ERROR constant contains unimplemented expression type
//~| HELP add `#![feature(const_mut_refs)]` to the crate attributes to enable
};
fn main() {}

View File

@ -7,15 +7,6 @@ LL | *std::ptr::null_mut() = 0;
= note: see issue #51911 <https://github.com/rust-lang/rust/issues/51911> for more information
= help: add `#![feature(const_raw_ptr_deref)]` to the crate attributes to enable
error[E0019]: constant contains unimplemented expression type
--> $DIR/const-suggest-feature.rs:2:5
|
LL | *std::ptr::null_mut() = 0;
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0019, E0658.
For more information about an error, try `rustc --explain E0019`.
For more information about this error, try `rustc --explain E0658`.

View File

@ -1,7 +1,7 @@
// New test for #53818: modifying static memory at compile-time is not allowed.
// The test should never compile successfully
#![feature(const_raw_ptr_deref)]
#![feature(const_raw_ptr_deref, const_mut_refs)]
use std::cell::UnsafeCell;
@ -13,7 +13,7 @@ unsafe impl Sync for Foo {}
static FOO: Foo = Foo(UnsafeCell::new(42));
static BAR: () = unsafe {
*FOO.0.get() = 5; //~ ERROR contains unimplemented expression type
*FOO.0.get() = 5; //~ ERROR
};
fn main() {}

View File

@ -1,11 +1,9 @@
error[E0019]: static contains unimplemented expression type
error[E0080]: could not evaluate static initializer
--> $DIR/assign-to-static-within-other-static-2.rs:16:5
|
LL | *FOO.0.get() = 5;
| ^^^^^^^^^^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
| ^^^^^^^^^^^^^^^^ modifying a static's initial value from another static's initializer
error: aborting due to previous error
For more information about this error, try `rustc --explain E0019`.
For more information about this error, try `rustc --explain E0080`.

View File

@ -12,14 +12,9 @@ unsafe impl Sync for Foo {}
static FOO: Foo = Foo(UnsafeCell::new(42));
fn foo() {}
static BAR: () = unsafe {
*FOO.0.get() = 5;
//~^ contains unimplemented expression
foo();
//~^ ERROR calls in statics are limited to constant functions, tuple structs and tuple variants
//~^ mutation through a reference
};
fn main() {

View File

@ -1,18 +1,12 @@
error[E0019]: static contains unimplemented expression type
--> $DIR/mod-static-with-const-fn.rs:18:5
error[E0658]: mutation through a reference is not allowed in statics
--> $DIR/mod-static-with-const-fn.rs:16:5
|
LL | *FOO.0.get() = 5;
| ^^^^^^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0015]: calls in statics are limited to constant functions, tuple structs and tuple variants
--> $DIR/mod-static-with-const-fn.rs:21:5
|
LL | foo();
| ^^^^^
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0015, E0019.
For more information about an error, try `rustc --explain E0015`.
For more information about this error, try `rustc --explain E0658`.

View File

@ -3,6 +3,7 @@
const extern fn unsize(x: &[u8; 3]) -> &[u8] { x }
const unsafe extern "C" fn closure() -> fn() { || {} }
//~^ ERROR function pointer
//~| ERROR function pointer cast
const unsafe extern fn use_float() { 1.0 + 1.0; }
//~^ ERROR floating point arithmetic
const extern "C" fn ptr_cast(val: *const u8) { val as usize; }

View File

@ -7,8 +7,17 @@ LL | const unsafe extern "C" fn closure() -> fn() { || {} }
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/const-extern-fn-min-const-fn.rs:4:48
|
LL | const unsafe extern "C" fn closure() -> fn() { || {} }
| ^^^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: floating point arithmetic is not allowed in constant functions
--> $DIR/const-extern-fn-min-const-fn.rs:6:38
--> $DIR/const-extern-fn-min-const-fn.rs:7:38
|
LL | const unsafe extern fn use_float() { 1.0 + 1.0; }
| ^^^^^^^^^
@ -17,7 +26,7 @@ LL | const unsafe extern fn use_float() { 1.0 + 1.0; }
= help: add `#![feature(const_fn_floating_point_arithmetic)]` to the crate attributes to enable
error[E0658]: casting pointers to integers in constant functions is unstable
--> $DIR/const-extern-fn-min-const-fn.rs:8:48
--> $DIR/const-extern-fn-min-const-fn.rs:9:48
|
LL | const extern "C" fn ptr_cast(val: *const u8) { val as usize; }
| ^^^^^^^^^^^^
@ -25,6 +34,6 @@ LL | const extern "C" fn ptr_cast(val: *const u8) { val as usize; }
= note: see issue #51910 <https://github.com/rust-lang/rust/issues/51910> for more information
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
error: aborting due to 3 previous errors
error: aborting due to 4 previous errors
For more information about this error, try `rustc --explain E0658`.

View File

@ -6,23 +6,21 @@ struct S {
impl S {
const fn foo(&mut self, x: u32) {
//~^ ERROR mutable references
//~^ ERROR mutable reference
self.state = x;
}
}
const FOO: S = {
let mut s = S { state: 42 };
s.foo(3); //~ ERROR mutable references are not allowed in constants
s.foo(3); //~ ERROR mutable reference
s
};
type Array = [u32; {
let mut x = 2;
let y = &mut x;
//~^ ERROR mutable references are not allowed in constants
let y = &mut x; //~ ERROR mutable reference
*y = 42;
//~^ ERROR constant contains unimplemented expression type
*y
}];

View File

@ -19,15 +19,7 @@ error[E0764]: mutable references are not allowed in constants
LL | let y = &mut x;
| ^^^^^^ `&mut` is only allowed in `const fn`
error[E0019]: constant contains unimplemented expression type
--> $DIR/const_let_assign3.rs:24:5
|
LL | *y = 42;
| ^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to 3 previous errors
error: aborting due to 4 previous errors
Some errors have detailed explanations: E0019, E0658, E0764.
For more information about an error, try `rustc --explain E0019`.
Some errors have detailed explanations: E0658, E0764.
For more information about an error, try `rustc --explain E0658`.

View File

@ -1,6 +1,6 @@
#![feature(llvm_asm)]
const _: () = unsafe { llvm_asm!("nop") };
//~^ ERROR contains unimplemented expression type
//~^ ERROR inline assembly
fn main() {}

View File

@ -1,4 +1,4 @@
error[E0019]: constant contains unimplemented expression type
error[E0015]: inline assembly is not allowed in constants
--> $DIR/inline_asm.rs:3:24
|
LL | const _: () = unsafe { llvm_asm!("nop") };
@ -8,4 +8,4 @@ LL | const _: () = unsafe { llvm_asm!("nop") };
error: aborting due to previous error
For more information about this error, try `rustc --explain E0019`.
For more information about this error, try `rustc --explain E0015`.

View File

@ -4,11 +4,14 @@ error: const-stable function cannot use `#[feature(const_fn_fn_ptr_basics)]`
LL | const fn error(_: fn()) {}
| ^
|
= note: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
help: if it is not part of the public API, make this function unstably const
|
LL | #[rustc_const_unstable(feature = "...", issue = "...")]
|
help: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
|
LL | #[allow_internal_unstable(const_fn_fn_ptr_basics)]
|
error: aborting due to previous error

View File

@ -1,7 +1,6 @@
const fn foo(a: i32) -> Vec<i32> {
vec![1, 2, 3]
//~^ ERROR allocations are not allowed
//~| ERROR unimplemented expression type
//~| ERROR calls in constant functions
}

View File

@ -6,15 +6,6 @@ LL | vec![1, 2, 3]
|
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
error[E0019]: constant function contains unimplemented expression type
--> $DIR/bad_const_fn_body_ice.rs:2:5
|
LL | vec![1, 2, 3]
| ^^^^^^^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
error[E0015]: calls in constant functions are limited to constant functions, tuple structs and tuple variants
--> $DIR/bad_const_fn_body_ice.rs:2:5
|
@ -23,7 +14,7 @@ LL | vec![1, 2, 3]
|
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
error: aborting due to 3 previous errors
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0010, E0015, E0019.
Some errors have detailed explanations: E0010, E0015.
For more information about an error, try `rustc --explain E0010`.

View File

@ -3,11 +3,15 @@ fn main() {}
const fn unsize(x: &[u8; 3]) -> &[u8] { x }
const fn closure() -> fn() { || {} }
//~^ ERROR function pointer
//~| ERROR function pointer cast
const fn closure2() {
(|| {}) as fn();
//~^ ERROR function pointer
}
const fn reify(f: fn()) -> unsafe fn() { f }
//~^ ERROR function pointer
//~| ERROR function pointer
//~| ERROR function pointer cast
const fn reify2() { main as unsafe fn(); }
//~^ ERROR function pointer
//~| ERROR function pointer cast

View File

@ -7,17 +7,35 @@ LL | const fn closure() -> fn() { || {} }
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/cast_errors.rs:7:5
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/cast_errors.rs:4:30
|
LL | const fn closure() -> fn() { || {} }
| ^^^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/cast_errors.rs:8:5
|
LL | (|| {}) as fn();
| ^^^^^^^^^^^^^^^
| ^^^^^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/cast_errors.rs:10:28
--> $DIR/cast_errors.rs:11:16
|
LL | const fn reify(f: fn()) -> unsafe fn() { f }
| ^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/cast_errors.rs:11:28
|
LL | const fn reify(f: fn()) -> unsafe fn() { f }
| ^^^^^^^^^^^
@ -25,15 +43,33 @@ LL | const fn reify(f: fn()) -> unsafe fn() { f }
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/cast_errors.rs:12:21
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/cast_errors.rs:11:42
|
LL | const fn reify2() { main as unsafe fn(); }
| ^^^^^^^^^^^^^^^^^^^
LL | const fn reify(f: fn()) -> unsafe fn() { f }
| ^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: aborting due to 4 previous errors
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/cast_errors.rs:15:21
|
LL | const fn reify2() { main as unsafe fn(); }
| ^^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/cast_errors.rs:15:21
|
LL | const fn reify2() { main as unsafe fn(); }
| ^^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: aborting due to 8 previous errors
For more information about this error, try `rustc --explain E0658`.

View File

@ -1,5 +1,8 @@
const fn cmp(x: fn(), y: fn()) -> bool { //~ ERROR function pointer
const fn cmp(x: fn(), y: fn()) -> bool {
//~^ ERROR function pointer
//~| ERROR function pointer
unsafe { x == y }
//~^ ERROR pointers cannot be reliably compared
}
fn main() {}

View File

@ -7,6 +7,23 @@ LL | const fn cmp(x: fn(), y: fn()) -> bool {
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: aborting due to previous error
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/cmp_fn_pointers.rs:1:23
|
LL | const fn cmp(x: fn(), y: fn()) -> bool {
| ^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: pointers cannot be reliably compared during const eval.
--> $DIR/cmp_fn_pointers.rs:4:14
|
LL | unsafe { x == y }
| ^^^^^^
|
= note: see issue #53020 <https://github.com/rust-lang/rust/issues/53020> for more information
error: aborting due to 3 previous errors
For more information about this error, try `rustc --explain E0658`.

View File

@ -38,6 +38,8 @@ impl<T> Foo<T> {
const fn get(&self) -> &T { &self.0 }
const fn get_mut(&mut self) -> &mut T { &mut self.0 }
//~^ mutable references
//~| mutable references
//~| mutable references
}
impl<'a, T> Foo<T> {
const fn new_lt(t: T) -> Self { Foo(t) }
@ -45,6 +47,8 @@ impl<'a, T> Foo<T> {
const fn get_lt(&'a self) -> &T { &self.0 }
const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
//~^ mutable references
//~| mutable references
//~| mutable references
}
impl<T: Sized> Foo<T> {
const fn new_s(t: T) -> Self { Foo(t) }
@ -52,11 +56,15 @@ impl<T: Sized> Foo<T> {
const fn get_s(&self) -> &T { &self.0 }
const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
//~^ mutable references
//~| mutable references
//~| mutable references
}
impl<T: ?Sized> Foo<T> {
const fn get_sq(&self) -> &T { &self.0 }
const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
//~^ mutable references
//~| mutable references
//~| mutable references
}
@ -117,17 +125,24 @@ impl<T: Sync + Sized> Foo<T> {
struct AlanTuring<T>(T);
const fn no_apit2(_x: AlanTuring<impl std::fmt::Debug>) {}
//~^ ERROR trait bounds other than `Sized`
const fn no_apit(_x: impl std::fmt::Debug) {} //~ ERROR trait bounds other than `Sized`
const fn no_dyn_trait(_x: &dyn std::fmt::Debug) {} //~ ERROR trait bounds other than `Sized`
//~| ERROR destructor
const fn no_apit(_x: impl std::fmt::Debug) {}
//~^ ERROR trait bounds other than `Sized`
//~| ERROR destructor
const fn no_dyn_trait(_x: &dyn std::fmt::Debug) {}
//~^ ERROR trait bounds other than `Sized`
const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
//~^ ERROR trait bounds other than `Sized`
//~| ERROR unsizing cast
//~| ERROR unsizing cast
const fn no_unsafe() { unsafe {} }
const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
//~^ ERROR trait bounds other than `Sized`
//~^ ERROR unsizing cast
const fn no_fn_ptrs(_x: fn()) {}
//~^ ERROR function pointer
const fn no_fn_ptrs2() -> fn() { fn foo() {} foo }
//~^ ERROR function pointer
//~| ERROR function pointer cast

View File

@ -6,6 +6,15 @@ LL | const fn into_inner(self) -> T { self.0 }
| |
| constant functions cannot evaluate destructors
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:39:22
|
LL | const fn get_mut(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:39:36
|
@ -15,8 +24,17 @@ LL | const fn get_mut(&mut self) -> &mut T { &mut self.0 }
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:39:45
|
LL | const fn get_mut(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0493]: destructors cannot be evaluated at compile-time
--> $DIR/min_const_fn.rs:44:28
--> $DIR/min_const_fn.rs:46:28
|
LL | const fn into_inner_lt(self) -> T { self.0 }
| ^^^^ - value is dropped here
@ -24,7 +42,16 @@ LL | const fn into_inner_lt(self) -> T { self.0 }
| constant functions cannot evaluate destructors
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:46:42
--> $DIR/min_const_fn.rs:48:25
|
LL | const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:48:42
|
LL | const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
| ^^^^^^
@ -32,8 +59,17 @@ LL | const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:48:51
|
LL | const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0493]: destructors cannot be evaluated at compile-time
--> $DIR/min_const_fn.rs:51:27
--> $DIR/min_const_fn.rs:55:27
|
LL | const fn into_inner_s(self) -> T { self.0 }
| ^^^^ - value is dropped here
@ -41,7 +77,16 @@ LL | const fn into_inner_s(self) -> T { self.0 }
| constant functions cannot evaluate destructors
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:53:38
--> $DIR/min_const_fn.rs:57:24
|
LL | const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:57:38
|
LL | const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^
@ -50,7 +95,25 @@ LL | const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:58:39
--> $DIR/min_const_fn.rs:57:47
|
LL | const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:64:25
|
LL | const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:64:39
|
LL | const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^
@ -58,8 +121,17 @@ LL | const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:64:48
|
LL | const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
| ^^^^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:76:16
--> $DIR/min_const_fn.rs:84:16
|
LL | const fn foo11<T: std::fmt::Display>(t: T) -> T { t }
| ^
@ -68,7 +140,7 @@ LL | const fn foo11<T: std::fmt::Display>(t: T) -> T { t }
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:78:18
--> $DIR/min_const_fn.rs:86:18
|
LL | const fn foo11_2<T: Send>(t: T) -> T { t }
| ^
@ -77,7 +149,7 @@ LL | const fn foo11_2<T: Send>(t: T) -> T { t }
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0013]: constant functions cannot refer to statics
--> $DIR/min_const_fn.rs:82:27
--> $DIR/min_const_fn.rs:90:27
|
LL | const fn foo25() -> u32 { BAR }
| ^^^
@ -85,7 +157,7 @@ LL | const fn foo25() -> u32 { BAR }
= help: consider extracting the value of the `static` to a `const`, and referring to that
error[E0013]: constant functions cannot refer to statics
--> $DIR/min_const_fn.rs:83:37
--> $DIR/min_const_fn.rs:91:37
|
LL | const fn foo26() -> &'static u32 { &BAR }
| ^^^
@ -93,7 +165,7 @@ LL | const fn foo26() -> &'static u32 { &BAR }
= help: consider extracting the value of the `static` to a `const`, and referring to that
error[E0658]: casting pointers to integers in constant functions is unstable
--> $DIR/min_const_fn.rs:84:42
--> $DIR/min_const_fn.rs:92:42
|
LL | const fn foo30(x: *const u32) -> usize { x as usize }
| ^^^^^^^^^^
@ -102,7 +174,7 @@ LL | const fn foo30(x: *const u32) -> usize { x as usize }
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
error[E0658]: casting pointers to integers in constant functions is unstable
--> $DIR/min_const_fn.rs:86:63
--> $DIR/min_const_fn.rs:94:63
|
LL | const fn foo30_with_unsafe(x: *const u32) -> usize { unsafe { x as usize } }
| ^^^^^^^^^^
@ -111,7 +183,7 @@ LL | const fn foo30_with_unsafe(x: *const u32) -> usize { unsafe { x as usize }
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
error[E0658]: casting pointers to integers in constant functions is unstable
--> $DIR/min_const_fn.rs:88:42
--> $DIR/min_const_fn.rs:96:42
|
LL | const fn foo30_2(x: *mut u32) -> usize { x as usize }
| ^^^^^^^^^^
@ -120,7 +192,7 @@ LL | const fn foo30_2(x: *mut u32) -> usize { x as usize }
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
error[E0658]: casting pointers to integers in constant functions is unstable
--> $DIR/min_const_fn.rs:90:63
--> $DIR/min_const_fn.rs:98:63
|
LL | const fn foo30_2_with_unsafe(x: *mut u32) -> usize { unsafe { x as usize } }
| ^^^^^^^^^^
@ -129,7 +201,7 @@ LL | const fn foo30_2_with_unsafe(x: *mut u32) -> usize { unsafe { x as usize }
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/min_const_fn.rs:93:14
--> $DIR/min_const_fn.rs:101:14
|
LL | const fn inc(x: &mut i32) { *x += 1 }
| ^
@ -138,7 +210,7 @@ LL | const fn inc(x: &mut i32) { *x += 1 }
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:102:6
--> $DIR/min_const_fn.rs:110:6
|
LL | impl<T: std::fmt::Debug> Foo<T> {
| ^
@ -147,7 +219,7 @@ LL | impl<T: std::fmt::Debug> Foo<T> {
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:107:6
--> $DIR/min_const_fn.rs:115:6
|
LL | impl<T: std::fmt::Debug + Sized> Foo<T> {
| ^
@ -156,7 +228,7 @@ LL | impl<T: std::fmt::Debug + Sized> Foo<T> {
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:112:6
--> $DIR/min_const_fn.rs:120:6
|
LL | impl<T: Sync + Sized> Foo<T> {
| ^
@ -165,7 +237,7 @@ LL | impl<T: Sync + Sized> Foo<T> {
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:118:34
--> $DIR/min_const_fn.rs:126:34
|
LL | const fn no_apit2(_x: AlanTuring<impl std::fmt::Debug>) {}
| ^^^^^^^^^^^^^^^^^^^^
@ -173,8 +245,16 @@ LL | const fn no_apit2(_x: AlanTuring<impl std::fmt::Debug>) {}
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0493]: destructors cannot be evaluated at compile-time
--> $DIR/min_const_fn.rs:126:19
|
LL | const fn no_apit2(_x: AlanTuring<impl std::fmt::Debug>) {}
| ^^ - value is dropped here
| |
| constant functions cannot evaluate destructors
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:120:22
--> $DIR/min_const_fn.rs:129:22
|
LL | const fn no_apit(_x: impl std::fmt::Debug) {}
| ^^^^^^^^^^^^^^^^^^^^
@ -182,8 +262,16 @@ LL | const fn no_apit(_x: impl std::fmt::Debug) {}
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0493]: destructors cannot be evaluated at compile-time
--> $DIR/min_const_fn.rs:129:18
|
LL | const fn no_apit(_x: impl std::fmt::Debug) {}
| ^^ - value is dropped here
| |
| constant functions cannot evaluate destructors
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:121:23
--> $DIR/min_const_fn.rs:132:23
|
LL | const fn no_dyn_trait(_x: &dyn std::fmt::Debug) {}
| ^^
@ -192,7 +280,7 @@ LL | const fn no_dyn_trait(_x: &dyn std::fmt::Debug) {}
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:122:32
--> $DIR/min_const_fn.rs:134:32
|
LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -200,17 +288,35 @@ LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
--> $DIR/min_const_fn.rs:127:41
error[E0723]: unsizing casts to types besides slices are not allowed in const fn
--> $DIR/min_const_fn.rs:134:63
|
LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
| ^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: unsizing casts to types besides slices are not allowed in const fn
--> $DIR/min_const_fn.rs:134:63
|
LL | const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
| ^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: unsizing casts to types besides slices are not allowed in const fn
--> $DIR/min_const_fn.rs:141:42
|
LL | const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| ^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/min_const_fn.rs:130:21
--> $DIR/min_const_fn.rs:144:21
|
LL | const fn no_fn_ptrs(_x: fn()) {}
| ^^
@ -219,7 +325,7 @@ LL | const fn no_fn_ptrs(_x: fn()) {}
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
--> $DIR/min_const_fn.rs:132:27
--> $DIR/min_const_fn.rs:146:27
|
LL | const fn no_fn_ptrs2() -> fn() { fn foo() {} foo }
| ^^^^
@ -227,7 +333,16 @@ LL | const fn no_fn_ptrs2() -> fn() { fn foo() {} foo }
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: aborting due to 26 previous errors
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/min_const_fn.rs:146:46
|
LL | const fn no_fn_ptrs2() -> fn() { fn foo() {} foo }
| ^^^
|
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error: aborting due to 39 previous errors
Some errors have detailed explanations: E0013, E0493, E0658, E0723.
For more information about an error, try `rustc --explain E0013`.

View File

@ -10,6 +10,6 @@ const fn no_inner_dyn_trait2(x: Hide) {
//~^ ERROR trait bounds other than `Sized`
}
const fn no_inner_dyn_trait_ret() -> Hide { Hide(HasDyn { field: &0 }) }
//~^ ERROR trait bounds other than `Sized`
//~^ ERROR unsizing cast
fn main() {}

View File

@ -7,7 +7,7 @@ LL | x.0.field;
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn)]` to the crate attributes to enable
error[E0723]: trait bounds other than `Sized` on const fn parameters are unstable
error[E0723]: unsizing casts to types besides slices are not allowed in const fn
--> $DIR/min_const_fn_dyn.rs:12:66
|
LL | const fn no_inner_dyn_trait_ret() -> Hide { Hide(HasDyn { field: &0 }) }

View File

@ -7,7 +7,7 @@ LL | x.0.field;
= note: see issue #57563 <https://github.com/rust-lang/rust/issues/57563> for more information
= help: add `#![feature(const_fn_fn_ptr_basics)]` to the crate attributes to enable
error[E0658]: function pointers cannot appear in constant functions
error[E0658]: function pointer casts are not allowed in constant functions
--> $DIR/min_const_fn_fn_ptr.rs:16:59
|
LL | const fn no_inner_dyn_trait_ret() -> Hide { Hide(HasPtr { field }) }

View File

@ -20,11 +20,14 @@ error: const-stable function cannot use `#[feature(const_fn_floating_point_arith
LL | const fn bar3() -> u32 { (5f32 + 6f32) as u32 }
| ^^^^^^^^^^^^^
|
= note: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
help: if it is not part of the public API, make this function unstably const
|
LL | #[rustc_const_unstable(feature = "...", issue = "...")]
|
help: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
|
LL | #[allow_internal_unstable(const_fn_floating_point_arithmetic)]
|
error: `foo2_gated` is not yet stable as a const fn
--> $DIR/min_const_fn_libstd_stability.rs:39:32

View File

@ -20,11 +20,14 @@ error: const-stable function cannot use `#[feature(const_fn_floating_point_arith
LL | const unsafe fn bar3() -> u32 { (5f32 + 6f32) as u32 }
| ^^^^^^^^^^^^^
|
= note: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
help: if it is not part of the public API, make this function unstably const
|
LL | #[rustc_const_unstable(feature = "...", issue = "...")]
|
help: otherwise `#[allow_internal_unstable]` can be used to bypass stability checks
|
LL | #[allow_internal_unstable(const_fn_floating_point_arithmetic)]
|
error: `foo2_gated` is not yet stable as a const fn
--> $DIR/min_const_unsafe_fn_libstd_stability.rs:39:48

View File

@ -1,17 +1,17 @@
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/mutable_borrow.rs:3:9
--> $DIR/mutable_borrow.rs:3:13
|
LL | let b = &mut a;
| ^
| ^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/mutable_borrow.rs:12:13
--> $DIR/mutable_borrow.rs:12:17
|
LL | let b = &mut a;
| ^
| ^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable

View File

@ -9,7 +9,6 @@ const FOO: &u32 = {
{
let b: *mut u32 = &mut a; //~ ERROR mutable references are not allowed in constants
unsafe { *b = 5; } //~ ERROR dereferencing raw pointers in constants
//[stock]~^ contains unimplemented expression
}
&{a}
};

View File

@ -13,15 +13,7 @@ LL | unsafe { *b = 5; }
= note: see issue #51911 <https://github.com/rust-lang/rust/issues/51911> for more information
= help: add `#![feature(const_raw_ptr_deref)]` to the crate attributes to enable
error[E0019]: constant contains unimplemented expression type
--> $DIR/projection_qualif.rs:11:18
|
LL | unsafe { *b = 5; }
| ^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to 2 previous errors
error: aborting due to 3 previous errors
Some errors have detailed explanations: E0019, E0658, E0764.
For more information about an error, try `rustc --explain E0019`.
Some errors have detailed explanations: E0658, E0764.
For more information about an error, try `rustc --explain E0658`.

View File

@ -6,6 +6,5 @@ static mut STDERR_BUFFER_SPACE: u8 = 0;
pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
//~^ ERROR mutable references are not allowed in statics
//[stock]~| ERROR static contains unimplemented expression type
fn main() {}

View File

@ -4,15 +4,6 @@ error[E0764]: mutable references are not allowed in statics
LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ `&mut` is only allowed in `const fn`
error[E0019]: static contains unimplemented expression type
--> $DIR/static_mut_containing_mut_ref2.rs:7:45
|
LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0019, E0764.
For more information about an error, try `rustc --explain E0019`.
For more information about this error, try `rustc --explain E0764`.

View File

@ -4,6 +4,5 @@
#![allow(warnings)]
const CON : Box<i32> = box 0; //~ ERROR E0010
//~^ ERROR constant contains unimplemented expression type
fn main() {}

View File

@ -6,17 +6,6 @@ LL | const CON : Box<i32> = box 0;
|
= note: The value of statics and constants must be known at compile time, and they live for the entire lifetime of a program. Creating a boxed value allocates memory on the heap at runtime, and therefore cannot be done at compile time.
error[E0019]: constant contains unimplemented expression type
--> $DIR/E0010-teach.rs:6:28
|
LL | const CON : Box<i32> = box 0;
| ^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
= note: A function call isn't allowed in the const's initialization expression because the expression's value must be known at compile-time.
= note: Remember: you can't use a function call inside a const's initialization expression! However, you can use it anywhere else.
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0010, E0019.
For more information about an error, try `rustc --explain E0010`.
For more information about this error, try `rustc --explain E0010`.

View File

@ -2,6 +2,5 @@
#![allow(warnings)]
const CON : Box<i32> = box 0; //~ ERROR E0010
//~^ ERROR constant contains unimplemented expression type
fn main() {}

View File

@ -4,15 +4,6 @@ error[E0010]: allocations are not allowed in constants
LL | const CON : Box<i32> = box 0;
| ^^^^^ allocation not allowed in constants
error[E0019]: constant contains unimplemented expression type
--> $DIR/E0010.rs:4:28
|
LL | const CON : Box<i32> = box 0;
| ^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0010, E0019.
For more information about an error, try `rustc --explain E0010`.
For more information about this error, try `rustc --explain E0010`.

View File

@ -5,8 +5,8 @@ static mut M: i32 = 3;
const CR: &'static mut i32 = &mut C; //~ ERROR E0764
//~| WARN taking a mutable
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0764
//~| ERROR E0019
//~| ERROR cannot borrow
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0764
//~| WARN taking a mutable
static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M }; //~ ERROR E0764

View File

@ -19,14 +19,6 @@ error[E0764]: mutable references are not allowed in constants
LL | const CR: &'static mut i32 = &mut C;
| ^^^^^^ `&mut` is only allowed in `const fn`
error[E0019]: static contains unimplemented expression type
--> $DIR/E0017.rs:7:39
|
LL | static STATIC_REF: &'static mut i32 = &mut X;
| ^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0764]: mutable references are not allowed in statics
--> $DIR/E0017.rs:7:39
|
@ -65,7 +57,7 @@ error[E0764]: mutable references are not allowed in statics
LL | static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M };
| ^^^^^^ `&mut` is only allowed in `const fn`
error: aborting due to 6 previous errors; 2 warnings emitted
error: aborting due to 5 previous errors; 2 warnings emitted
Some errors have detailed explanations: E0019, E0596, E0764.
For more information about an error, try `rustc --explain E0019`.
Some errors have detailed explanations: E0596, E0764.
For more information about an error, try `rustc --explain E0596`.

View File

@ -3,9 +3,9 @@ const C: i32 = 2;
const CR: &'static mut i32 = &mut C; //~ ERROR E0764
//~| WARN taking a mutable
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0019
//~| ERROR cannot borrow
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR cannot borrow
//~| ERROR E0764
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0764
//~| WARN taking a mutable

View File

@ -19,14 +19,6 @@ error[E0764]: mutable references are not allowed in constants
LL | const CR: &'static mut i32 = &mut C;
| ^^^^^^ `&mut` is only allowed in `const fn`
error[E0019]: static contains unimplemented expression type
--> $DIR/E0388.rs:6:39
|
LL | static STATIC_REF: &'static mut i32 = &mut X;
| ^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0764]: mutable references are not allowed in statics
--> $DIR/E0388.rs:6:39
|
@ -59,7 +51,7 @@ error[E0764]: mutable references are not allowed in statics
LL | static CONST_REF: &'static mut i32 = &mut C;
| ^^^^^^ `&mut` is only allowed in `const fn`
error: aborting due to 5 previous errors; 2 warnings emitted
error: aborting due to 4 previous errors; 2 warnings emitted
Some errors have detailed explanations: E0019, E0596, E0764.
For more information about an error, try `rustc --explain E0019`.
Some errors have detailed explanations: E0596, E0764.
For more information about an error, try `rustc --explain E0596`.

View File

@ -6,6 +6,5 @@ use std::cell::RefCell;
static boxed: Box<RefCell<isize>> = box RefCell::new(0);
//~^ ERROR allocations are not allowed in statics
//~| ERROR `RefCell<isize>` cannot be shared between threads safely [E0277]
//~| ERROR static contains unimplemented expression type
fn main() { }

View File

@ -4,14 +4,6 @@ error[E0010]: allocations are not allowed in statics
LL | static boxed: Box<RefCell<isize>> = box RefCell::new(0);
| ^^^^^^^^^^^^^^^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/issue-7364.rs:6:41
|
LL | static boxed: Box<RefCell<isize>> = box RefCell::new(0);
| ^^^^^^^^^^^^^^^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0277]: `RefCell<isize>` cannot be shared between threads safely
--> $DIR/issue-7364.rs:6:1
|
@ -23,7 +15,7 @@ LL | static boxed: Box<RefCell<isize>> = box RefCell::new(0);
= note: required because it appears within the type `Box<RefCell<isize>>`
= note: shared static variables must have a type that implements `Sync`
error: aborting due to 3 previous errors
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0010, E0019, E0277.
Some errors have detailed explanations: E0010, E0277.
For more information about an error, try `rustc --explain E0010`.

View File

@ -12,7 +12,6 @@ fn main() {
extern "C" fn ff4() {} // OK.
const async unsafe extern "C" fn ff5() {} // OK.
//~^ ERROR functions cannot be both `const` and `async`
//~| ERROR `from_generator` is not yet stable as a const fn
trait X {
async fn ft1(); //~ ERROR functions in traits cannot be declared `async`
@ -35,7 +34,6 @@ fn main() {
const async unsafe extern "C" fn ft5() {}
//~^ ERROR functions in traits cannot be declared `async`
//~| ERROR functions in traits cannot be declared const
//~| ERROR `from_generator` is not yet stable as a const fn
//~| ERROR method `ft5` has an incompatible type for trait
//~| ERROR functions cannot be both `const` and `async`
}
@ -47,7 +45,6 @@ fn main() {
extern "C" fn fi4() {} // OK.
const async unsafe extern "C" fn fi5() {}
//~^ ERROR functions cannot be both `const` and `async`
//~| ERROR `from_generator` is not yet stable as a const fn
}
extern {

View File

@ -8,7 +8,7 @@ LL | const async unsafe extern "C" fn ff5() {} // OK.
| `const` because of this
error[E0706]: functions in traits cannot be declared `async`
--> $DIR/fn-header-semantic-fail.rs:18:9
--> $DIR/fn-header-semantic-fail.rs:17:9
|
LL | async fn ft1();
| -----^^^^^^^^^^
@ -19,19 +19,19 @@ LL | async fn ft1();
= note: consider using the `async-trait` crate: https://crates.io/crates/async-trait
error[E0379]: functions in traits cannot be declared const
--> $DIR/fn-header-semantic-fail.rs:20:9
--> $DIR/fn-header-semantic-fail.rs:19:9
|
LL | const fn ft3();
| ^^^^^ functions in traits cannot be const
error[E0379]: functions in traits cannot be declared const
--> $DIR/fn-header-semantic-fail.rs:22:9
--> $DIR/fn-header-semantic-fail.rs:21:9
|
LL | const async unsafe extern "C" fn ft5();
| ^^^^^ functions in traits cannot be const
error[E0706]: functions in traits cannot be declared `async`
--> $DIR/fn-header-semantic-fail.rs:22:9
--> $DIR/fn-header-semantic-fail.rs:21:9
|
LL | const async unsafe extern "C" fn ft5();
| ^^^^^^-----^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -42,7 +42,7 @@ LL | const async unsafe extern "C" fn ft5();
= note: consider using the `async-trait` crate: https://crates.io/crates/async-trait
error: functions cannot be both `const` and `async`
--> $DIR/fn-header-semantic-fail.rs:22:9
--> $DIR/fn-header-semantic-fail.rs:21:9
|
LL | const async unsafe extern "C" fn ft5();
| ^^^^^-^^^^^----------------------------
@ -51,7 +51,7 @@ LL | const async unsafe extern "C" fn ft5();
| `const` because of this
error[E0706]: functions in traits cannot be declared `async`
--> $DIR/fn-header-semantic-fail.rs:30:9
--> $DIR/fn-header-semantic-fail.rs:29:9
|
LL | async fn ft1() {}
| -----^^^^^^^^^^^^
@ -62,19 +62,19 @@ LL | async fn ft1() {}
= note: consider using the `async-trait` crate: https://crates.io/crates/async-trait
error[E0379]: functions in traits cannot be declared const
--> $DIR/fn-header-semantic-fail.rs:33:9
--> $DIR/fn-header-semantic-fail.rs:32:9
|
LL | const fn ft3() {}
| ^^^^^ functions in traits cannot be const
error[E0379]: functions in traits cannot be declared const
--> $DIR/fn-header-semantic-fail.rs:35:9
--> $DIR/fn-header-semantic-fail.rs:34:9
|
LL | const async unsafe extern "C" fn ft5() {}
| ^^^^^ functions in traits cannot be const
error[E0706]: functions in traits cannot be declared `async`
--> $DIR/fn-header-semantic-fail.rs:35:9
--> $DIR/fn-header-semantic-fail.rs:34:9
|
LL | const async unsafe extern "C" fn ft5() {}
| ^^^^^^-----^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -85,7 +85,7 @@ LL | const async unsafe extern "C" fn ft5() {}
= note: consider using the `async-trait` crate: https://crates.io/crates/async-trait
error: functions cannot be both `const` and `async`
--> $DIR/fn-header-semantic-fail.rs:35:9
--> $DIR/fn-header-semantic-fail.rs:34:9
|
LL | const async unsafe extern "C" fn ft5() {}
| ^^^^^-^^^^^------------------------------
@ -94,7 +94,7 @@ LL | const async unsafe extern "C" fn ft5() {}
| `const` because of this
error: functions cannot be both `const` and `async`
--> $DIR/fn-header-semantic-fail.rs:48:9
--> $DIR/fn-header-semantic-fail.rs:46:9
|
LL | const async unsafe extern "C" fn fi5() {}
| ^^^^^-^^^^^------------------------------
@ -103,7 +103,7 @@ LL | const async unsafe extern "C" fn fi5() {}
| `const` because of this
error: functions in `extern` blocks cannot have qualifiers
--> $DIR/fn-header-semantic-fail.rs:54:18
--> $DIR/fn-header-semantic-fail.rs:51:18
|
LL | extern {
| ------ in this `extern` block
@ -113,7 +113,7 @@ LL | async fn fe1();
| help: remove the qualifiers: `fn`
error: functions in `extern` blocks cannot have qualifiers
--> $DIR/fn-header-semantic-fail.rs:55:19
--> $DIR/fn-header-semantic-fail.rs:52:19
|
LL | extern {
| ------ in this `extern` block
@ -124,7 +124,7 @@ LL | unsafe fn fe2();
| help: remove the qualifiers: `fn`
error: functions in `extern` blocks cannot have qualifiers
--> $DIR/fn-header-semantic-fail.rs:56:18
--> $DIR/fn-header-semantic-fail.rs:53:18
|
LL | extern {
| ------ in this `extern` block
@ -135,7 +135,7 @@ LL | const fn fe3();
| help: remove the qualifiers: `fn`
error: functions in `extern` blocks cannot have qualifiers
--> $DIR/fn-header-semantic-fail.rs:57:23
--> $DIR/fn-header-semantic-fail.rs:54:23
|
LL | extern {
| ------ in this `extern` block
@ -146,7 +146,7 @@ LL | extern "C" fn fe4();
| help: remove the qualifiers: `fn`
error: functions in `extern` blocks cannot have qualifiers
--> $DIR/fn-header-semantic-fail.rs:58:42
--> $DIR/fn-header-semantic-fail.rs:55:42
|
LL | extern {
| ------ in this `extern` block
@ -157,7 +157,7 @@ LL | const async unsafe extern "C" fn fe5();
| help: remove the qualifiers: `fn`
error: functions cannot be both `const` and `async`
--> $DIR/fn-header-semantic-fail.rs:58:9
--> $DIR/fn-header-semantic-fail.rs:55:9
|
LL | const async unsafe extern "C" fn fe5();
| ^^^^^-^^^^^----------------------------
@ -165,16 +165,8 @@ LL | const async unsafe extern "C" fn fe5();
| | `async` because of this
| `const` because of this
error: `from_generator` is not yet stable as a const fn
--> $DIR/fn-header-semantic-fail.rs:13:44
|
LL | const async unsafe extern "C" fn ff5() {} // OK.
| ^^
|
= help: add `#![feature(gen_future)]` to the crate attributes to enable
error[E0053]: method `ft1` has an incompatible type for trait
--> $DIR/fn-header-semantic-fail.rs:30:24
--> $DIR/fn-header-semantic-fail.rs:29:24
|
LL | async fn ft1();
| - type in trait
@ -189,7 +181,7 @@ LL | async fn ft1() {}
found fn pointer `fn() -> impl Future`
error[E0053]: method `ft5` has an incompatible type for trait
--> $DIR/fn-header-semantic-fail.rs:35:48
--> $DIR/fn-header-semantic-fail.rs:34:48
|
LL | const async unsafe extern "C" fn ft5();
| - type in trait
@ -203,23 +195,7 @@ LL | const async unsafe extern "C" fn ft5() {}
= note: expected fn pointer `unsafe extern "C" fn()`
found fn pointer `unsafe extern "C" fn() -> impl Future`
error: `from_generator` is not yet stable as a const fn
--> $DIR/fn-header-semantic-fail.rs:35:48
|
LL | const async unsafe extern "C" fn ft5() {}
| ^^
|
= help: add `#![feature(gen_future)]` to the crate attributes to enable
error: `from_generator` is not yet stable as a const fn
--> $DIR/fn-header-semantic-fail.rs:48:48
|
LL | const async unsafe extern "C" fn fi5() {}
| ^^
|
= help: add `#![feature(gen_future)]` to the crate attributes to enable
error: aborting due to 23 previous errors
error: aborting due to 20 previous errors
Some errors have detailed explanations: E0053, E0379, E0706.
For more information about an error, try `rustc --explain E0053`.

View File

@ -2,6 +2,5 @@
static mut a: Box<isize> = box 3;
//~^ ERROR allocations are not allowed in statics
//~| ERROR static contains unimplemented expression type
fn main() {}

View File

@ -4,15 +4,6 @@ error[E0010]: allocations are not allowed in statics
LL | static mut a: Box<isize> = box 3;
| ^^^^^ allocation not allowed in statics
error[E0019]: static contains unimplemented expression type
--> $DIR/static-mut-not-constant.rs:3:32
|
LL | static mut a: Box<isize> = box 3;
| ^
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error: aborting due to previous error
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0010, E0019.
For more information about an error, try `rustc --explain E0010`.
For more information about this error, try `rustc --explain E0010`.

View File

@ -1,17 +1,17 @@
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/ranged_ints2_const.rs:11:9
--> $DIR/ranged_ints2_const.rs:11:13
|
LL | let y = &mut x.0;
| ^
| ^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
error[E0658]: mutable references are not allowed in constant functions
--> $DIR/ranged_ints2_const.rs:18:9
--> $DIR/ranged_ints2_const.rs:18:22
|
LL | let y = unsafe { &mut x.0 };
| ^
| ^^^^^^^^
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable