Skip to content

Instantly share code, notes, and snippets.

@kevinmehall
Created July 18, 2015 22:59
Show Gist options
  • Save kevinmehall/75018c1b69da366e5fc8 to your computer and use it in GitHub Desktop.
Save kevinmehall/75018c1b69da366e5fc8 to your computer and use it in GitHub Desktop.
Check Saleae CSV dumps from Tessel 2 bridge for timing margin
use std::io;
use std::io::prelude::*;
use std::fs;
use std::env;
use std::cmp::Ordering;
fn main() {
let args: Vec<String> = env::args().collect();
let file = io::BufReader::new(fs::File::open(&args[1]).unwrap());
let mut sync_to_cs = vec![];
let mut sync_to_ready = vec![];
let mut data_to_cs = vec![];
let mut data_to_ready = vec![];
let cs_probe = 1;
let sync_probe = 5;
let ready_probe = 7;
let mut last_sync = 0f64;
let mut old_state = 0;
for line in file.lines().skip(1) {
let line: String = line.unwrap();
let mut components = line.split(',').map(|x| x.trim());
let time = components.next().unwrap().parse().unwrap();
let mut state = 0;
for (i, v) in components.take(8).enumerate() {
state |= v.parse::<u8>().unwrap() << i;
}
let changed = state^old_state;
let falling = changed & old_state;
let sync_high = state & (1<<sync_probe) != 0;
let sync_changed = changed & (1<<sync_probe) != 0;
let ready_falling = falling & (1<<ready_probe) != 0;
let cs_falling = falling & (1<<cs_probe) != 0;
if sync_changed { last_sync = time; }
if !sync_high {
if ready_falling { sync_to_ready.push(time - last_sync); }
if cs_falling { sync_to_cs.push(time - last_sync); }
} else {
if ready_falling { data_to_ready.push(time - last_sync); }
if cs_falling { data_to_cs.push(time - last_sync); }
}
old_state = state;
}
println!("{} transactions", sync_to_cs.len());
print_stats("sync_to_ready", &mut sync_to_ready);
print_stats("sync_to_cs", &mut sync_to_cs);
print_margin("control:", &sync_to_ready, &sync_to_cs);
println!("\n{} with data", data_to_cs.len());
print_stats("data_to_ready", &mut data_to_ready);
print_stats("data_to_cs", &mut data_to_cs);
print_margin("data:", &data_to_ready, &data_to_cs);
}
trait Percentile {
type V;
fn percentile(&self, pos: f64) -> Self::V;
}
impl Percentile for [f64] {
type V = f64;
fn percentile(&self, pos: f64) -> f64 {
let max = (self.len()-1) as f64;
self[(max * pos).round() as usize]
}
}
fn print_stats(name: &str, data: &mut [f64]) {
data.sort_by(|a, b| a.partial_cmp(b).unwrap_or(Ordering::Less));
println!("{:15} {:>7.02}us {:>7.02}us {:>7.02}us {:>7.02}us {:>7.02}us",
name,
data.percentile(0.0)*1e6,
data.percentile(0.1)*1e6,
data.percentile(0.5)*1e6,
data.percentile(0.9)*1e6,
data.percentile(1.0)*1e6
);
}
fn print_margin(name: &str, d1: &[f64], d2: &[f64]) {
let margin = d2[0] - d1[d1.len()-1];
println!("{:12} {:>7.02}us", name, margin*1e6);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment