Skip to content

Commit ded88b9

Browse files
committed
Added bound checking on trait definitions. Closes rust-lang#23.
1 parent 2b1444e commit ded88b9

File tree

4 files changed

+77
-3
lines changed

4 files changed

+77
-3
lines changed

src/semcheck/traverse.rs

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ pub fn run_analysis<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, old: DefId, new: DefI
5454
diff_types(&mut changes, &id_mapping, tcx, old, new);
5555
}
5656

57-
// fourth pass still
57+
// fourth pass on impls
5858
diff_inherent_impls(&mut changes, &id_mapping, tcx);
5959
diff_trait_impls(&mut changes, &id_mapping, tcx);
6060

@@ -655,6 +655,9 @@ fn diff_types<'a, 'tcx>(changes: &mut ChangeSet<'tcx>,
655655
}
656656
}
657657
},
658+
Trait(_) => {
659+
cmp_bounds(changes, id_mapping, tcx, old_def_id, new_def_id);
660+
},
658661
_ => (),
659662
}
660663
}
@@ -769,15 +772,15 @@ fn diff_trait_impls<'a, 'tcx>(changes: &mut ChangeSet<'tcx>,
769772
}
770773
}
771774

772-
/// Compare two types and possibly register the error.
775+
/// Compare two types and their trait bounds and possibly register the error.
773776
fn cmp_types<'a, 'tcx>(changes: &mut ChangeSet<'tcx>,
774777
id_mapping: &IdMapping,
775778
tcx: TyCtxt<'a, 'tcx, 'tcx>,
776779
orig_def_id: DefId,
777780
target_def_id: DefId,
778781
orig: Ty<'tcx>,
779782
target: Ty<'tcx>) {
780-
info!("comparing types of {:?} / {:?}:\n {:?} / {:?}",
783+
info!("comparing types and bounds of {:?} / {:?}:\n {:?} / {:?}",
781784
orig_def_id, target_def_id, orig, target);
782785

783786
tcx.infer_ctxt().enter(|infcx| {
@@ -815,6 +818,29 @@ fn cmp_types<'a, 'tcx>(changes: &mut ChangeSet<'tcx>,
815818
});
816819
}
817820

821+
/// Compare two sets of trait bounds and possibly register the error.
822+
fn cmp_bounds<'a, 'tcx>(changes: &mut ChangeSet<'tcx>,
823+
id_mapping: &IdMapping,
824+
tcx: TyCtxt<'a, 'tcx, 'tcx>,
825+
orig_def_id: DefId,
826+
target_def_id: DefId) {
827+
info!("comparing bounds of {:?} / {:?}", orig_def_id, target_def_id);
828+
829+
tcx.infer_ctxt().enter(|infcx| {
830+
let compcx = TypeComparisonContext::target_new(&infcx, id_mapping);
831+
832+
let orig_substs = Substs::identity_for_item(infcx.tcx, target_def_id);
833+
let target_substs = compcx.compute_target_default_substs(target_def_id);
834+
835+
compcx.check_bounds_bidirectional(changes,
836+
tcx,
837+
orig_def_id,
838+
target_def_id,
839+
orig_substs,
840+
target_substs);
841+
})
842+
}
843+
818844
/// Compare two implementations and indicate whether the target one is compatible with the
819845
/// original one.
820846
fn match_trait_impl<'a, 'tcx>(id_mapping: &IdMapping,

tests/cases/traits/new.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,3 +38,11 @@ pub trait Ghi { }
3838
pub trait Hij {
3939
type A;
4040
}
41+
42+
pub trait Klm : Clone { }
43+
44+
pub trait Nop { }
45+
46+
pub trait Qrs<A: Clone> { }
47+
48+
pub trait Tuv<A> { }

tests/cases/traits/old.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,3 +36,11 @@ pub trait Ghi {
3636
}
3737

3838
pub trait Hij { }
39+
40+
pub trait Klm { }
41+
42+
pub trait Nop : Clone { }
43+
44+
pub trait Qrs<A> { }
45+
46+
pub trait Tuv<A: Clone> { }

tests/cases/traits/stdout

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,3 +124,35 @@ warning: added item to trait (breaking)
124124
39 | type A;
125125
| ^^^^^^^
126126

127+
warning: breaking changes in `Klm`
128+
--> $REPO_PATH/tests/cases/traits/new.rs:42:1
129+
|
130+
42 | pub trait Klm : Clone { }
131+
| ^^^^^^^^^^^^^^^^^^^^^^^^^
132+
|
133+
= warning: added bound: `Self: std::clone::Clone` (breaking)
134+
135+
warning: technically breaking changes in `Nop`
136+
--> $REPO_PATH/tests/cases/traits/new.rs:44:1
137+
|
138+
44 | pub trait Nop { }
139+
| ^^^^^^^^^^^^^^^^^
140+
|
141+
= note: removed bound: `Self: std::clone::Clone` (technically breaking)
142+
143+
warning: breaking changes in `Qrs`
144+
--> $REPO_PATH/tests/cases/traits/new.rs:46:1
145+
|
146+
46 | pub trait Qrs<A: Clone> { }
147+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^
148+
|
149+
= warning: added bound: `A: std::clone::Clone` (breaking)
150+
151+
warning: technically breaking changes in `Tuv`
152+
--> $REPO_PATH/tests/cases/traits/new.rs:48:1
153+
|
154+
48 | pub trait Tuv<A> { }
155+
| ^^^^^^^^^^^^^^^^^^^^
156+
|
157+
= note: removed bound: `A: std::clone::Clone` (technically breaking)
158+

0 commit comments

Comments
 (0)