summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPavel V. Shatov (Meister) <meisterpaul1@yandex.ru>2020-09-23 16:10:33 +0300
committerPavel V. Shatov (Meister) <meisterpaul1@yandex.ru>2020-09-23 16:10:33 +0300
commitb1d5782d7e7642b45a85bb70436c1ec92afdc380 (patch)
tree2817fe6be15b37e79c28e846b2e58af86f3fbe77
parentf32d184cec05c42bc20a45010f7172905e3b561c (diff)
Forgot to commit the script I wrote to help repair forward annotation,
basically it just scans schematics pages and the PCB file and then recreates the mapping between schematic component and PCB component based on KiCAD's "unique ID" and "sheet ID".
-rw-r--r--helper/repair_annotation.py135
1 files changed, 135 insertions, 0 deletions
diff --git a/helper/repair_annotation.py b/helper/repair_annotation.py
new file mode 100644
index 0000000..822880e
--- /dev/null
+++ b/helper/repair_annotation.py
@@ -0,0 +1,135 @@
+#
+# quick and dirty script to fix eeschema -> pcbnew (forward) annotation
+#
+import os
+import re
+
+PROJ_DIR = "./KiCAD"
+SCH_IN = "Cryptech Alpha.sch"
+PCB_IN = "Cryptech Alpha BACKUP.kicad_pcb"
+PCB_OUT = "Cryptech Alpha.kicad_pcb"
+
+def parse_toc():
+ print("Parsing toc...")
+ toc = {}
+ re_u = re.compile("^U ([0-9A-F]{8})$")
+ re_p = re.compile('^F1 \"(rev02_\d+\.sch)\" \d+$')
+ with open("%s/%s" % (PROJ_DIR, SCH_IN), 'r') as f:
+ i, fls = 0, f.readlines()
+ while i < len(fls):
+ i, fl = i+1, fls[i].strip()
+ if fl.startswith('$Sheet'):
+ #
+ # $Sheet
+ # S 8700 3800 750 400
+ # U 57D84C55
+ # F0 "Real Time Clock" 60
+ # F1 "rev02_08.sch" 60
+ #
+ fl_s = fls[i+0].strip()
+ fl_u = fls[i+1].rstrip()
+ fl_f0 = fls[i+2].rstrip()
+ fl_f1 = fls[i+3].rstrip()
+ m_u = re.match(re_u, fl_u)
+ m_p = re.match(re_p, fl_f1)
+ if m_u is None:
+ raise RuntimeError(fl_u)
+ if m_p is None:
+ raise RuntimeError(fl_f1)
+ u = m_u.group(1)
+ p = m_p.group(1)
+ print(" page '%s' => '%s'" % (p, u))
+ toc[p] = u
+ i += 4
+ continue
+ return toc
+
+
+
+def find_pages():
+ print("Finding pages...")
+ pgs = []
+ fs = os.listdir(PROJ_DIR)
+ re_sch = re.compile("^rev02_\d+.sch$")
+ for f in fs:
+ f_is_sch = re.match(re_sch, f)
+ if f_is_sch is None: continue
+ print(" page '%s'" % f)
+ pgs.append(f)
+ return pgs
+
+def parse_syms(pgs):
+ #
+ # $Comp
+ # L <footprint> RefDes
+ # U <num> <num> ID
+ #
+ syms = {}
+ re_refdes = re.compile("^L \S+ ([#A-Z_\d]+)$")
+ re_id = re.compile("^U \d 1 ([0-9A-F]{8})$")
+ for pg in pgs:
+ with open("%s/%s" % (PROJ_DIR, pg), 'r') as f:
+ fls = f.readlines()
+ for i in range(len(fls)):
+ fl = fls[i].strip()
+ if fl == '$Comp':
+ fl_refdes = fls[i+1].strip()
+ fl_id = fls[i+2].strip()
+ m_refdes = re.match(re_refdes, fl_refdes)
+ m_id = re.match(re_id, fl_id)
+ if m_refdes is None:
+ raise RuntimeError(fl_refdes)
+ if m_id is None:
+ raise RuntimeError(fl_id)
+ refdes = m_refdes.group(1)
+ id = m_id.group(1)
+ if refdes.startswith('#'): continue
+ syms[refdes] = (pg, id)
+ print(" comp '%s' @ page '%s' => %s" % (refdes, pg, id))
+ return syms
+
+def fix_pcb(syms, pids):
+ print("Fixing pcb...")
+ new_syms = syms.copy()
+ re_refdes = re.compile("^ \(fp_text reference (\S+)\s")
+ with open("%s/%s" % (PROJ_DIR, PCB_OUT), 'w') as fw:
+ with open("%s/%s" % (PROJ_DIR, PCB_IN), 'r') as fr:
+ fls = fr.readlines()
+ i = 0
+ while i < len(fls):
+ fl = fls[i].rstrip()
+ fw.write("%s\n" % fl)
+ i += 1
+ if fl.startswith(' (module'):
+ fl_at = fls[i+0].rstrip()
+ fl_path = fls[i+1].rstrip()
+ fl_attr = fls[i+2].rstrip()
+ fl_refdes = fls[i+3].rstrip()
+ #
+ if fl_refdes.startswith(' (fp_text reference ""'): continue
+ #
+ m_refdes = re.match(re_refdes, fl_refdes)
+ if m_refdes is None:
+ raise RuntimeError(fl_refdes)
+ refdes = m_refdes.group(1)
+ #
+ pg, id = new_syms[refdes]
+ pid = pids[pg]
+ del new_syms[refdes]
+ #
+ fw.write("%s\n" % fl_at)
+ #fw.write("%s\n" % (fl_path[:-1], '/'+id, fl_path[-1]))
+ fw.write(" (path /%s/%s)\n" % (pid, id))
+ i += 2
+ continue
+ return new_syms
+
+
+if __name__ == "__main__":
+ pids = parse_toc()
+ pgs = find_pages()
+ syms = parse_syms(pgs)
+ new_syms = fix_pcb(syms, pids)
+ print("Leftover components:")
+ print(new_syms)
+ \ No newline at end of file