Skip to content

Commit 7770bce

Browse files
committed
Make rustc::traits::object_safety::{astconv_object_safety_violations,is_vtable_safe_method,object_safety_violations} free functions.
1 parent 0b1521e commit 7770bce

File tree

6 files changed

+54
-49
lines changed

6 files changed

+54
-49
lines changed

src/librustc/infer/error_reporting/mod.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ use crate::infer::opaque_types;
5454
use crate::infer::{self, SuppressRegionErrors};
5555
use crate::middle::region;
5656
use crate::traits::error_reporting::report_object_safety_error;
57+
use crate::traits::object_safety_violations;
5758
use crate::traits::{
5859
IfExpressionCause, MatchExpressionArmCause, ObligationCause, ObligationCauseCode,
5960
};
@@ -1487,7 +1488,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
14871488
let failure_code = trace.cause.as_failure_code(terr);
14881489
let mut diag = match failure_code {
14891490
FailureCode::Error0038(did) => {
1490-
let violations = self.tcx.object_safety_violations(did);
1491+
let violations = object_safety_violations(self.tcx, did);
14911492
report_object_safety_error(self.tcx, span, did, violations)
14921493
}
14931494
FailureCode::Error0317(failure_str) => {

src/librustc/traits/error_reporting.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ use crate::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
1111
use crate::infer::{self, InferCtxt};
1212
use crate::mir::interpret::ErrorHandled;
1313
use crate::session::DiagnosticMessageId;
14+
use crate::traits::object_safety_violations;
1415
use crate::ty::error::ExpectedFound;
1516
use crate::ty::fast_reject;
1617
use crate::ty::fold::TypeFolder;
@@ -915,7 +916,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
915916
}
916917

917918
ty::Predicate::ObjectSafe(trait_def_id) => {
918-
let violations = self.tcx.object_safety_violations(trait_def_id);
919+
let violations = object_safety_violations(self.tcx, trait_def_id);
919920
report_object_safety_error(self.tcx, span, trait_def_id, violations)
920921
}
921922

@@ -1079,7 +1080,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
10791080
}
10801081

10811082
TraitNotObjectSafe(did) => {
1082-
let violations = self.tcx.object_safety_violations(did);
1083+
let violations = object_safety_violations(self.tcx, did);
10831084
report_object_safety_error(self.tcx, span, did, violations)
10841085
}
10851086

src/librustc/traits/mod.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,9 @@ pub use self::coherence::{add_placeholder_note, orphan_check, overlapping_impls}
4747
pub use self::coherence::{OrphanCheckErr, OverlapResult};
4848
pub use self::engine::{TraitEngine, TraitEngineExt};
4949
pub use self::fulfill::{FulfillmentContext, PendingPredicateObligation};
50+
pub use self::object_safety::astconv_object_safety_violations;
51+
pub use self::object_safety::is_vtable_safe_method;
52+
pub use self::object_safety::object_safety_violations;
5053
pub use self::object_safety::MethodViolationCode;
5154
pub use self::object_safety::ObjectSafetyViolation;
5255
pub use self::on_unimplemented::{OnUnimplementedDirective, OnUnimplementedNote};
@@ -1062,7 +1065,7 @@ fn vtable_methods<'tcx>(
10621065
let def_id = trait_method.def_id;
10631066

10641067
// Some methods cannot be called on an object; skip those.
1065-
if !tcx.is_vtable_safe_method(trait_ref.def_id(), &trait_method) {
1068+
if !is_vtable_safe_method(tcx, trait_ref.def_id(), &trait_method) {
10661069
debug!("vtable_methods: not vtable safe");
10671070
return None;
10681071
}

src/librustc/traits/object_safety.rs

Lines changed: 41 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -108,54 +108,52 @@ pub enum MethodViolationCode {
108108
UndispatchableReceiver,
109109
}
110110

111-
impl<'tcx> TyCtxt<'tcx> {
112-
/// Returns the object safety violations that affect
113-
/// astconv -- currently, `Self` in supertraits. This is needed
114-
/// because `object_safety_violations` can't be used during
115-
/// type collection.
116-
pub fn astconv_object_safety_violations(
117-
self,
118-
trait_def_id: DefId,
119-
) -> Vec<ObjectSafetyViolation> {
120-
debug_assert!(self.generics_of(trait_def_id).has_self);
121-
let violations = traits::supertrait_def_ids(self, trait_def_id)
122-
.filter(|&def_id| predicates_reference_self(self, def_id, true))
123-
.map(|_| ObjectSafetyViolation::SupertraitSelf)
124-
.collect();
111+
/// Returns the object safety violations that affect
112+
/// astconv -- currently, `Self` in supertraits. This is needed
113+
/// because `object_safety_violations` can't be used during
114+
/// type collection.
115+
pub fn astconv_object_safety_violations(
116+
tcx: TyCtxt<'_>,
117+
trait_def_id: DefId,
118+
) -> Vec<ObjectSafetyViolation> {
119+
debug_assert!(tcx.generics_of(trait_def_id).has_self);
120+
let violations = traits::supertrait_def_ids(tcx, trait_def_id)
121+
.filter(|&def_id| predicates_reference_self(tcx, def_id, true))
122+
.map(|_| ObjectSafetyViolation::SupertraitSelf)
123+
.collect();
125124

126-
debug!(
127-
"astconv_object_safety_violations(trait_def_id={:?}) = {:?}",
128-
trait_def_id, violations
129-
);
125+
debug!("astconv_object_safety_violations(trait_def_id={:?}) = {:?}", trait_def_id, violations);
130126

131-
violations
132-
}
127+
violations
128+
}
129+
130+
pub fn object_safety_violations(
131+
tcx: TyCtxt<'_>,
132+
trait_def_id: DefId,
133+
) -> Vec<ObjectSafetyViolation> {
134+
debug_assert!(tcx.generics_of(trait_def_id).has_self);
135+
debug!("object_safety_violations: {:?}", trait_def_id);
133136

134-
pub fn object_safety_violations(self, trait_def_id: DefId) -> Vec<ObjectSafetyViolation> {
135-
debug_assert!(self.generics_of(trait_def_id).has_self);
136-
debug!("object_safety_violations: {:?}", trait_def_id);
137+
traits::supertrait_def_ids(tcx, trait_def_id)
138+
.flat_map(|def_id| object_safety_violations_for_trait(tcx, def_id))
139+
.collect()
140+
}
137141

138-
traits::supertrait_def_ids(self, trait_def_id)
139-
.flat_map(|def_id| object_safety_violations_for_trait(self, def_id))
140-
.collect()
142+
/// We say a method is *vtable safe* if it can be invoked on a trait
143+
/// object. Note that object-safe traits can have some
144+
/// non-vtable-safe methods, so long as they require `Self: Sized` or
145+
/// otherwise ensure that they cannot be used when `Self = Trait`.
146+
pub fn is_vtable_safe_method(tcx: TyCtxt<'_>, trait_def_id: DefId, method: &ty::AssocItem) -> bool {
147+
debug_assert!(tcx.generics_of(trait_def_id).has_self);
148+
debug!("is_vtable_safe_method({:?}, {:?})", trait_def_id, method);
149+
// Any method that has a `Self: Sized` bound cannot be called.
150+
if generics_require_sized_self(tcx, method.def_id) {
151+
return false;
141152
}
142153

143-
/// We say a method is *vtable safe* if it can be invoked on a trait
144-
/// object. Note that object-safe traits can have some
145-
/// non-vtable-safe methods, so long as they require `Self: Sized` or
146-
/// otherwise ensure that they cannot be used when `Self = Trait`.
147-
pub fn is_vtable_safe_method(self, trait_def_id: DefId, method: &ty::AssocItem) -> bool {
148-
debug_assert!(self.generics_of(trait_def_id).has_self);
149-
debug!("is_vtable_safe_method({:?}, {:?})", trait_def_id, method);
150-
// Any method that has a `Self: Sized` bound cannot be called.
151-
if generics_require_sized_self(self, method.def_id) {
152-
return false;
153-
}
154-
155-
match virtual_call_violation_for_method(self, trait_def_id, method) {
156-
None | Some(MethodViolationCode::WhereClauseReferencesSelf) => true,
157-
Some(_) => false,
158-
}
154+
match virtual_call_violation_for_method(tcx, trait_def_id, method) {
155+
None | Some(MethodViolationCode::WhereClauseReferencesSelf) => true,
156+
Some(_) => false,
159157
}
160158
}
161159

@@ -724,5 +722,5 @@ fn contains_illegal_self_type_reference<'tcx>(
724722
}
725723

726724
pub(super) fn is_object_safe_provider(tcx: TyCtxt<'_>, trait_def_id: DefId) -> bool {
727-
tcx.object_safety_violations(trait_def_id).is_empty()
725+
object_safety_violations(tcx, trait_def_id).is_empty()
728726
}

src/librustc_typeck/astconv.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ use errors::{Applicability, DiagnosticId};
1313
use rustc::hir::intravisit::Visitor;
1414
use rustc::lint::builtin::AMBIGUOUS_ASSOCIATED_ITEMS;
1515
use rustc::traits;
16+
use rustc::traits::astconv_object_safety_violations;
1617
use rustc::traits::error_reporting::report_object_safety_error;
1718
use rustc::ty::subst::{self, InternalSubsts, Subst, SubstsRef};
1819
use rustc::ty::wf::object_region_bounds;
@@ -1453,7 +1454,7 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
14531454
// to avoid ICEs.
14541455
for item in &regular_traits {
14551456
let object_safety_violations =
1456-
tcx.astconv_object_safety_violations(item.trait_ref().def_id());
1457+
astconv_object_safety_violations(tcx, item.trait_ref().def_id());
14571458
if !object_safety_violations.is_empty() {
14581459
report_object_safety_error(
14591460
tcx,

src/librustc_typeck/check/cast.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ use rustc::middle::lang_items;
3838
use rustc::session::Session;
3939
use rustc::traits;
4040
use rustc::traits::error_reporting::report_object_safety_error;
41+
use rustc::traits::object_safety_violations;
4142
use rustc::ty::adjustment::AllowTwoPhase;
4243
use rustc::ty::cast::{CastKind, CastTy};
4344
use rustc::ty::error::TypeError;
@@ -519,7 +520,7 @@ impl<'a, 'tcx> CastCheck<'tcx> {
519520
}
520521

521522
fn report_object_unsafe_cast(&self, fcx: &FnCtxt<'a, 'tcx>, did: DefId) {
522-
let violations = fcx.tcx.object_safety_violations(did);
523+
let violations = object_safety_violations(fcx.tcx, did);
523524
let mut err = report_object_safety_error(fcx.tcx, self.cast_span, did, violations);
524525
err.note(&format!("required by cast to type '{}'", fcx.ty_to_string(self.cast_ty)));
525526
err.emit();

0 commit comments

Comments
 (0)