let val: usize = point.into();
let mid = val % 2 == 1;
let bb = val >> 16;
- let stmt = (val >> 1) & 0xFFFF;
- print!("{}(bb{}[{}])", if mid { "Mid" } else { "Start" }, bb, stmt);
+ let stmt = (val >> 1) & ((1 << 15) - 1);
+ eprint!("{}(bb{}[{}])", if mid { "Mid" } else { "Start" }, bb, stmt);
}
/// Run the polonius analysis on the given facts (for a single function).
/// Right now, results are only printed and not propagated back to the gccrs.
#[no_mangle]
-pub unsafe extern "C" fn polonius_run(input: gccrs_ffi::FactsView, dump_enabled: bool) {
+pub unsafe extern "C" fn polonius_run(
+ input: gccrs_ffi::FactsView,
+ dump_enabled: bool,
+) -> gccrs_ffi::Output {
let facts = AllFacts::<GccrsFacts>::from(input);
- let output = Output::compute(&facts, polonius_engine::Algorithm::Naive, dump_enabled);
-
- // FIXME: Temporary output
- println!("Polonius analysis completed. Results:");
- println!("Errors: {:#?}", output.errors);
- println!("Subset error: {:#?}", output.subset_errors);
- println!("Move error: {:#?}", output.move_errors);
-
- println!("Subsets:");
- let mut subset_vec: Vec<_> = output.subset.iter().collect();
- subset_vec.sort_by_key(|&(point, _)| point);
- for (point, subsets) in subset_vec {
- print_point(*point);
- println!(": {{");
- for (&lhs, rhss) in subsets {
- for &rhs in rhss {
- println!(" {} <= {}", usize::from(lhs), usize::from(rhs));
+ let output = Output::compute(
+ &facts,
+ polonius_engine::Algorithm::DatafrogOpt,
+ dump_enabled,
+ );
+
+ if dump_enabled {
+ eprintln!("Subsets:");
+ let mut subset_vec: Vec<_> = output.subset.iter().collect();
+ subset_vec.sort_by_key(|&(point, _)| point);
+ for (point, subsets) in subset_vec {
+ print_point(*point);
+ eprintln!(": {{");
+ for (&lhs, rhss) in subsets {
+ for &rhs in rhss {
+ eprintln!(" {} <= {}", usize::from(lhs), usize::from(rhs));
+ }
}
+ eprintln!("}}");
}
- println!("}}");
- }
- println!("Subset anywhere: {:#?}", output.subset_anywhere);
-
- // Print origin live on entry
- println!("Origin live on entry:");
- let mut origin_vec: Vec<_> = output.origin_live_on_entry.iter().collect();
- origin_vec.sort_by_key(|&(point, _)| point);
- for (point, origins) in origin_vec {
- print_point(*point);
- println!(": {{");
- for &origin in origins {
- println!(" {}", usize::from(origin));
+
+ // Print origin live on entry
+ eprintln!("Origin live on entry:");
+ let mut origin_vec: Vec<_> = output.origin_live_on_entry.iter().collect();
+ origin_vec.sort_by_key(|&(point, _)| point);
+ for (point, origins) in origin_vec {
+ print_point(*point);
+ eprintln!(": {{");
+ for &origin in origins {
+ eprintln!(" {}", usize::from(origin));
+ }
+ eprintln!("}}");
+ }
+
+ eprintln!("Origin contains loan at:");
+ let mut origin_vec: Vec<_> = output.origin_contains_loan_at.iter().collect();
+ origin_vec.sort_by_key(|&(point, _)| point);
+ for (point, origins) in origin_vec {
+ print_point(*point);
+ eprintln!(": {{");
+ for (&origin, loans) in origins {
+ eprintln!(
+ " {}:{:?}",
+ usize::from(origin),
+ loans.iter().map(|&e| usize::from(e)).collect::<Vec<_>>()
+ );
+ }
+ eprintln!("}}");
+ }
+
+ eprintln!("Polonius analysis completed. Results:");
+ if output.errors.len() > 0 {
+ eprintln!("Errors:");
+ for (&point, errors) in &output.errors {
+ print_point(point);
+ eprintln!(": {:?}", errors);
+ }
+ }
+ if output.subset_errors.len() > 0 {
+ eprintln!("Subset errors:");
+ for (&point, errors) in &output.subset_errors {
+ print_point(point);
+ eprintln!(": {:?}", errors);
+ }
+ }
+ if output.move_errors.len() > 0 {
+ eprintln!("Move errors:");
+ for (&point, moves) in &output.move_errors {
+ print_point(point);
+ eprintln!("{:?}", moves);
+ }
}
- println!("}}");
}
+
+ return gccrs_ffi::Output {
+ loan_errors: output.errors.len() > 0,
+ subset_errors: output.subset_errors.len() > 0,
+ move_errors: output.move_errors.len() > 0,
+ };
}
&Polonius::Facts::dump_placeholder);
}
- Polonius::polonius_run (facts.freeze (), rust_be_debug_p ());
+ auto result
+ = Polonius::polonius_run (facts.freeze (), rust_be_debug_p ());
+
+ if (result.loan_errors)
+ {
+ rust_error_at (func->get_locus (), "Found loan errors in function %s",
+ func->get_function_name ().as_string ().c_str ());
+ }
+ if (result.subset_errors)
+ {
+ rust_error_at (func->get_locus (),
+ "Found subset errors in function %s. Some lifetime "
+ "constraints need to be added.",
+ func->get_function_name ().as_string ().c_str ());
+ }
+ if (result.move_errors)
+ {
+ rust_error_at (func->get_locus (), "Found move errors in function %s",
+ func->get_function_name ().as_string ().c_str ());
+ }
}
for (auto closure ATTRIBUTE_UNUSED : collector.get_closures ())