actually works now! maybe
This commit is contained in:
parent
4a21613f42
commit
b1d50fb611
131
memoribbon.rs
131
memoribbon.rs
|
@ -4,25 +4,56 @@ use std::io::prelude::*;
|
|||
use std::fs::File;
|
||||
use std::io;
|
||||
|
||||
static FILTER_STRENGTH:u8 = 10; // how severely to low-pass the incoming data
|
||||
static RESET_THRESH:usize = 20; // this many samples with no bits = reset byte position
|
||||
static FILTER_STRENGTH:u8 = 200; // how severely to low-pass the incoming data
|
||||
static OVERSAMPLE_FACTOR:usize = 10; // how many samples long are each bit in the decoder input?
|
||||
static INVERT:bool = false; // whether or not the source inverts the samples
|
||||
|
||||
struct StreamCoder {
|
||||
encoder:[u16;256],
|
||||
decoder:[u8;4096],
|
||||
decoder:[Option<u8>;65536],
|
||||
}
|
||||
|
||||
fn streamcoder_gen() -> StreamCoder {
|
||||
let mut output_a:[u16;256] = [0x0000;256];
|
||||
let mut output_b:[u8;4096] = [0x20;4096];
|
||||
let mut output_b:[Option<u8>;65536] = [None;65536];
|
||||
let mut a:u8 = 0;
|
||||
let mut b:u16 = 0;
|
||||
loop {
|
||||
if b.count_ones() == b.count_zeros()-4 {
|
||||
let mut score:i8 = 0;
|
||||
let mut max_consec:u8 = 0;
|
||||
let mut consec:u8 = 0;
|
||||
let mut state:bool = false;
|
||||
for i in 0..16 {
|
||||
let thisbit = b & (0x01 << i) != 0x00;
|
||||
if thisbit != state {
|
||||
state = thisbit;
|
||||
consec = 1;
|
||||
} else {
|
||||
consec += 1;
|
||||
}
|
||||
if consec > max_consec {
|
||||
max_consec = consec;
|
||||
}
|
||||
if thisbit {
|
||||
score += 1;
|
||||
} else {
|
||||
score -= 1;
|
||||
}
|
||||
}
|
||||
let mut errors:[u16;16] = [0x0000;16];
|
||||
let mut errorcollide:bool = false;
|
||||
for i in 0..16 {
|
||||
errors[i] = b ^ (0x01 << i);
|
||||
if output_b[errors[i] as usize] != None {
|
||||
errorcollide = true;
|
||||
}
|
||||
}
|
||||
if score == 0 && max_consec <= 8 && !errorcollide {
|
||||
output_a[a as usize] = b;
|
||||
output_b[b as usize] = a;
|
||||
output_b[b as usize] = Some(a);
|
||||
for error in errors.iter() {
|
||||
output_b[*error as usize] = Some(a);
|
||||
}
|
||||
if a == 0xFF {
|
||||
break;
|
||||
} else {
|
||||
|
@ -37,9 +68,9 @@ fn streamcoder_gen() -> StreamCoder {
|
|||
};
|
||||
}
|
||||
|
||||
fn code_bits(n:u16) -> [bool;12] {
|
||||
let mut output:[bool;12] = [false;12];
|
||||
for i in 0..12 {
|
||||
fn code_bits(n:u16) -> [bool;16] {
|
||||
let mut output:[bool;16] = [false;16];
|
||||
for i in 0..16 {
|
||||
output[i] = (n >> i) & 0x01 == 0x01;
|
||||
}
|
||||
return output;
|
||||
|
@ -47,10 +78,10 @@ fn code_bits(n:u16) -> [bool;12] {
|
|||
|
||||
fn bits_code(b:&[bool]) -> u16 {
|
||||
let mut output:u16 = 0;
|
||||
if b.len() < 12 {
|
||||
if b.len() < 16 {
|
||||
return 0;
|
||||
}
|
||||
for i in 0..12 {
|
||||
for i in 0..16 {
|
||||
if b[i] {
|
||||
output += (0x01 << i) as u16;
|
||||
}
|
||||
|
@ -60,12 +91,15 @@ fn bits_code(b:&[bool]) -> u16 {
|
|||
|
||||
impl StreamCoder {
|
||||
|
||||
fn encode(&self,byte:u8) -> [bool;12] {
|
||||
fn encode(&self,byte:u8) -> [bool;16] {
|
||||
return code_bits(self.encoder[byte as usize]);
|
||||
}
|
||||
|
||||
fn decode(&self,states:&[bool]) -> u8 {
|
||||
return self.decoder[bits_code(states) as usize];
|
||||
return match self.decoder[bits_code(states) as usize] {
|
||||
None => 0x20,
|
||||
Some(b) => b,
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -118,14 +152,15 @@ fn main() {
|
|||
},
|
||||
Ok(_) => (),
|
||||
};
|
||||
let mut payload:Vec<u8> = Vec::with_capacity(16*OVERSAMPLE_FACTOR);
|
||||
let mut payload:Vec<u8> = Vec::with_capacity(18*OVERSAMPLE_FACTOR);
|
||||
let bits = coder.encode(ibuffer[0]);
|
||||
for i in 0..12 {
|
||||
for i in 0..16 {
|
||||
payload.append(&mut match bits[i] {
|
||||
true => vec![0xFF;OVERSAMPLE_FACTOR],
|
||||
false => vec![0x00;OVERSAMPLE_FACTOR],
|
||||
});
|
||||
}
|
||||
payload.append(&mut vec![0x80;OVERSAMPLE_FACTOR*2]);
|
||||
match iooutput.write_all(&payload) {
|
||||
Err(why) => {
|
||||
eprintln!("write failed: {}",why);
|
||||
|
@ -136,11 +171,11 @@ fn main() {
|
|||
}
|
||||
} else if mode == "d" {
|
||||
let mut ibuffer:[u8;1] = [0x00];
|
||||
let mut filterstate:u16 = 0x0000;
|
||||
let mut filterstate:u16 = 0x0080;
|
||||
let mut logicstate:i8 = 0;
|
||||
let mut statecount:Option<(i8,usize)> = None;
|
||||
let mut count:usize = 1;
|
||||
let mut outbits:Vec<bool> = Vec::with_capacity(12);
|
||||
let mut sampleclock:usize = 1;
|
||||
let mut outbits:Vec<bool> = Vec::with_capacity(16);
|
||||
let mut outbyte:Option<u8> = None;
|
||||
loop {
|
||||
match ioinput.read_exact(&mut ibuffer) {
|
||||
Err(why) => match why.kind() {
|
||||
|
@ -153,52 +188,40 @@ fn main() {
|
|||
Ok(_) => (),
|
||||
};
|
||||
filterstate = filterstate*(FILTER_STRENGTH as u16)/0x00FF + ((0x00FF-FILTER_STRENGTH as u16)*ibuffer[0] as u16)/0x00FF;
|
||||
if filterstate > 170 {
|
||||
if logicstate == 1 {
|
||||
count += 1;
|
||||
} else {
|
||||
statecount = Some((logicstate,count));
|
||||
count = 1;
|
||||
logicstate = 1;
|
||||
}
|
||||
} else if filterstate < 85 {
|
||||
if logicstate == -1 {
|
||||
count += 1;
|
||||
} else {
|
||||
statecount = Some((logicstate,count));
|
||||
count = 1;
|
||||
logicstate = -1;
|
||||
}
|
||||
} else {
|
||||
if logicstate != 0 {
|
||||
count = 1;
|
||||
logicstate = 0;
|
||||
}
|
||||
statecount = Some((logicstate,count));
|
||||
let newlogicstate = match (filterstate > 170,filterstate < 85) {
|
||||
(true,false) => 1,
|
||||
(false,true) => -1,
|
||||
_ => 0,
|
||||
};
|
||||
if logicstate != newlogicstate {
|
||||
sampleclock = OVERSAMPLE_FACTOR/5;
|
||||
}
|
||||
if let Some((state,n)) = statecount {
|
||||
if state == 0 {
|
||||
if n >= RESET_THRESH {
|
||||
logicstate = newlogicstate;
|
||||
if (sampleclock + OVERSAMPLE_FACTOR/2) % OVERSAMPLE_FACTOR == 0 {
|
||||
match logicstate {
|
||||
1 => outbits.push(true ^ INVERT),
|
||||
-1 => outbits.push(false ^ INVERT),
|
||||
_ => if outbits.len() > 0 {
|
||||
outbyte = Some(0x20);
|
||||
outbits.clear();
|
||||
}
|
||||
} else {
|
||||
for _ in 0..(n+OVERSAMPLE_FACTOR/2)/OVERSAMPLE_FACTOR {
|
||||
outbits.push((state > 0) ^ INVERT);
|
||||
}
|
||||
}
|
||||
statecount = None;
|
||||
},
|
||||
};
|
||||
}
|
||||
if outbits.len() >= 12 {
|
||||
let outbyte:u8 = coder.decode(&outbits);
|
||||
if outbits.len() >= 16 {
|
||||
outbyte = Some(coder.decode(&outbits));
|
||||
outbits.clear();
|
||||
match iooutput.write_all(&[outbyte]) {
|
||||
}
|
||||
if let Some(byte) = outbyte {
|
||||
match iooutput.write_all(&[byte]) {
|
||||
Err(why) => {
|
||||
eprintln!("write failed: {}",why);
|
||||
exit(1);
|
||||
},
|
||||
Ok(_) => (),
|
||||
};
|
||||
outbyte = None;
|
||||
}
|
||||
sampleclock += 1;
|
||||
}
|
||||
} else {
|
||||
eprintln!("unknown mode operation `{}`",mode);
|
||||
|
|
Loading…
Reference in New Issue