2 # generates markdown tables from CSV files, after doing lovely sorting
3 # by different columns, blah blah...
4 from copy
import deepcopy
7 def write_mdwn_row(f
, row
):
12 def underlines(header
):
15 row
.append("-" * len(col
))
19 def is_svp64_page(page
):
20 return page
in ['sv/setvl', 'sv/svstep', 'sv/remap']
22 def sort_by_page(p1
, p2
):
25 if not (is_svp64_page(p1
) ^
is_svp64_page(p2
)):
35 levels
= ['SFFS', 'SV/E', 'SV/D', 'SV/S', 'opt']
37 def sort_by_level(p1
, p2
):
38 p1
= levels
.index(p1
['level'])
39 p2
= levels
.index(p2
['level'])
44 priorities
= ['high', 'med', 'low', 'TBD']
46 def sort_by_priority(p1
, p2
):
47 p1
= priorities
.index(p1
['priority'])
48 p2
= priorities
.index(p2
['priority'])
53 def sort_by_cost(p1
, p2
):
56 if not p1
.isdigit(): p1
= 0
57 if not p2
.isdigit(): p2
= 0
64 def sort_by_level_priority_cost(p1
, p2
):
65 v
= sort_by_level(p1
, p2
)
67 v
= sort_by_priority(p1
, p2
)
69 v
= sort_by_cost(p1
, p2
)
73 def sort_by_cost_priority_page(p1
, p2
):
74 v
= sort_by_cost(p1
, p2
)
76 v
= sort_by_priority(p1
, p2
)
78 v
= sort_by_page(p1
, p2
)
82 def by_levelpriority_then_cost(areas
):
83 # first blat all columns together (drop area-dict)
85 for row
in areas
.values():
88 res
= sorted(res
, key
=functools
.cmp_to_key(sort_by_level_priority_cost
))
89 # now split out into a dict again this time by cost-priority
92 key
= row
['level']+row
['priority']
95 levels
[key
].append(row
)
99 def by_cost_then_priority_then_page(areas
):
100 # first blat all columns together (drop area-dict)
102 for row
in areas
.values():
105 res
= sorted(res
, key
=functools
.cmp_to_key(sort_by_cost_priority_page
))
106 # now split out into a dict again this time by cost-priority
110 if cost
not in costs
:
112 costs
[cost
].append(row
)
116 # For prettier printing, replace short column heading
117 # names with full, consistent names.
118 # Expected input is a list of column strings
119 def column_header_replacement(header
):
120 replacement_col
= {'cost': 'XO Cost'}
121 new_header
= deepcopy(header
)
122 for index
, shortname
in enumerate(replacement_col
.keys()):
123 # update with replacement if any otherwise leave alone
124 new_header
[index
] = replacement_col
.get(shortname
, shortname
)
128 def print_table(title
, header
, areas
, sortby
):
129 fname
= title
.lower().replace(" ", "_")
130 with
open("ls012/%s.mdwn" % fname
, "w") as f
:
131 # write out the page header
132 f
.write("\\newpage{}\n")
134 f
.write("# %s\n" % title
)
136 # sort everything if required
137 if sortby
is not None:
138 areas
= sortby(areas
)
140 # start writing out areas
141 for title
, rows
in areas
.items():
142 # start new page (if not first newpage)
143 if linecount
is not None:
144 # allow 58 rows per page
145 linecount
+= len(rows
)
149 f
.write("\\newpage{}\n")
151 if linecount
is None: # skipped first newpage
154 f
.write("## %s\n" % title
)
157 # work out maximum length of items, and adjust header
158 hdr
= deepcopy(header
)
163 for hd
, value
in row
.items():
164 cols
[hd
] = max(cols
[hd
], len(value
))
165 # adjust header (add spaces)
166 for i
, hd
in enumerate(hdr
):
167 n_spaces
= cols
[hd
] - len(hd
)
168 hdr
[i
] = hdr
[i
] + " " * n_spaces
170 write_mdwn_row(f
, hdr
)
171 write_mdwn_row(f
, underlines(hdr
))
173 # adjust row (add same spaces as header width)
175 for key
in row
.keys():
176 col_len
, value
= cols
[key
], row
[key
]
178 prefix
= 'https://libre-soc.org/openpower/'
179 v
= value
.replace("_", "\_") # latex, duh
180 url
= '[%s](%s%s)' % (value
, prefix
, v
)
182 elif key
== 'rfc' and value
.startswith('ls'):
183 prefix
= 'https://libre-soc.org/openpower/sv/rfc/'
184 url
= '[%s](%s%s)' % (value
, prefix
, value
)
187 value
= value
.replace("_", "\_") # latex, duh
188 n_spaces
= col_len
- len(value
)
189 r
.append(value
+ " " * n_spaces
)
194 # approx 8 lines per header
197 if __name__
== '__main__':
198 with
open("ls012/optable.csv") as f
:
199 l
= map(str.strip
, f
.readlines())
203 if line
.startswith("#"):
204 area
= line
[1:].strip()
207 # split line by commas, whitespace-strip it
208 line
= list(map(str.strip
, line
.split(',')))
213 # create a dictionary by tuple of header+line
214 linedict
= dict(zip(header
, line
))
219 areas
[area
].append(linedict
)
221 # excellent - now have a dictionary of list of dictionaries:
222 # area - list-of-instructions - dictionary-by-heading
223 print_table("Areas", header
, areas
, None)
225 # now sort by cost and then by page
226 print_table("XO cost", header
, areas
, by_cost_then_priority_then_page
)
228 # now sort by level combined with priority, then cost
229 print_table("Level", header
, areas
, by_levelpriority_then_cost
)