Skip to content

Commit a2fbe4d

Browse files
committed
Construct the graph only when it is needed to report errors.
1 parent e706590 commit a2fbe4d

File tree

1 file changed

+57
-55
lines changed
  • src/librustc/middle/typeck/infer/region_inference

1 file changed

+57
-55
lines changed

src/librustc/middle/typeck/infer/region_inference/mod.rs

Lines changed: 57 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -722,63 +722,21 @@ struct RegionAndOrigin {
722722
origin: SubregionOrigin,
723723
}
724724

725-
type Graph = graph::Graph<(), Constraint>;
726-
type GraphNode = graph::Node<()>;
727-
type GraphEdge = graph::Edge<Constraint>;
725+
type RegionGraph = graph::Graph<(), Constraint>;
728726

729727
impl RegionVarBindings {
730-
fn infer_variable_values(&mut self,
728+
fn infer_variable_values(&self,
731729
errors: &mut OptVec<RegionResolutionError>)
732730
-> ~[VarValue] {
733731
let mut var_data = self.construct_var_data();
734732
self.expansion(var_data);
735733
self.contraction(var_data);
736-
let graph = self.construct_graph();
737-
self.collect_concrete_region_errors(&graph, errors);
738-
self.extract_values_and_collect_conflicts(&graph, var_data, errors)
734+
self.collect_concrete_region_errors(errors);
735+
self.extract_values_and_collect_conflicts(var_data, errors)
739736
}
740737

741-
fn construct_graph(&mut self) -> Graph {
742-
let num_vars = self.num_vars();
743-
let num_edges = self.constraints.len();
744-
745-
let mut graph = graph::Graph::with_capacity(num_vars + 1,
746-
num_edges);
747-
748-
for uint::range(0, num_vars) |var_idx| {
749-
graph.add_node(());
750-
}
751-
let dummy_idx = graph.add_node(());
752-
753-
for self.constraints.iter().advance |(constraint, _)| {
754-
match *constraint {
755-
ConstrainVarSubVar(a_id, b_id) => {
756-
graph.add_edge(NodeIndex(a_id.to_uint()),
757-
NodeIndex(b_id.to_uint()),
758-
*constraint);
759-
}
760-
ConstrainRegSubVar(_, b_id) => {
761-
graph.add_edge(dummy_idx,
762-
NodeIndex(b_id.to_uint()),
763-
*constraint);
764-
}
765-
ConstrainVarSubReg(a_id, _) => {
766-
graph.add_edge(NodeIndex(a_id.to_uint()),
767-
dummy_idx,
768-
*constraint);
769-
}
770-
ConstrainRegSubReg(*) => {
771-
// Relations between two concrete regions do not
772-
// require an edge in the graph.
773-
}
774-
}
775-
}
776-
777-
return graph;
778-
}
779-
780-
fn construct_var_data(&mut self) -> ~[VarData] {
781-
vec::from_fn(self.num_vars(), |var_idx| {
738+
fn construct_var_data(&self) -> ~[VarData] {
739+
vec::from_fn(self.num_vars(), |_| {
782740
VarData {
783741
// All nodes are initially classified as contracting; during
784742
// the expansion phase, we will shift the classification for
@@ -790,7 +748,7 @@ impl RegionVarBindings {
790748
})
791749
}
792750

793-
fn expansion(&mut self, var_data: &mut [VarData]) {
751+
fn expansion(&self, var_data: &mut [VarData]) {
794752
do self.iterate_until_fixed_point("Expansion") |constraint| {
795753
match *constraint {
796754
ConstrainRegSubVar(a_region, b_vid) => {
@@ -957,7 +915,6 @@ impl RegionVarBindings {
957915

958916
fn collect_concrete_region_errors(
959917
&self,
960-
graph: &Graph,
961918
errors: &mut OptVec<RegionResolutionError>)
962919
{
963920
for self.constraints.iter().advance |(constraint, _)| {
@@ -985,7 +942,6 @@ impl RegionVarBindings {
985942

986943
fn extract_values_and_collect_conflicts(
987944
&self,
988-
graph: &Graph,
989945
var_data: &[VarData],
990946
errors: &mut OptVec<RegionResolutionError>)
991947
-> ~[VarValue]
@@ -1005,6 +961,8 @@ impl RegionVarBindings {
1005961
// overlapping locations.
1006962
let mut dup_vec = vec::from_elem(self.num_vars(), uint::max_value);
1007963

964+
let mut opt_graph = None;
965+
1008966
for uint::range(0, self.num_vars()) |idx| {
1009967
match var_data[idx].value {
1010968
Value(_) => {
@@ -1040,6 +998,11 @@ impl RegionVarBindings {
1040998
starts to create problems we'll have to revisit
1041999
this portion of the code and think hard about it. =) */
10421000

1001+
if opt_graph.is_none() {
1002+
opt_graph = Some(self.construct_graph());
1003+
}
1004+
let graph = opt_graph.get_ref();
1005+
10431006
let node_vid = RegionVid { id: idx };
10441007
match var_data[idx].classification {
10451008
Expanding => {
@@ -1058,9 +1021,48 @@ impl RegionVarBindings {
10581021
vec::from_fn(self.num_vars(), |idx| var_data[idx].value)
10591022
}
10601023

1024+
fn construct_graph(&self) -> RegionGraph {
1025+
let num_vars = self.num_vars();
1026+
let num_edges = self.constraints.len();
1027+
1028+
let mut graph = graph::Graph::with_capacity(num_vars + 1,
1029+
num_edges);
1030+
1031+
for uint::range(0, num_vars) |_| {
1032+
graph.add_node(());
1033+
}
1034+
let dummy_idx = graph.add_node(());
1035+
1036+
for self.constraints.iter().advance |(constraint, _)| {
1037+
match *constraint {
1038+
ConstrainVarSubVar(a_id, b_id) => {
1039+
graph.add_edge(NodeIndex(a_id.to_uint()),
1040+
NodeIndex(b_id.to_uint()),
1041+
*constraint);
1042+
}
1043+
ConstrainRegSubVar(_, b_id) => {
1044+
graph.add_edge(dummy_idx,
1045+
NodeIndex(b_id.to_uint()),
1046+
*constraint);
1047+
}
1048+
ConstrainVarSubReg(a_id, _) => {
1049+
graph.add_edge(NodeIndex(a_id.to_uint()),
1050+
dummy_idx,
1051+
*constraint);
1052+
}
1053+
ConstrainRegSubReg(*) => {
1054+
// Relations between two concrete regions do not
1055+
// require an edge in the graph.
1056+
}
1057+
}
1058+
}
1059+
1060+
return graph;
1061+
}
1062+
10611063
fn collect_error_for_expanding_node(
10621064
&self,
1063-
graph: &Graph,
1065+
graph: &RegionGraph,
10641066
var_data: &[VarData],
10651067
dup_vec: &mut [uint],
10661068
node_idx: RegionVid,
@@ -1105,7 +1107,7 @@ impl RegionVarBindings {
11051107

11061108
fn collect_error_for_contracting_node(
11071109
&self,
1108-
graph: &Graph,
1110+
graph: &RegionGraph,
11091111
var_data: &[VarData],
11101112
dup_vec: &mut [uint],
11111113
node_idx: RegionVid,
@@ -1148,7 +1150,7 @@ impl RegionVarBindings {
11481150
}
11491151

11501152
fn collect_concrete_regions(&self,
1151-
graph: &Graph,
1153+
graph: &RegionGraph,
11521154
var_data: &[VarData],
11531155
orig_node_idx: RegionVid,
11541156
dir: Direction,
@@ -1202,7 +1204,7 @@ impl RegionVarBindings {
12021204

12031205
fn process_edges(this: &RegionVarBindings,
12041206
state: &mut WalkState,
1205-
graph: &Graph,
1207+
graph: &RegionGraph,
12061208
source_vid: RegionVid,
12071209
dir: Direction) {
12081210
debug!("process_edges(source_vid=%?, dir=%?)", source_vid, dir);

0 commit comments

Comments
 (0)