blob: 83165bfdedc8e727b5e74e565189ae339442f7b4 [file] [log] [blame] [edit]
#!/usr/bin/env python3
import csv
import os
import pprint
import re
import sys
from collections import defaultdict
import common
import flatten
RE_MODEL_START = re.compile(r'^model\s+(?P<model>[^ ]+)\s+bsim(?P<bsim>[0-9vV]+)\s+{(\n|$)')
RE_MODEL_END = re.compile(r'^[\s\n]*ends(?P<end>.*)(\n|$)')
RE_ROW = re.compile(r'^\s*(?P<row>[0-9]+):\s*type=(?P<type>.*?)(\n|$)')
RE_PARAM = re.compile(r'^[+] (?P<param>[^ ]+)\s+=\s+(?P<value>.+?)(\n|$)')
RE_GROUP = re.compile(r'[*\s]*?(?P<group>[^*\n]+?)[*\s]*(\n|$)')
GROUPS = defaultdict(set)
FIELDS = set()
def write_csv(outname, models):
w = csv.writer(open(outname,'w'))
row = ['model', 'bin', 'num_bins']
row.extend(sorted(FIELDS))
w.writerow(row)
for m in models:
for i, r in enumerate(m['rows']):
row = []
row.append(m['model'])
row.append(i)
row.append(len(m['rows']))
for f in sorted(FIELDS):
row.append(r.get(f, 'N\A'))
w.writerow(row)
def pm3_to_rows(infile):
models = [None]
rows = []
row_params = {}
group = None
for comment, bit in flatten.read_bits(infile, 'spice'):
if comment:
m = RE_GROUP.match(bit)
if m:
group = m.group('group').title()
print('g', group)
else:
print('#', repr(bit))
else:
for l in bit.splitlines(keepends=True):
if models[-1] is None:
m = RE_MODEL_START.match(l)
if not m:
print("Skipping", repr(l))
continue
models.pop(-1)
models.append({
'model': m.group('model'),
'bsim': m.group('bsim'),
'rows': [],
})
continue
m = RE_MODEL_END.match(l)
if m:
if row_params:
models[-1]['rows'].append(row_params)
print("Ends", m.group('end'))
models.append(None)
break
m = RE_ROW.match(l)
if m:
if row_params:
models[-1]['rows'].append(row_params)
row = m.group('row')
t = m.group('type')
row_params = {
'row': 0,
'type': t,
}
continue
m = RE_PARAM.match(l)
if m:
params = {}
name = [m.group('param')]
value = []
bits = m.group('value').split()
print(name, bits)
while bits:
value.append(bits.pop(0))
if bits and bits[0] in ('+', '*'):
value.append(bits.pop(0))
value.append(bits.pop(0))
if value[-1][-1] == '(':
value.append(bits.pop(0))
continue
params["".join(name)] = " ".join(value)
if bits:
name = [bits.pop(0)]
value = []
assert bits.pop(0) == '=', repr(l)
print(params)
for k in params:
FIELDS.add(k)
GROUPS[group].add(k)
assert k not in row_params
try:
params[k] = float(params[k])
except ValueError:
pass
row_params[k] = params[k]
continue
if l.strip():
print('?', repr(l))
assert models[-1] == None
models.pop(-1)
return models
models = []
for pn in common.files(['.pm3']):
if 'rf' in pn:
continue
print()
print(pn)
print('='*75)
newmodels = pm3_to_rows(pn)
base, ext = os.path.splitext(pn)
print('-'*75)
outfile = base+'.csv'
print(outfile)
write_csv(outfile, newmodels)
print('='*75)
models.extend(newmodels)
write_csv('out.csv', models)
sys.exit(1)
# Header 1
#row = ['',]
#for h1 in sorted(groups):
# row.append(h1)
# row.extend(['']*(len(groups[h1])-1))
#csv_rows.append(row)
# Header 2
row = ['type',]
#h2toh1 = {}
for h1 in sorted(groups):
for h2 in sorted(groups[h1]):
row.append(h2)
h2toh1[h2] = h1
csv_rows.append(row)
for row in rows:
csv_rows.append([row['type'],])
for h2 in csv_rows[1][1:]:
h1 = h2toh1[h2]
csv_rows[-1].append(row[h1].get(h2,'N/A'))
w.writerows(csv_rows)