Skip to content

Commit

Permalink
Fix ICE for lib features
Browse files Browse the repository at this point in the history
  • Loading branch information
nbdd0121 committed Jun 26, 2020
1 parent fc239e8 commit 779b05d
Show file tree
Hide file tree
Showing 2 changed files with 25 additions and 4 deletions.
4 changes: 2 additions & 2 deletions src/librustc_mir/transform/check_consts/validation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -550,9 +550,9 @@ impl Visitor<'tcx> for Validator<'mir, 'tcx> {
} else if let Some(feature) = is_unstable_const_fn(self.tcx, def_id) {
// Exempt unstable const fns inside of macros or functions with
// `#[allow_internal_unstable]`.
use crate::transform::qualify_min_const_fn::feature_allowed;
use crate::transform::qualify_min_const_fn::lib_feature_allowed;
if !self.span.allows_unstable(feature)
&& !feature_allowed(self.tcx, self.def_id, feature)
&& !lib_feature_allowed(self.tcx, self.def_id, feature)
{
self.check_op(ops::FnCallUnstable(def_id, feature));
}
Expand Down
25 changes: 23 additions & 2 deletions src/librustc_mir/transform/qualify_min_const_fn.rs
Original file line number Diff line number Diff line change
Expand Up @@ -315,7 +315,7 @@ fn check_place(
}

/// Returns `true` if the given feature gate is allowed within the function with the given `DefId`.
pub fn feature_allowed(tcx: TyCtxt<'tcx>, def_id: DefId, feature_gate: Symbol) -> bool {
fn feature_allowed(tcx: TyCtxt<'tcx>, def_id: DefId, feature_gate: Symbol) -> bool {
// All features require that the corresponding gate be enabled,
// even if the function has `#[allow_internal_unstable(the_gate)]`.
if !tcx.features().enabled(feature_gate) {
Expand All @@ -334,6 +334,26 @@ pub fn feature_allowed(tcx: TyCtxt<'tcx>, def_id: DefId, feature_gate: Symbol) -
.map_or(false, |mut features| features.any(|name| name == feature_gate))
}

/// Returns `true` if the given library feature gate is allowed within the function with the given `DefId`.
pub fn lib_feature_allowed(tcx: TyCtxt<'tcx>, def_id: DefId, feature_gate: Symbol) -> bool {
// All features require that the corresponding gate be enabled,
// even if the function has `#[allow_internal_unstable(the_gate)]`.
if !tcx.features().declared_lib_features.iter().any(|&(sym, _)| sym == feature_gate) {
return false;
}

// If this crate is not using stability attributes, or this function is not claiming to be a
// stable `const fn`, that is all that is required.
if !tcx.features().staged_api || tcx.has_attr(def_id, sym::rustc_const_unstable) {
return true;
}

// However, we cannot allow stable `const fn`s to use unstable features without an explicit
// opt-in via `allow_internal_unstable`.
attr::allow_internal_unstable(&tcx.get_attrs(def_id), &tcx.sess.diagnostic())
.map_or(false, |mut features| features.any(|name| name == feature_gate))
}

fn check_terminator(
tcx: TyCtxt<'tcx>,
body: &'a Body<'tcx>,
Expand Down Expand Up @@ -383,7 +403,8 @@ fn check_terminator(
if !crate::const_eval::is_min_const_fn(tcx, fn_def_id)
&& !crate::const_eval::is_unstable_const_fn(tcx, fn_def_id)
.map(|feature| {
span.allows_unstable(feature) || feature_allowed(tcx, def_id, feature)
span.allows_unstable(feature)
|| lib_feature_allowed(tcx, def_id, feature)
})
.unwrap_or(false)
{
Expand Down

0 comments on commit 779b05d

Please sign in to comment.