diagnostics: use DeepRejectCtxt for check · rust-lang/rust@c6fb0f3 (original) (raw)

`@@ -4,6 +4,7 @@ use rustc_hir as hir;

`

4

4

`use rustc_hir::def::DefKind;

`

5

5

`use rustc_middle::traits::{ObligationCause, ObligationCauseCode};

`

6

6

`use rustc_middle::ty::error::{ExpectedFound, TypeError};

`

``

7

`+

use rustc_middle::ty::fast_reject::{DeepRejectCtxt, TreatParams};

`

7

8

`use rustc_middle::ty::print::{FmtPrinter, Printer};

`

8

9

`use rustc_middle::ty::{self, suggest_constraining_type_param, Ty};

`

9

10

`use rustc_span::def_id::DefId;

`

`@@ -313,9 +314,15 @@ impl Trait for X {

`

313

314

`(ty::Dynamic(t, _, ty::DynKind::Dyn), _)

`

314

315

`if let Some(def_id) = t.principal_def_id() =>

`

315

316

`{

`

316

``

`-

let has_non_blanket_impl =

`

317

``

`-

tcx.non_blanket_impls_for_ty(def_id, values.found).next().is_some();

`

318

``

`-

if has_non_blanket_impl {

`

``

317

`+

let mut has_matching_impl = false;

`

``

318

`+

tcx.for_each_relevant_impl(def_id, values.found, |did| {

`

``

319

`+

if DeepRejectCtxt::new(tcx, TreatParams::ForLookup)

`

``

320

`+

.types_may_unify(values.found, tcx.type_of(did).skip_binder())

`

``

321

`+

{

`

``

322

`+

has_matching_impl = true;

`

``

323

`+

}

`

``

324

`+

});

`

``

325

`+

if has_matching_impl {

`

319

326

`let trait_name = tcx.item_name(def_id);

`

320

327

` diag.help(format!(

`

321

328

`` "{} implements {trait_name} so you could box the found value \

``

`@@ -328,9 +335,15 @@ impl Trait for X {

`

328

335

`(_, ty::Dynamic(t, _, ty::DynKind::Dyn))

`

329

336

`if let Some(def_id) = t.principal_def_id() =>

`

330

337

`{

`

331

``

`-

let has_non_blanket_impl =

`

332

``

`-

tcx.non_blanket_impls_for_ty(def_id, values.expected).next().is_some();

`

333

``

`-

if has_non_blanket_impl {

`

``

338

`+

let mut has_matching_impl = false;

`

``

339

`+

tcx.for_each_relevant_impl(def_id, values.expected, |did| {

`

``

340

`+

if DeepRejectCtxt::new(tcx, TreatParams::ForLookup)

`

``

341

`+

.types_may_unify(values.expected, tcx.type_of(did).skip_binder())

`

``

342

`+

{

`

``

343

`+

has_matching_impl = true;

`

``

344

`+

}

`

``

345

`+

});

`

``

346

`+

if has_matching_impl {

`

334

347

`let trait_name = tcx.item_name(def_id);

`

335

348

` diag.help(format!(

`

336

349

`` "{} implements {trait_name} so you could change the expected \

``

`@@ -342,9 +355,15 @@ impl Trait for X {

`

342

355

`(ty::Dynamic(t, _, ty::DynKind::DynStar), _)

`

343

356

`if let Some(def_id) = t.principal_def_id() =>

`

344

357

`{

`

345

``

`-

let has_non_blanket_impl =

`

346

``

`-

tcx.non_blanket_impls_for_ty(def_id, values.found).next().is_some();

`

347

``

`-

if has_non_blanket_impl {

`

``

358

`+

let mut has_matching_impl = false;

`

``

359

`+

tcx.for_each_relevant_impl(def_id, values.found, |did| {

`

``

360

`+

if DeepRejectCtxt::new(tcx, TreatParams::ForLookup)

`

``

361

`+

.types_may_unify(values.found, tcx.type_of(did).skip_binder())

`

``

362

`+

{

`

``

363

`+

has_matching_impl = true;

`

``

364

`+

}

`

``

365

`+

});

`

``

366

`+

if has_matching_impl {

`

348

367

`let trait_name = tcx.item_name(def_id);

`

349

368

` diag.help(format!(

`

350

369

`` "{} implements {trait_name}, #[feature(dyn_star)] is likely \

``