backyard/ciel/charsqueeze.py
2022-06-13 07:18:08 +02:00

111 lines
2.3 KiB
Python

lines = r"""
#define OPS \
X(TOPCOM, 1)
X(TOPSET, 2)
X(TOPLOR, 3)
X(TOPLXOR, 4)
X(TOPLAND, 5)
X(TUNLNOT, 6)
X(TOPEQ, 7)
X(TOPNE, 7)
X(TOPLT, 7)
X(TOPGT, 7)
X(TOPLE, 7)
X(TOPGE, 7)
X(TOPOR, 8)
X(TOPXOR, 9)
X(TOPAND, 10)
X(TOPSHL, 11)
X(TOPSHR, 11)
X(TOPADD, 12)
X(TOPSUB, 12)
X(TOPMUL, 13)
X(TOPDIV, 13)
X(TOPMOD, 13)
X(TUNNOT, 14)
X(TUNINV, 14)
X(TUNPOS, 14)
X(TUNNEG, 14)
X(TOPPOW, 15)
X(TOPTYPE, 16)
X(TOPLT_S, 0)
X(TOPGT_S, 0)
X(TOPLE_S, 0)
X(TOPGE_S, 0)
X(TOPSHL_S, 0)
X(TOPSHR_S, 0)
X(TOPDIV_S, 0)
X(TOPMOD_S, 0)
X(TOPPOW_S, 0)
"""
lines = r"""
const char
*fall = "failed to allocate memory",
*farg = "malformed argc/argv",
*fbignum = "number too large",
*femp = "empty token",
*feof = "unexpected end of file",
*ffread = "read failed",
*fid = "identifiers cannot be longer than " STR(MAXLEN) " bytes",
*finc8 = "incomplete UTF-8",
*finv8 = "invalid UTF-8",
*fmiscl = "missing \")\"",
*fmisop = "missing \"(\"",
*fmop = "missing operand",
*fnan = "not a number",
*fnot = "no token",
*fnotid = "left-hand operand must be an identifier",
*fnumpre = "invalid numeric prefix",
*fopmod = "operands have different modulos",
*fopsign = "operands have different signedness",
*fout8 = "out of range for UTF-8",
*fstart = "invalid starting token",
*ftype = "invalid type",
*fuchar = "unknown character",
*fundef = "undefined",
*funex = "unexpected",
*funkop = "unknown operator",
"""
lines = lines.strip().split('\n')
header, lines = lines[0], lines[1:]
lines = sorted(lines, key=lambda k: -len(k))
ispp = header[0] == '#'
def tryout(s, *used):
if len(s) > 80 - (6 if ispp else 4):
return None, None
best_str = s
best_used = used
for j, other in enumerate(lines):
if j in used:
continue
ts, tused = tryout(s + ' ' + other, j, *used)
if ts is None:
continue
if len(ts) > len(best_str):
best_str = ts
best_used = tused
return best_str, best_used
used = []
print(header)
for i, line in enumerate(lines):
if i in used:
continue
s, tused = tryout(line, i, *used)
used += tused
islast = not any(j not in used for j in range(i, len(lines)))
if islast:
if s[-1] == ',':
print(' ' + s[:-1] + ';')
else:
print(' ' + s)
else:
if ispp:
print(' ' + s + ' \\')
else:
print(' ' + s)