//! How many copies of a captured buffer does a container hold?
//!
//! The twins showed that two resources decoding to one buffer can mean the
//! container really holds two (mirrored) copies and our scan found only one.
//! This asks that question for any draw: give it a `vbase`, and it reports every
//! offset whose leading vertices match the draw's dumped positions — directly, and
//! X-mirrored.
//!
//! Usage: locate_draw <container.xpr> <capture.log> <vbase-hex>...
use sylpheed_formats::ship_capture::{parse_capture, parse_drawlog};

fn main() {
    let a: Vec<String> = std::env::args().collect();
    let bytes = std::fs::read(&a[1]).expect("container");
    let text = std::fs::read_to_string(&a[2]).expect("log");
    let mut draws = parse_capture(&text);
    if draws.is_empty() {
        draws = parse_drawlog(&text);
    }
    let be = |at: usize| f32::from_be_bytes(bytes[at..at + 4].try_into().unwrap());

    for want in &a[3..] {
        let vb = u32::from_str_radix(want.trim_start_matches("0x"), 16).expect("hex vbase");
        let Some(d) = draws.iter().find(|d| d.vbase == vb) else {
            println!("vbase 0x{vb:08X}: not in this log");
            continue;
        };
        let n = d.pos.len().min(8);
        let mut direct = Vec::new();
        let mut mirror = Vec::new();
        for o in (0..bytes.len().saturating_sub(12 + 64 * 24)).step_by(4) {
            for (flip, out) in [(1.0f32, &mut direct), (-1.0f32, &mut mirror)] {
                let hit = (0..n).all(|k| {
                    let at = o + k * 24;
                    (be(at) - flip * d.pos[k][0]).abs() <= 1e-4
                        && (be(at + 4) - d.pos[k][1]).abs() <= 1e-4
                        && (be(at + 8) - d.pos[k][2]).abs() <= 1e-4
                });
                if hit {
                    out.push(o);
                }
            }
        }
        println!(
            "vbase 0x{vb:08X} vcount={}: {} direct copy/copies {:x?}, {} mirrored {:x?}",
            d.vcount,
            direct.len(),
            &direct[..],
            mirror.len(),
            &mirror[..]
        );
    }
}
