create pinmap dictionaries
authorLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Fri, 2 Oct 2020 18:34:40 +0000 (19:34 +0100)
committerLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Fri, 2 Oct 2020 18:34:40 +0000 (19:34 +0100)
src/pinmux_generator.py
src/spec/base.py
src/spec/gen.py
src/spec/ifaceprint.py
src/spec/interfaces.py
src/spec/ls180.py

index 176660b34b1593e819fe999328db87361ee41332..f59730f3636d9ffb0406f04e31e16a68fd733c02 100644 (file)
@@ -81,18 +81,21 @@ if __name__ == '__main__':
         module = modules[pinspec]
 
         fname = os.path.join(output_dir or '', "%s.mdwn" % pinspec)
+        pyname = os.path.join(output_dir or '', "%s_pins.py" % pinspec)
         d = os.path.split(fname)[0]
         if not os.path.exists(d):
             os.makedirs(d)
         with open(fname, "w") as of:
-            ps = module.pinspec()
-            pinout, bankspec, pin_spec, fixedpins = ps.write(of)
-            if testing:
-                dummytest(ps, output_dir, output_type)
-            else:
-                specgen(of, output_dir, pinout,
-                        bankspec, ps.muxwidths, pin_spec, fixedpins, ps.fastbus)
-                module.pinparse(ps, pinspec)
+            with open(pyname, "w") as pyf:
+                ps = module.pinspec()
+                pm = module.pinparse(ps, pinspec)
+                pinout, bankspec, pin_spec, fixedpins = ps.write(pyf, of, pm)
+                if testing:
+                    dummytest(ps, output_dir, output_type)
+                else:
+                    specgen(of, output_dir, pinout,
+                            bankspec, ps.muxwidths, pin_spec, fixedpins,
+                            ps.fastbus)
     else:
         if output_type == 'bsv':
             from bsv.pinmux_generator import pinmuxgen as gentypes
index 701a4caf5bd3c11e8ce1aad05e273184410f0509..372099c49d5b952cd072afb2037b8a97f2be31d3 100644 (file)
@@ -1,7 +1,7 @@
 from spec.interfaces import Pinouts
 
 from spec.ifaceprint import display, display_fns, check_functions
-from spec.ifaceprint import display_fixed
+from spec.ifaceprint import display_fixed, python_dict_fns
 from collections import OrderedDict
 
 
@@ -37,7 +37,10 @@ class PinSpec(Pinouts):
 
         self.scenarios.append((name, needed, eint, pwm, descriptions))
 
-    def write(self, of):
+    def write(self, pyf, of, pinmap):
+
+        fns = python_dict_fns(pyf, pinmap, self, self.function_names)
+
         of.write("""# Pinouts (PinMux)
 auto-generated by [[pinouts.py]]
 
index a392264e7fd87e7038a8d9106d033093719900e0..492ba535074087c93ffb4a8d879082ba6b2c64d7 100644 (file)
@@ -44,7 +44,7 @@ def specgen(of, pth, pinouts, bankspec, muxwidths, pinbanks, fixedpins,
             with open(os.path.join(pth, '%s.txt' % k.lower()), 'w') as g:
                 if len(s0.pingroup) == 1:  # only one function, grouped higher
                     for ks in s.keys():  # grouped by interface
-                        #assert False, "TODO, single-function"
+                        assert False, "TODO, single-function"
                         fntype = 'inout'  # XXX TODO
                         k = s[ks].suffix
                         k_ = k.lower()
index abd809166daf68a87b9342137de816fe70eb456d..d5ad116b85a61c968904e371577b77287cb91e45 100644 (file)
@@ -61,6 +61,75 @@ def find_fn(fname, names):
         if fname.startswith(n):
             return n
 
+def map_name(pinmap, fn, fblower, pin, rename):
+    if not rename:
+        if pin[:-1].isdigit():
+            print "map name digit", pin, fn, fblower
+            if fn in ['PWM', 'EINT', 'VDD', 'VSS']:
+                return fn.lower() + pin.lower()
+        if fn == 'GPIO':
+            return 'gpio' + pin[1:].lower()
+        return pin.lower()
+    pin = pin.lower()
+    if fn == 'GPIO':
+        pk = '%s%s_%s' % (fblower, pin[0], pin[:-1])
+    elif pin[:-1].isdigit() and fn != 'EINT':
+        pk = '%s%s_out' % (fblower, pin[:-1])
+    else:
+        pk = '%s_%s' % (fblower, pin[:-1])
+    print "map name", pk, fblower, pinmap.has_key(pk)
+    if not pinmap.has_key(pk):
+        return pin.lower()
+    remapped = pinmap[pk]
+    uscore = remapped.find('_')
+    if uscore == -1:
+        return pin.lower()
+    fn, pin = remapped[:uscore], remapped[uscore+1:] + pin[-1]
+    return pin.lower()
+
+def python_pindict(of, pinmap, pins, function_names, dname, remap):
+
+    of.write("%s = {\n" % dname)
+
+    for k, pingroup in pins.byspec.items():
+        (a, n) = k
+        if n.isdigit():
+            a = "%s%s" % (a, n)
+        fblower = a.lower()
+        of.write("    '%s': [ " % fblower)
+        count = 0
+        for i, p in enumerate(pingroup):
+            of.write("'%s', " % map_name(pinmap, k[0], fblower, p, remap))
+            count += 1
+            if count == 4 and i != len(pingroup)-1:
+                of.write("\n                ")
+                count = 0
+        of.write("],\n")
+        print "    dict %s" % dname, a, n, pingroup
+    of.write("}\n\n")
+
+def python_dict_fns(of, pinmap, pins, function_names):
+    of.write("# auto-generated by Libre-SOC pinmux program: do not edit\n")
+    of.write("# python src/pinmux_generator.py -v -s {spec} -o {output}\n")
+
+    fn_names = function_names.keys()
+    fns = {}
+
+    fnidx = list(fns.keys())
+    fnidx.sort(key=fnsplit)
+
+    print "python fnames", function_names
+    print "python speckeys", pins.byspec.keys()
+    print "python dict fns", dir(pins.gpio)
+    print pins.gpio.pinfn('', '')
+    print pins.pwm.pinfn('', '')
+    print pins.sdmmc.pinfn('', '')
+    print "by spec", pins.byspec
+    print pinmap
+
+    python_pindict(of, {}, pins, function_names, 'pindict', False)
+    python_pindict(of, pinmap, pins, function_names, 'litexdict', True)
+
 
 def display_fns(of, bankspec, pins, function_names):
     fn_names = function_names.keys()
index 91d460252024d665f9aa4689e0d6215f41d77eed..c59a83d1530a26f44a822f4dd5b856dd6475c15d 100644 (file)
@@ -77,7 +77,14 @@ class PinGen(object):
             prefix = self.fname
         if start and limit:  # limit turns into an offset from start
             limit = start + limit
+        sk = (self.fname, suffix)
+        print "pingroup pre", sk, pingroup
         pingroup = pingroup[start:limit]  # see comment in spec.pinfunctions
+        print "pingroup post", sk, pingroup
+        if self.pinouts.byspec.has_key(sk):
+            self.pinouts.byspec[sk] += pingroup
+        else:
+            self.pinouts.byspec[sk] = deepcopy(pingroup)
         pins = Pins(prefix, pingroup, self.bankspec,
                     suffix, offs, bank, mux,
                     spec, origsuffix=suffix, gangedgrp=gangedgroup)
@@ -94,6 +101,7 @@ class Pinouts(object):
         self.fnspec = {}
         self.ganged = {}
         self.clocks = {}
+        self.byspec = {}
         for fname, pinfn in pinspec:
             if isinstance(pinfn, tuple):
                 name, pinfn = pinfn
index 6c8246a69e54abc36c130bb0858e8cff74550501..48c94a8f782fc3a6eede1b0e302ea10f3468febe 100644 (file)
@@ -135,6 +135,7 @@ def pinspec():
 # map pins to litex name conventions, primarily for use in coriolis2
 def pinparse(psp, pinspec):
     p = Parse(pinspec, verify=False)
+    pinmap = {}
 
     print p.muxed_cells
     print p.muxed_cells_bank
@@ -321,10 +322,14 @@ def pinparse(psp, pinspec):
                     clk = psp.clocks[domain]
                     if clk.lower() in orig_name: # TODO, might over-match
                         clocks[domain] = name
+            # record remap
+            pinmap[orig_name] = name
 
     # HACK!
     pe[13] = 'p_vddeck_0'
+    #pe[0] = 'p_vddeck_1'
     pe[23] = 'p_vsseck_0'
+    #pe[31] = 'p_vsseck_1'
     pw[10] = 'p_vddick_0'
     pw[17] = 'p_vssick_0'
 
@@ -368,3 +373,4 @@ def pinparse(psp, pinspec):
     with open("ls180/litex_pinpads.json", "w") as f:
         f.write(chip)
 
+    return pinmap