Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 13 additions & 13 deletions compiler/rustc_ast_lowering/src/expr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ use super::{
use crate::errors::{InvalidLegacyConstGenericArg, UseConstGenericArg, YieldInClosure};
use crate::{AllowReturnTypeNotation, FnDeclKind, ImplTraitPosition, TryBlockScope};

struct WillCreateDefIdsVisitor {}
pub(super) struct WillCreateDefIdsVisitor;

impl<'v> rustc_ast::visit::Visitor<'v> for WillCreateDefIdsVisitor {
type Result = ControlFlow<Span>;
Expand Down Expand Up @@ -479,18 +479,18 @@ impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> {
DefPathData::LateAnonConst,
f.span,
);
let mut visitor = WillCreateDefIdsVisitor {};
let const_value = if let ControlFlow::Break(span) = visitor.visit_expr(&arg) {
Box::new(Expr {
id: self.next_node_id(),
kind: ExprKind::Err(invalid_expr_error(self.tcx, span)),
span: f.span,
attrs: [].into(),
tokens: None,
})
} else {
arg
};
let const_value =
if let ControlFlow::Break(span) = WillCreateDefIdsVisitor.visit_expr(&arg) {
Box::new(Expr {
id: self.next_node_id(),
kind: ExprKind::Err(invalid_expr_error(self.tcx, span)),
span: f.span,
attrs: [].into(),
tokens: None,
})
} else {
arg
};

let anon_const = AnonConst {
id: node_id,
Expand Down
36 changes: 25 additions & 11 deletions compiler/rustc_ast_lowering/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ use std::mem;
use std::sync::Arc;

use rustc_ast::node_id::NodeMap;
use rustc_ast::visit::Visitor;
use rustc_ast::{self as ast, *};
use rustc_attr_parsing::{AttributeParser, Late, OmitDoc};
use rustc_data_structures::fingerprint::Fingerprint;
Expand Down Expand Up @@ -2219,14 +2220,22 @@ impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> {
// since later compiler stages cannot handle them (and shouldn't need to be able to).
let default = default
.as_ref()
.filter(|_| match source {
.filter(|anon_const| match source {
hir::GenericParamSource::Generics => true,
hir::GenericParamSource::Binder => {
self.dcx().emit_err(errors::GenericParamDefaultInBinder {
span: param.span(),
});

false
let err = errors::GenericParamDefaultInBinder { span: param.span() };
if expr::WillCreateDefIdsVisitor
.visit_expr(&anon_const.value)
.is_break()
{
// FIXME(mgca): make this non-fatal once we have a better way
// to handle nested items in anno const from binder
// Issue: https://github.com/rust-lang/rust/issues/123629
self.dcx().emit_fatal(err)
} else {
self.dcx().emit_err(err);
false
}
}
})
.map(|def| self.lower_anon_const_to_const_arg_and_alloc(def));
Expand Down Expand Up @@ -2563,12 +2572,17 @@ impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> {
let span = self.lower_span(expr.span);

let overly_complex_const = |this: &mut Self| {
let e = this.dcx().struct_span_err(
expr.span,
"complex const arguments must be placed inside of a `const` block",
);
let msg = "complex const arguments must be placed inside of a `const` block";
let e = if expr::WillCreateDefIdsVisitor.visit_expr(expr).is_break() {
// FIXME(mgca): make this non-fatal once we have a better way to handle
// nested items in const args
// Issue: https://github.com/rust-lang/rust/issues/154539
this.dcx().struct_span_fatal(expr.span, msg).emit()
} else {
this.dcx().struct_span_err(expr.span, msg).emit()
};

ConstArg { hir_id: this.next_id(), kind: hir::ConstArgKind::Error(e.emit()), span }
ConstArg { hir_id: this.next_id(), kind: hir::ConstArgKind::Error(e), span }
};

match &expr.kind {
Expand Down
10 changes: 0 additions & 10 deletions tests/crashes/123629.rs

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#![feature(generic_assert)]

fn foo()
where
for<const N: usize = { assert!(u) }> ():,
//~^ ERROR cannot find value `u` in this scope
//~^^ ERROR only lifetime parameters can be used in this context
//~^^^ ERROR defaults for generic parameters are not allowed in `for<...>` binders
{
}

fn main() {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
error[E0425]: cannot find value `u` in this scope
--> $DIR/bad-defaults-for-generic-param-in-binder-123629.rs:5:36
|
LL | for<const N: usize = { assert!(u) }> ():,
| ^ not found in this scope

error[E0658]: only lifetime parameters can be used in this context
--> $DIR/bad-defaults-for-generic-param-in-binder-123629.rs:5:15
|
LL | for<const N: usize = { assert!(u) }> ():,
| ^
|
= note: see issue #108185 <https://github.com/rust-lang/rust/issues/108185> for more information
= help: add `#![feature(non_lifetime_binders)]` to the crate attributes to enable
= note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date

error: defaults for generic parameters are not allowed in `for<...>` binders
--> $DIR/bad-defaults-for-generic-param-in-binder-123629.rs:5:9
|
LL | for<const N: usize = { assert!(u) }> ():,
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error: aborting due to 3 previous errors

Some errors have detailed explanations: E0425, E0658.
For more information about an error, try `rustc --explain E0425`.
8 changes: 8 additions & 0 deletions tests/ui/const-generics/mgca/array-expr-complex.r1.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
error: complex const arguments must be placed inside of a `const` block
--> $DIR/array-expr-complex.rs:11:28
|
LL | takes_array::<{ [1, 2, 1 + 2] }>();
| ^^^^^

error: aborting due to 1 previous error

8 changes: 8 additions & 0 deletions tests/ui/const-generics/mgca/array-expr-complex.r2.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
error: complex const arguments must be placed inside of a `const` block
--> $DIR/array-expr-complex.rs:14:21
|
LL | takes_array::<{ [X; 3] }>();
| ^^^^^^

error: aborting due to 1 previous error

8 changes: 8 additions & 0 deletions tests/ui/const-generics/mgca/array-expr-complex.r3.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
error: complex const arguments must be placed inside of a `const` block
--> $DIR/array-expr-complex.rs:17:21
|
LL | takes_array::<{ [0; Y] }>();
| ^^^^^^

error: aborting due to 1 previous error

11 changes: 8 additions & 3 deletions tests/ui/const-generics/mgca/array-expr-complex.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,21 @@
//@ revisions: r1 r2 r3

#![expect(incomplete_features)]
#![feature(min_generic_const_args, adt_const_params)]

fn takes_array<const A: [u32; 3]>() {}

fn generic_caller<const X: u32, const Y: usize>() {
// not supported yet
#[cfg(r1)]
takes_array::<{ [1, 2, 1 + 2] }>();
//~^ ERROR: complex const arguments must be placed inside of a `const` block
//[r1]~^ ERROR: complex const arguments must be placed inside of a `const` block
#[cfg(r2)]
takes_array::<{ [X; 3] }>();
//~^ ERROR: complex const arguments must be placed inside of a `const` block
//[r2]~^ ERROR: complex const arguments must be placed inside of a `const` block
#[cfg(r3)]
takes_array::<{ [0; Y] }>();
//~^ ERROR: complex const arguments must be placed inside of a `const` block
//[r3]~^ ERROR: complex const arguments must be placed inside of a `const` block
}

fn main() {}
20 changes: 0 additions & 20 deletions tests/ui/const-generics/mgca/array-expr-complex.stderr

This file was deleted.

12 changes: 12 additions & 0 deletions tests/ui/const-generics/mgca/bad-const-arg-fn-154539.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#![feature(min_generic_const_args)]

trait Iter<
const FN: fn() = {
|| { //~ ERROR complex const arguments must be placed inside of a `const` block
use std::io::*;
write!(_, "")
}
},
>
{
}
11 changes: 11 additions & 0 deletions tests/ui/const-generics/mgca/bad-const-arg-fn-154539.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
error: complex const arguments must be placed inside of a `const` block
--> $DIR/bad-const-arg-fn-154539.rs:5:9
|
LL | / || {
LL | | use std::io::*;
LL | | write!(_, "")
LL | | }
| |_________^

error: aborting due to 1 previous error

Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
error[E0428]: the name `foo` is defined multiple times
--> $DIR/hir-crate-items-before-lowering-ices.rs:13:17
|
LL | fn foo() {}
| -------- previous definition of the value `foo` here
LL | reuse foo;
| ^^^^^^^^^^ `foo` redefined here
|
= note: `foo` must be defined only once in the value namespace of this block

error: complex const arguments must be placed inside of a `const` block
--> $DIR/hir-crate-items-before-lowering-ices.rs:11:13
|
LL | / {
LL | | fn foo() {}
LL | | reuse foo;
LL | | 2
LL | | },
| |_____________^

error: aborting due to 2 previous errors

For more information about this error, try `rustc --explain E0428`.
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
error: `#[deprecated]` attribute cannot be used on delegations
--> $DIR/hir-crate-items-before-lowering-ices.rs:27:9
|
LL | #[deprecated]
| ^^^^^^^^^^^^^
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
= help: `#[deprecated]` can be applied to associated consts, associated types, constants, crates, data types, enum variants, foreign statics, functions, inherent impl blocks, macro defs, modules, statics, struct fields, traits, type aliases, and use statements
= note: `#[deny(useless_deprecated)]` on by default

error: aborting due to 1 previous error

Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
error[E0061]: this function takes 0 arguments but 1 argument was supplied
--> $DIR/hir-crate-items-before-lowering-ices.rs:37:11
|
LL | reuse a as b {
| ___________^______-
LL | | fn foo<T>() {};
LL | | foo
LL | | }
| |_____- unexpected argument of type `fn() {foo::<_>}`
|
note: function defined here
--> $DIR/hir-crate-items-before-lowering-ices.rs:35:8
|
LL | fn a() {}
| ^
help: remove the extra argument
|
LL - reuse a as b {
LL + reuse {
|

error: aborting due to 1 previous error

For more information about this error, try `rustc --explain E0061`.
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
error: complex const arguments must be placed inside of a `const` block
--> $DIR/hir-crate-items-before-lowering-ices.rs:47:13
|
LL | / {
LL | |
LL | | struct W<I>;
LL | | impl<I> W<I> {
... |
LL | | },
| |_____________^

error: aborting due to 1 previous error

Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
error[E0425]: cannot find value `async` in this scope
--> $DIR/hir-crate-items-before-lowering-ices.rs:66:13
|
LL | async || {};
| ^^^^^ not found in this scope

error[E0308]: mismatched types
--> $DIR/hir-crate-items-before-lowering-ices.rs:66:22
|
LL | async || {};
| ^^ expected `bool`, found `()`

error: aborting due to 2 previous errors

Some errors have detailed explanations: E0308, E0425.
For more information about an error, try `rustc --explain E0308`.
Loading
Loading