1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80

use std::time;
use std::fs;
use std::result;

use anyhow::{anyhow,Context};

use apigpio::*;
use apigpio::Level::*;

use picollar::*;
use picollar::local::{prepare_xmit};
use sequence::*;

use tokio::time::delay_for;

async fn transmit(pi : &Connection, pulses : &[Pulse], ms : u32)
                  -> Result<()> {
  prepare_xmit(pi).await?;
  pi.wave_clear().await?;
  pi.wave_add_generic(&pulses).await?;
  println!("{}us / {}us",
           pi.wave_get_micros().await?,
           pi.wave_get_max_micros().await?);
  let w = pi.wave_create().await?;
  pi.wave_send_repeat(w).await?;
  delay_for(time::Duration::from_millis(ms as u64)).await;
  pi.wave_tx_stop().await?;
  pi.wave_clear().await?;
  pi.gpio_write(GPIO,L).await?;
  Ok(())
}

const USAGE : &str = 
"usage: sync KEY|KEY-FILE|CFG-FILE CHANNEL MODE [POWER] [MS]";

fn get_key(args : &mut picollar::args::Args) -> result::Result<CollarKey,anyhow::Error> {
  let arg = args.next().ok_or_else(|| anyhow!("missing argument"))?;
  if let Ok(k) = arg.parse() { return Ok(k) }

  let content = fs::read_to_string(&arg)
    .context("not 4 hex digits, treating as filename")?;
  if let Ok(k) = content.trim().parse() { return Ok(k) }

  let cfg = config::parse(&content, arg)
    .context("file contents not 4 hex digits, treatng as TOML config file")?;
  let k = cfg.collar_key()?;
  Ok(k)
}

async fn execute() -> Result<()> {
  let mut args = picollar::args::Args::new(USAGE);

  let _ : String     = args.parse_next("argv0");

  let key = get_key(&mut args)
    .context("KEY|KEY-FILE|CFG-FILE").expect(USAGE);

  let channel        = args.parse_next("channel");
  let mode    : Mode = args.parse_next("mode");
  let power = if !mode.needs_power() { 1 } else {
                       args.parse_next("power")
  };
  let ms = if args.len()==0 { 400 } else {
                       args.parse_next("duratior")
  };
  let c = Command { key, channel, mode, power };

  let (pulses, desc) = mk_pulses(&c);
  println!("will transmit {}", desc);

  let pi = Connection::new().await?;
  transmit(&pi, &pulses, ms).await?;
  Ok(())
}

#[tokio::main]
async fn main(){
  execute().await.expect("error");
}