Simplified code for calling Python decode method.
[libsigrokdecode.git] / decoders / spi.py
1 class Sample():
2         def __init__(self, data):
3                 self.data = data
4         def probe(self, probe):
5                 s = ord(self.data[probe / 8]) & (1 << (probe % 8))
6                 return True if s else False
7
8 def sampleiter(data, unitsize):
9         for i in range(0, len(data), unitsize):
10                 yield(Sample(data[i:i+unitsize]))
11
12 class Decoder():
13         # Probe names with a set of defaults
14         probes = {'sdata':0, 'sck':1}
15
16         def __init__(self, unitsize, **kwargs):
17                 # Metadata comes in here, we don't care for now
18                 #print kwargs
19                 self.unitsize = unitsize
20
21                 self.probes = Decoder.probes
22                 self.oldsck = True
23                 self.rxcount = 0
24                 self.rxdata = 0
25                 self.bytesreceived = 0
26
27         def summary(self):
28                 return "SPI: %d bytes received" % self.bytesreceived
29
30         def decode(self, data):
31                 # We should accept a list of samples and iterate...
32                 for sample in sampleiter(data["data"], self.unitsize):
33
34                         sck = sample.probe(self.probes["sck"])
35                         # Sample SDATA on rising SCK
36                         if sck == self.oldsck:
37                                 continue
38                         self.oldsck = sck
39                         if not sck: 
40                                 continue        
41
42                         # If this is first bit, save timestamp
43                         if self.rxcount == 0:
44                                 self.time = data["time"]
45                         # Receive bit into our shift register
46                         sdata = sample.probe(self.probes["sdata"])
47                         if sdata:
48                                 self.rxdata |= 1 << (7 - self.rxcount)
49                         self.rxcount += 1
50                         # Continue to receive if not a byte yet
51                         if self.rxcount != 8:
52                                 continue
53                         # Received a byte, pass up to sigrok
54                         outdata = {"time":self.time,
55                                 "duration":data["time"] + data["duration"] - self.time,
56                                 "data":self.rxdata,
57                                 "display":("%02X" % self.rxdata),
58                                 "type":"spi",
59                         }
60                         print outdata
61                         sigrok.put(outdata)
62                         # Reset decoder state
63                         self.rxdata = 0
64                         self.rxcount = 0
65                         # Keep stats for summary
66                         self.bytesreceived += 1
67                         
68
69 register = {
70         'id': 'spi',
71         'name': 'SPI Decoder',
72         'longname': '...',
73         'desc': 'Decodes SPI frames',
74         'longdesc': '...',
75         'author': 'Gareth McMullin',
76         'email': 'gareth@blacksphere.co.nz',
77         'license': 'gplv2+',
78         'in': ['logic'],
79         'out': ['spi'],
80         'probes': [
81                 # All probes.
82         ],
83         'options': {
84                 # No options so far.
85         },
86         # 'start': start,
87         # 'report': report,
88 }
89
90 if __name__ == "__main__":
91         data = open("spi_dump.bin").read()
92
93         # dummy class to keep Decoder happy for test
94         class Sigrok():
95                 def put(self, data):
96                         print "\t", data
97         sigrok = Sigrok()
98
99         dec = Decoder(driver='ols', unitsize=1, starttime=0)
100         dec.decode({"time":0, "duration":len(data), "data":data, "type":"logic"})
101
102         print dec.summary()
103 else:
104         import sigrok
105
106 #Tested with:
107 #  sigrok-cli -d 0:samplerate=1000000:rle=on --time=1s -p 1,2 -a spidec
108
109