whoops need __contains__ due to pep8 replacement in for has_key
[pinmux.git] / src / spec / interfaces.py
1 #!/usr/bin/env python
2
3 from copy import deepcopy
4
5
6 class Pinouts(object):
7 def __init__(self):
8 self.pins = {}
9 self.fnspec = {}
10
11 def __contains__(self, k):
12 return k in self.pins
13
14 def has_key(self, k):
15 return k in self.pins
16
17 def add_spec(self, k, v):
18 self.fnspec[k] = v
19
20 def update(self, pinidx, v):
21 if pinidx not in self.pins:
22 self.pins[pinidx] = v
23 else:
24 self.pins[pinidx].update(v)
25
26 def keys(self):
27 return self.pins.keys()
28
29 def items(self):
30 return self.pins.items()
31
32 def get(self, k):
33 return self.pins[k]
34
35 def __len__(self):
36 return len(self.pins)
37
38 def __delitem__(self, k):
39 del self.pins[k]
40
41 def __getitem__(self, k):
42 return self.pins[k]
43
44
45 class Pins(object):
46
47 def __init__(self, fname, pingroup, bankspec, suffix, offs, bank, mux,
48 spec=None, limit=None, origsuffix=None):
49
50 # function type can be in, out or inout, represented by - + *
51 # strip function type out of each pin name
52 self.fntype = {}
53 for i in range(len(pingroup)):
54 pname = pingroup[i]
55 if not pname:
56 continue
57 fntype = pname[-1]
58 if fntype not in '+-*':
59 continue
60 pname = pname[:-1]
61 fntype = {'-': 'in', '+': 'out', '*': 'inout'}[fntype]
62 self.fntype[pname] = fntype
63 pingroup[i] = pname
64
65 self.fname = fname
66 self.pingroup = pingroup
67 self.bankspec = bankspec
68 self.suffix = suffix
69 self.origsuffix = origsuffix or suffix
70 self.bank = bank
71 self.mux = mux
72
73 # create consistent name suffixes
74 pingroup = namesuffix(fname, suffix, pingroup)
75 suffix = '' # hack
76
77 res = {}
78 names = {}
79 idx = 0
80 for name in pingroup[:limit]:
81 if suffix and name:
82 name_ = "%s_%s" % (name, suffix)
83 else:
84 name_ = name
85 if spec and name in spec:
86 continue
87 pin = {mux: (name_, bank)}
88 offs_bank, offs_ = offs
89 idx_ = offs_ + idx
90 idx += 1
91 idx_ += bankspec[bank]
92 res[idx_] = pin
93 names[name] = idx_
94 for name in pingroup:
95 if suffix and name:
96 name_ = "%s_%s" % (name, suffix)
97 else:
98 name_ = name
99 if not spec:
100 continue
101 if name not in spec:
102 continue
103 idx_, mux_, bank_ = spec[name]
104 idx_ = names[idx_]
105 pin = {mux_: (name_, bank_)}
106 if idx_ in res:
107 res[idx_].update(pin)
108 else:
109 res[idx_] = pin
110
111 self.pins = res
112
113
114 def i2s(bankspec, suffix, offs, bank, mux=1, spec=None, limit=None):
115 i2spins = ['MCK+', 'BCK+', 'LRCK+', 'DI-', 'DO+']
116 # for i in range(4):
117 # i2spins.append("DO%d+" % i)
118 return Pins('IIS', i2spins, bankspec, suffix, offs, bank, mux, spec, limit,
119 origsuffix=suffix)
120
121
122 def emmc(bankspec, suffix, offs, bank, mux=1, spec=None):
123 emmcpins = ['CMD+', 'CLK+']
124 for i in range(8):
125 emmcpins.append("D%d*" % i)
126 return Pins('MMC', emmcpins, bankspec, suffix, offs, bank, mux, spec,
127 origsuffix=suffix)
128
129
130 def sdmmc(bankspec, suffix, offs, bank, mux=1, spec=None,
131 start=None, limit=None):
132 sdmmcpins = ['CMD+', 'CLK+']
133 for i in range(4):
134 sdmmcpins.append("D%d*" % i)
135 sdmmcpins = sdmmcpins[start:limit]
136 return Pins('SD', sdmmcpins, bankspec, suffix, offs, bank, mux, spec,
137 origsuffix=suffix)
138
139
140 def spi(bankspec, suffix, offs, bank, mux=1, spec=None):
141 spipins = ['CLK*', 'NSS*', 'MOSI*', 'MISO*']
142 return Pins('SPI', spipins, bankspec, suffix, offs, bank, mux, spec,
143 origsuffix=suffix)
144
145
146 def quadspi(bankspec, suffix, offs, bank, mux=1, spec=None, limit=None):
147 spipins = ['CK*', 'NSS*', 'IO0*', 'IO1*', 'IO2*', 'IO3*']
148 return Pins(
149 'QSPI',
150 spipins,
151 bankspec,
152 suffix,
153 offs,
154 bank,
155 mux,
156 spec,
157 limit,
158 origsuffix=suffix)
159
160
161 def i2c(bankspec, suffix, offs, bank, mux=1, spec=None):
162 spipins = ['SDA*', 'SCL*']
163 return Pins('TWI', spipins, bankspec, suffix, offs, bank, mux, spec,
164 origsuffix=suffix)
165
166
167 def jtag(bankspec, suffix, offs, bank, mux=1, spec=None):
168 jtagpins = ['MS+', 'DI-', 'DO+', 'CK+']
169 return Pins('JTAG', jtagpins, bankspec, suffix, offs, bank, mux, spec,
170 origsuffix=suffix)
171
172
173 def uart(bankspec, suffix, offs, bank, mux=1, spec=None):
174 uartpins = ['TX+', 'RX-']
175 return Pins('UART', uartpins, bankspec, suffix, offs, bank, mux, spec,
176 origsuffix=suffix)
177
178
179 def namesuffix(name, suffix, namelist):
180 names = []
181 for n in namelist:
182 if n:
183 names.append("%s%s_%s" % (name, suffix, n))
184 else:
185 names.append("%s_%s" % (name, suffix))
186 return names
187
188
189 def ulpi(bankspec, suffix, offs, bank, mux=1, spec=None):
190 ulpipins = ['CK+', 'DIR+', 'STP+', 'NXT+']
191 for i in range(8):
192 ulpipins.append('D%d*' % i)
193 return Pins('ULPI', ulpipins, bankspec, suffix, offs, bank, mux, spec,
194 origsuffix=suffix)
195
196
197 def uartfull(bankspec, suffix, offs, bank, mux=1, spec=None):
198 uartpins = ['TX+', 'RX-', 'CTS-', 'RTS+']
199 return Pins('UARTQ', uartpins, bankspec, suffix, offs, bank, mux, spec,
200 origsuffix=suffix)
201
202
203 def rgbttl(bankspec, suffix, offs, bank, mux=1, spec=None):
204 ttlpins = ['CK+', 'DE+', 'HS+', 'VS+']
205 for i in range(24):
206 ttlpins.append("D%d+" % i)
207 return Pins('LCD', ttlpins, bankspec, suffix, offs, bank, mux, spec,
208 origsuffix=suffix)
209
210
211 def rgmii(bankspec, suffix, offs, bank, mux=1, spec=None):
212 buspins = []
213 for i in range(4):
214 buspins.append("ERXD%d-" % i)
215 for i in range(4):
216 buspins.append("ETXD%d+" % i)
217 buspins += ['ERXCK-', 'ERXERR-', 'ERXDV-',
218 'EMDC+', 'EMDIO*',
219 'ETXEN+', 'ETXCK+', 'ECRS-',
220 'ECOL+', 'ETXERR+']
221 return Pins('RG', buspins, bankspec, suffix, offs, bank, mux, spec,
222 origsuffix=suffix)
223
224
225 def flexbus1(bankspec, suffix, offs, bank, mux=1, spec=None, limit=None):
226 buspins = []
227 for i in range(8):
228 buspins.append("AD%d*" % i)
229 for i in range(2):
230 buspins.append("CS%d+" % i)
231 buspins += ['ALE', 'OE', 'RW', 'TA', 'CLK+',
232 'A0', 'A1', 'TS', 'TBST',
233 'TSIZ0', 'TSIZ1']
234 for i in range(4):
235 buspins.append("BWE%d" % i)
236 for i in range(2, 6):
237 buspins.append("CS%d+" % i)
238 return Pins('FB', buspins, bankspec, suffix, offs, bank, mux, spec, limit,
239 origsuffix=suffix)
240
241
242 def flexbus2(bankspec, suffix, offs, bank, mux=1, spec=None, limit=None):
243 buspins = []
244 for i in range(8, 32):
245 buspins.append("AD%d*" % i)
246 return Pins('FB', buspins, bankspec, suffix, offs, bank, mux, spec, limit,
247 origsuffix=suffix)
248
249
250 def sdram1(bankspec, suffix, offs, bank, mux=1, spec=None):
251 buspins = []
252 for i in range(16):
253 buspins.append("SDRDQM%d*" % i)
254 for i in range(12):
255 buspins.append("SDRAD%d+" % i)
256 for i in range(8):
257 buspins.append("SDRDQ%d+" % i)
258 for i in range(3):
259 buspins.append("SDRCS%d#+" % i)
260 for i in range(2):
261 buspins.append("SDRDQ%d+" % i)
262 for i in range(2):
263 buspins.append("SDRBA%d+" % i)
264 buspins += ['SDRCKE+', 'SDRRAS#+', 'SDRCAS#+', 'SDRWE#+',
265 'SDRRST+']
266 return Pins('SDR', buspins, bankspec, suffix, offs, bank, mux, spec,
267 origsuffix=suffix)
268
269
270 def sdram2(bankspec, suffix, offs, bank, mux=1, spec=None, limit=None):
271 buspins = []
272 for i in range(3, 6):
273 buspins.append("SDRCS%d#+" % i)
274 for i in range(8, 32):
275 buspins.append("SDRDQ%d*" % i)
276 return Pins('SDR', buspins, bankspec, suffix, offs, bank, mux, spec, limit,
277 origsuffix=suffix)
278
279
280 def mcu8080(bankspec, suffix, offs, bank, mux=1, spec=None):
281 buspins = []
282 for i in range(8):
283 buspins.append("MCUD%d*" % i)
284 for i in range(8):
285 buspins.append("MCUAD%d+" % (i + 8))
286 for i in range(6):
287 buspins.append("MCUCS%d+" % i)
288 for i in range(2):
289 buspins.append("MCUNRB%d+" % i)
290 buspins += ['MCUCD+', 'MCURD+', 'MCUWR+', 'MCUCLE+', 'MCUALE+',
291 'MCURST+']
292 return Pins('MCU', buspins, bankspec, suffix, offs, bank, mux, spec,
293 origsuffix=suffix)
294
295
296 def _pinbank(bankspec, prefix, suffix, offs, bank, gpiooffs, gpionum=1, mux=1,
297 spec=None):
298 gpiopins = []
299 for i in range(gpiooffs, gpiooffs + gpionum):
300 gpiopins.append("%s%d*" % (bank, i))
301 return Pins(prefix, gpiopins, bankspec, suffix, offs, bank, mux, spec,
302 origsuffix=suffix)
303
304
305 def eint(bankspec, suffix, offs, bank, gpiooffs, gpionum=1, mux=1, spec=None):
306 gpiopins = []
307 for i in range(gpiooffs, gpiooffs + gpionum):
308 gpiopins.append("%d*" % (i))
309 return Pins('EINT', gpiopins, bankspec, suffix, offs, bank, mux, spec,
310 origsuffix=suffix)
311
312
313 def pwm(bankspec, suffix, offs, bank, pwmoffs, pwmnum=1, mux=1, spec=None):
314 pwmpins = []
315 for i in range(pwmoffs, pwmoffs + pwmnum):
316 pwmpins.append("%d+" % (i))
317 return Pins('PWM', pwmpins, bankspec, suffix, offs, bank, mux, spec,
318 origsuffix=suffix)
319
320
321 def gpio(bankspec, suffix, offs, bank, gpiooffs, gpionum=1, mux=1, spec=None):
322 return _pinbank(bankspec, "GPIO%s" % bank, suffix, offs, bank, gpiooffs,
323 gpionum, mux=0, spec=None)
324
325
326 def pinmerge(pins, fn):
327 # hack, store the function specs in the pins dict
328 fname = fn.fname
329 suffix = fn.origsuffix
330 bank = fn.bank
331
332 if not hasattr(pins, 'fnspec'):
333 pins.fnspec = pins
334 if fname == 'GPIO':
335 fname = fname + bank
336 assert 'EINT' not in pins
337 if fname not in pins.fnspec:
338 pins.add_spec(fname, {})
339 print "fname bank suffix", fname, bank, suffix
340 if suffix or fname == 'EINT' or fname == 'PWM':
341 specname = fname + suffix
342 else:
343 specname = fname + bank
344 if specname in pins.fnspec[fname]:
345 # ok so some declarations may bring in different
346 # names at different stages (EINT, PWM, flexbus1/2)
347 # so we have to merge the names in. main thing is
348 # the pingroup
349 tomerge = pins.fnspec[fname][specname]
350 for p in fn.pingroup:
351 if p not in tomerge.pingroup:
352 tomerge.pingroup.append(p)
353 tomerge.pins.update(fn.pins)
354 tomerge.fntype.update(fn.fntype)
355 else:
356 pins.fnspec[fname][specname] = deepcopy(fn)
357
358 # merge actual pins
359 for (pinidx, v) in fn.pins.items():
360 pins.update(pinidx, v)