Última actividad 1 month ago

Very bad converter from ValueChangeDump (VCD) to Tikz Timing on Latex.

racerxdl's Avatar Lucas Teske revisó este gist 5 years ago. Ir a la revisión

1 file changed, 13 deletions

vcd2latex.py

@@ -21,13 +21,6 @@ def nibble_to_hex(s):
21 21 return hex(int(s, 2))[2:].upper()
22 22
23 23 def binary_string_to_hex(s, w):
24 - """
25 - Convert a binary string to hexadecimal.
26 - If any non 0/1 values are present such as 'x', return that single character
27 - as a representation.
28 - :param s: the string to be converted
29 - :type s: str
30 - """
31 24 if len(s) == 1:
32 25 if s != '0' and s != '1':
33 26 return s
@@ -37,11 +30,6 @@ def binary_string_to_hex(s, w):
37 30 groups = [s[i:i+n] for i in range(0, len(s), n)]
38 31 hexgroups = [nibble_to_hex(x) for x in groups]
39 32 return "".join(hexgroups)
40 - return s
41 - # for c in s:
42 - # if not c in '01':
43 - # return c
44 - # return hex(int(s, 2))[2:]
45 33
46 34
47 35 class ParserCallbacks(vcdvcd.StreamParserCallbacks):
@@ -66,7 +54,6 @@ class ParserCallbacks(vcdvcd.StreamParserCallbacks):
66 54 size = int(vcd.data[identifier_code].size)
67 55 width = max(((size // 4)), int(math.floor(math.log10(i))) + 1)
68 56 self._references_to_widths[ref] = width
69 - # print(ref, i, size)
70 57 dataW[i-1] = size
71 58
72 59 def time(

racerxdl's Avatar Lucas Teske revisó este gist 5 years ago. Ir a la revisión

1 file changed, 161 insertions

vcd2latex.py(archivo creado)

@@ -0,0 +1,161 @@
1 + #!/usr/bin/env python3
2 +
3 + import vcdvcd, math
4 + from vcdvcd import VCDVCD
5 +
6 + vcdfile = "digital_port_tb.vcd"
7 +
8 + vcd = VCDVCD(vcdfile, only_sigs=True)
9 +
10 + all_signals = vcd.signals
11 + # print(all_signals)
12 + dataW = [0 for i in range(len(all_signals))]
13 + data = [[] for i in range(len(all_signals))]
14 +
15 + ###########
16 +
17 + def nibble_to_hex(s):
18 + for c in s:
19 + if not c in '01':
20 + return c
21 + return hex(int(s, 2))[2:].upper()
22 +
23 + def binary_string_to_hex(s, w):
24 + """
25 + Convert a binary string to hexadecimal.
26 + If any non 0/1 values are present such as 'x', return that single character
27 + as a representation.
28 + :param s: the string to be converted
29 + :type s: str
30 + """
31 + if len(s) == 1:
32 + if s != '0' and s != '1':
33 + return s
34 +
35 + s = s.zfill(w)
36 + n = 4
37 + groups = [s[i:i+n] for i in range(0, len(s), n)]
38 + hexgroups = [nibble_to_hex(x) for x in groups]
39 + return "".join(hexgroups)
40 + return s
41 + # for c in s:
42 + # if not c in '01':
43 + # return c
44 + # return hex(int(s, 2))[2:]
45 +
46 +
47 + class ParserCallbacks(vcdvcd.StreamParserCallbacks):
48 + def __init__(self, deltas=True):
49 + self._deltas = deltas
50 + self._references_to_widths = {}
51 +
52 + def enddefinitions(
53 + self,
54 + vcd,
55 + signals,
56 + cur_sig_vals
57 + ):
58 + if signals:
59 + self._print_dumps_refs = signals
60 + else:
61 + self._print_dumps_refs = sorted(vcd.data[i].references[0] for i in cur_sig_vals.keys())
62 + for i, ref in enumerate(self._print_dumps_refs, 1):
63 + if i == 0:
64 + i = 1
65 + identifier_code = vcd.references_to_ids[ref]
66 + size = int(vcd.data[identifier_code].size)
67 + width = max(((size // 4)), int(math.floor(math.log10(i))) + 1)
68 + self._references_to_widths[ref] = width
69 + # print(ref, i, size)
70 + dataW[i-1] = size
71 +
72 + def time(
73 + self,
74 + vcd,
75 + time,
76 + cur_sig_vals
77 + ):
78 + if (not self._deltas or vcd.signal_changed):
79 + ss = []
80 + ss.append('{}'.format(time))
81 + for i, ref in enumerate(self._print_dumps_refs):
82 + identifier_code = vcd.references_to_ids[ref]
83 + value = cur_sig_vals[identifier_code]
84 + data[i].append(binary_string_to_hex(value, dataW[i]))
85 +
86 +
87 + ###########
88 +
89 +
90 + callbacks = ParserCallbacks()
91 + VCDVCD(
92 + vcdfile,
93 + signals=all_signals,
94 + store_tvs=False,
95 + callbacks=callbacks,
96 + )
97 +
98 + ltx = '''
99 + \\documentclass{standalone}
100 + \\usepackage{tikz-timing}
101 +
102 + \\begin{document}
103 + \\begin{tikztimingtable}[timing/xunit=35,timing/yunit=10]
104 + '''
105 +
106 + def latexEscape(val):
107 + return val.\
108 + replace("_", "\\_").\
109 + replace("{", "\\{").\
110 + replace("}", "\\}").\
111 + replace("&", "\\&").\
112 + replace("%", "\\%").\
113 + replace("$", "\\$").\
114 + replace("#", "\\#").\
115 + replace("$", "\\$")
116 +
117 +
118 + for sig in range(len(data)):
119 + sigName = latexEscape(all_signals[sig])
120 + sigSeries = data[sig]
121 + sigWidth = dataW[sig]
122 + # print(f"SigName: {sigName} - SigWidth: {sigWidth}")
123 + ltx += format(f" {sigName} &")
124 + for value in sigSeries:
125 + prefix = ""
126 + token = format(f" D{{{value}}} ")
127 + if value == "x":
128 + token = "X"
129 + elif value == "z":
130 + token = "Z"
131 + elif sigWidth == 1:
132 + token = "H" if value == "1" else "L"
133 + if "x" in token:
134 + prefix = " [red] "
135 + elif "z" in token:
136 + prefix = " [blue] "
137 +
138 + ltx += format(f" {prefix}{token} ;")
139 + ltx += " \\\\\n"
140 +
141 + # ltx += "\\vertlines[help lines,opacity=0.3]{}\n"
142 + ltx += '''\\extracode
143 + \\vertlines[help lines,opacity=0.3]{}
144 + \\end{tikztimingtable}
145 + \\end{document}
146 +
147 + '''
148 +
149 + # print(ltx)
150 + with open("tmp.tex", "w") as f:
151 + f.write(ltx)
152 +
153 +
154 + '''
155 + \\begin{tikztimingtable}[timing/wscale=0.8]
156 + M-cycle & X 8D{M1} 8D{M2/M1} X \\\\
157 + Instruction & ; [opacity=0.4] 9D{Previous} ; [opacity=1.0] 8D{LD r, r'} ; [opacity=0.4] X \\\\
158 + Mem R/W & X 8D{R: opcode}; [opacity=0.4] 8D{R: next op} X \\\\
159 + Mem addr & X 8D{PC} ; [opacity=0.4] 8D{PC+1} X \\\\
160 + \\end{tikztimingtable}
161 + '''
Siguiente Anterior