Skip to content

Commit

Permalink
only check cg defaults wf once instantiated
Browse files Browse the repository at this point in the history
  • Loading branch information
lcnr committed Jul 8, 2021
1 parent d0485c7 commit 4a53b11
Show file tree
Hide file tree
Showing 6 changed files with 31 additions and 38 deletions.
26 changes: 11 additions & 15 deletions compiler/rustc_typeck/src/check/wfcheck.rs
Original file line number Diff line number Diff line change
Expand Up @@ -738,15 +738,19 @@ fn check_where_clauses<'tcx, 'fcx>(
}
}
GenericParamDefKind::Const { .. } => {
// FIXME(const_generics_defaults): Figure out if this
// is the behavior we want, see the comment further below.
if is_our_default(&param) {
// FIXME(const_generics_defaults): This
// is incorrect when dealing with unused substs, for example
// for `struct Foo<const N: usize, const M: usize = { 1 - 2 }>`
// we should eagerly error.
let default_ct = tcx.const_param_default(param.def_id);
fcx.register_wf_obligation(
default_ct.into(),
tcx.def_span(param.def_id),
ObligationCauseCode::MiscObligation,
);
if !default_ct.needs_subst() {
fcx.register_wf_obligation(
default_ct.into(),
tcx.def_span(param.def_id),
ObligationCauseCode::MiscObligation,
);
}
}
}
// Doesn't have defaults.
Expand Down Expand Up @@ -783,14 +787,6 @@ fn check_where_clauses<'tcx, 'fcx>(
tcx.mk_param_from_def(param)
}
GenericParamDefKind::Const { .. } => {
// FIXME(const_generics_defaults): I(@lcnr) feel like always
// using the const parameter is the right choice here, even
// if it needs substs.
//
// Before stabilizing this we probably want to get some tests
// where this makes a difference and figure out what's the exact
// behavior we want here.

// If the param has a default, ...
if is_our_default(param) {
let default_ct = tcx.const_param_default(param.def_id);
Expand Down
10 changes: 10 additions & 0 deletions compiler/rustc_typeck/src/collect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2308,6 +2308,16 @@ fn const_evaluatable_predicates_of<'tcx>(
));
}
}

fn visit_const_param_default(&mut self, _param: HirId, _ct: &'tcx hir::AnonConst) {
// Do not look into const param defaults,
// these get checked when they are actually instantiated.
//
// We do not want the following to error:
//
// struct Foo<const N: usize, const M: usize = { N + 1 }>;
// struct Bar<const N: usize>(Foo<N, 3>);
}
}

let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// check-pass
#![feature(const_generics, const_evaluatable_checked, const_generics_defaults)]
#![allow(incomplete_features)]
struct Foo<const N: usize, const M: usize = { N + 1 }>;
struct Bar<const N: usize>(Foo<N, 3>);
fn main() {}

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
error: generic parameters may not be used in const operations
--> $DIR/complex-generic-default-expr.rs:6:47
--> $DIR/complex-generic-default-expr.rs:7:47
|
LL | struct Foo<const N: usize, const M: usize = { N + 1 }>;
| ^ cannot perform const operation using `N`
Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,13 @@
// revisions: full min
//[full] check-pass
#![cfg_attr(full, feature(const_generics))]
#![feature(const_generics_defaults)]
#![allow(incomplete_features)]

struct Foo<const N: usize, const M: usize = { N + 1 }>;
//[full]~^ ERROR constant expression depends on a generic parameter
//[min]~^^ ERROR generic parameters may not be used in const operations
//[min]~^ ERROR generic parameters may not be used in const operations

struct Bar<T, const TYPE_SIZE: usize = { std::mem::size_of::<T>() }>(T);
//[full]~^ ERROR constant expression depends on a generic parameter
//[min]~^^ ERROR generic parameters may not be used in const operations
//[min]~^ ERROR generic parameters may not be used in const operations

fn main() {}

0 comments on commit 4a53b11

Please sign in to comment.