1
use std::process::Command;
2

            
3
2
fn main() {
4
2
    let crate_dir = std::env::var("CARGO_MANIFEST_DIR").unwrap();
5

            
6
    // Rerun if source files change (for cbindgen)
7
2
    println!("cargo:rerun-if-changed=src/lib.rs");
8
2
    println!("cargo:rerun-if-changed=src/generated.rs");
9
2
    println!("cargo:rerun-if-changed=cbindgen.toml");
10

            
11
    // Step 1: Generate Rust structs from org document using emacs
12
2
    println!("cargo:rerun-if-changed=../../doc/nomisync-script-format.org");
13

            
14
2
    let status = Command::new("emacs")
15
2
        .args([
16
2
            "-q",
17
2
            "--batch",
18
2
            "../../doc/nomisync-script-format.org",
19
2
            "--eval",
20
2
            "(setq org-confirm-babel-evaluate nil create-lockfiles nil)",
21
2
            "--eval",
22
2
            "(org-babel-goto-named-src-block \"generate-structs\")",
23
2
            "--eval",
24
2
            "(org-babel-execute-src-block)",
25
2
            "-f",
26
2
            "kill-emacs",
27
2
        ])
28
2
        .status();
29

            
30
2
    match status {
31
2
        Ok(s) if s.success() => {}
32
        Ok(s) => eprintln!("Warning: org-babel-tangle exited with {s}"),
33
        Err(e) => eprintln!("Warning: Failed to run emacs for org-babel-tangle: {e}"),
34
    }
35

            
36
    // Step 2: Generate C header from Rust code using cbindgen
37
2
    let header_path = format!("{crate_dir}/scripting_format.h");
38
2
    let config_path = format!("{crate_dir}/cbindgen.toml");
39

            
40
2
    match cbindgen::Builder::new()
41
2
        .with_crate(&crate_dir)
42
2
        .with_config(cbindgen::Config::from_file(&config_path).unwrap())
43
2
        .with_src(format!("{crate_dir}/src/lib.rs"))
44
2
        .with_src(format!("{crate_dir}/src/generated.rs"))
45
2
        .generate()
46
    {
47
2
        Ok(bindings) => {
48
2
            bindings.write_to_file(&header_path);
49
2
            eprintln!("Generated C header: {header_path}");
50
2
        }
51
        Err(e) => eprintln!("Warning: cbindgen failed: {e}"),
52
    }
53
2
}