chiark / gitweb /
decodes packets
authorian <ian>
Sun, 9 Jan 2005 18:30:15 +0000 (18:30 +0000)
committerian <ian>
Sun, 9 Jan 2005 18:30:15 +0000 (18:30 +0000)
parport/nmra-decode.pl

index c68b1d8d244a6acf572352fc192f393dc8ed4acc..b94b281465ecbbf8d2c16ee341c661aaeffcc388 100755 (executable)
@@ -16,12 +16,58 @@ sub usec_from_to ($$) {
 
 #---------- bit stream (packet) decoder ----------
 
-sub found_bit ($) {
-    my ($bit) = @_;
-}
+our ($idle_counter, $bitnum, @bytes);
 
 sub reset_packet_decoder () {
-    printf "-- restarting decoder --\n";
+    $idle_counter= 0;
+}
+
+sub packet_decoder_error ($) {
+    printf "EP (%s)\n", $_[0];
+    reset_packet_decoder();
+}
+
+sub found_bit ($) {
+    my ($bit) = @_;
+    if (defined $idle_counter) {
+       if ($bit) {
+           $idle_counter++;
+           printf "I%-4d\n", $idle_counter;
+           return;
+       }
+       if ($idle_counter < 10) {
+           packet_decoder_error("I only $idle_counter");
+           return;
+       }
+       undef $idle_counter;
+       $bitnum= -1;
+       @bytes= ();
+    }
+    if ($bitnum<0) {
+       if ($bit) {
+           my ($checksum,$byte);
+           $checksum= 0;
+           foreach $byte (@bytes) {
+               $checksum ^= hex $byte;
+           }
+           if ($checksum) {
+               packet_decoder_error("csum $checksum, @bytes");
+               return;
+           }
+           print "P @bytes\n";
+           $idle_counter= 0;
+           return;
+       }
+       $bitnum= 7;
+       push @bytes, 0;
+       print "F @bytes...\n";
+       return;
+    }
+    $b= hex $bytes[$#bytes];
+    $b |= ($bit << $bitnum);
+    $bytes[$#bytes]= sprintf "%02x", $b;
+    print "B @bytes($bitnum)\n";
+    $bitnum--;
 }
 
 #---------- interval -> bit decoder ----------
@@ -52,6 +98,7 @@ sub interval_mapchar ($$@) {
 }
 
 sub reset_bit_decoder () {
+    printf "-- restarting bit decoder --\n";
     undef @valuefor;
     undef $in_bit;
     $bit_phase_determined= 0;
@@ -118,19 +165,19 @@ sub found_interval ($$$) {
     }
 
     if ($bit_half) {
+       undef $in_bit;
        if ($class eq 'U') {
-           printf " E UU\n";
+           printf " E UU";
            reset_packet_decoder();
-       } else {
-           $bit_value= !!($class eq 'S');
-           printf "  %d  ", $bit_value;
-           found_bit($bit_value);
+           return;
        }
-       undef $in_bit;
+       $bit_value= !!($class eq 'S');
+       printf "  %d  ", $bit_value;
+       found_bit($bit_value);
     } else {
        $in_bit= $class;
+       printf "\n";
     }
-    printf "\n";
 }
 
 #---------- interval scanner ----------