pass over config in json format
[pinmux.git] / src / spec / gen.py
1 import os
2 import json
3 import os.path
4 from spec.interfaces import Pinouts
5
6
7 def specgen(of, pth, pinouts, bankspec, muxwidths, pinbanks, fixedpins,
8 configs):
9 """ generates a specification of pinouts (tsv files)
10 for reading in by pinmux.
11
12 files generated:
13 * interfaces.txt - contains name and number of interfaces
14 * {interfacename}.txt - contains name of pin, type, and bus
15
16 type may be in, out or inout.
17 if type is "inout" then a THIRD optional parameter of type
18 "bus" indicates whether the bus is ganged together. in
19 future this may be "bus1", "bus2" and so on if an interface
20 contains more than one ganged group.
21
22 basically if the function needs to control whether a group
23 of pins shall be switched from input to output (as opposed
24 to the *pinmux* via user control deciding that), bus is
25 the way to indicate it.
26 """
27 pth = pth or ''
28 #print bankspec.keys()
29 #print fixedpins.keys()
30 #print pinouts.ganged.items()
31 if not os.path.exists(pth):
32 os.makedirs(pth)
33 with open(os.path.join(pth, 'configs.txt'), 'w') as f:
34 f.write("%s\n" % json.dumps(configs))
35
36 with open(os.path.join(pth, 'interfaces.txt'), 'w') as f:
37 for k in pinouts.fnspec.keys():
38 s = pinouts.fnspec[k]
39 line = [k.lower(), str(len(s))]
40 line = '\t'.join(line)
41 f.write("%s\n" % line)
42 s0 = s[list(s.keys())[0]] # hack, take first
43 gangedgroup = pinouts.ganged[k]
44 with open(os.path.join(pth, '%s.txt' % k.lower()), 'w') as g:
45 if len(s0.pingroup) == 1: # only one function, grouped higher
46 for ks in s.keys(): # grouped by interface
47 assert False, "TODO, single-function"
48 fntype = 'inout' # XXX TODO
49 k = s[ks].suffix
50 k_ = k.lower()
51 g.write("%s\t%s\n" % (k_, fntype))
52 else:
53 for pinname in s0.pingroup:
54 fntype = s0.fntype.get(pinname, 'inout')
55 pn = pinname.lower()
56 g.write("%s\t%s" % (pn, fntype))
57 if fntype == 'inout' and pinname in gangedgroup:
58 g.write("\tbus")
59 g.write("\n")
60
61 # work out range of bankspecs
62 bankpins = []
63 for k, v in bankspec.items():
64 bankpins.append((v, k))
65 bankpins.sort()
66 bankpins.reverse()
67 muxentries = {}
68 cellbank = {}
69
70 pks = sorted(pinouts.keys())
71
72 # truly dreadful way to work out the max mux size...
73 for k in pks:
74 for (sz, bname) in bankpins:
75 print "keys", k, sz, bname
76 if k >= sz:
77 print "found", bname
78 muxentries[k] = muxwidths[bname]
79 cellbank[k] = bname
80 break
81
82 print muxentries
83 # write out the mux...
84 with open(os.path.join(pth, 'pinmap.txt'), 'w') as g:
85 for k in pks:
86 muxsz = muxentries[k]
87 bank = cellbank[k]
88 res = [str(k), bank, str(muxsz)]
89 # append pin mux
90 for midx in range(muxsz):
91 if midx in pinouts[k]:
92 fname = pinouts[k][midx][0]
93 else:
94 fname = ''
95 res.append(fname.lower())
96 g.write('\t'.join(res) + '\n')
97
98 # ... and the dedicated pins
99 with open(os.path.join(pth, 'fixedpins.txt'), 'w') as g:
100 for p in fixedpins:
101 p = map(str, p)
102 p = map(str.lower, p)
103 g.write('\t'.join(p) + '\n')
104
105 # lists bankspec, shows where the pin-numbers *start*
106 of.write("# Pin Bank starting points and lengths\n\n")
107 with open(os.path.join(pth, 'pinspec.txt'), 'w') as g:
108 keys = sorted(bankspec.keys())
109 for bank in keys:
110 pinstart = bankspec[bank]
111 wid = muxwidths[bank]
112 of.write("* %s %d %d %d\n" % (bank, pinstart, pinbanks[bank], wid))
113 g.write("%s\t%d\t%d\t%d\n" % (bank, pinstart, pinbanks[bank], wid))