Skip to content

Instantly share code, notes, and snippets.

@winstonewert
Created July 5, 2019 20:20
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save winstonewert/08e628102fa169ac9454563585d633fc to your computer and use it in GitHub Desktop.
Save winstonewert/08e628102fa169ac9454563585d633fc to your computer and use it in GitHub Desktop.
import subprocess
import glob
import re
def type_lines(ll_files):
for ll_file in ll_files:
for line in open(ll_file):
if line.startswith('%'):
yield line
PATTERN = re.compile(r'->|([^<>, ]+)|<|>|,| ')
def parse_type(type_name):
stack = [[]]
for match in PATTERN.finditer(type_name):
part = match.group(0)
if part == '<':
stack.append([stack[-1].pop()])
elif part == '>':
top = stack.pop()
if not stack:
print(match)
print(len(type_name))
stack[-1].append(top)
else:
stack[-1].append(part)
assert len(stack) == 1
return stack[0]
def fl(t):
if type(t) is str:
return len(t)
else:
return sum(fl(x) for x in t)
def process_type(cache, t):
if type(t) is str:
if t in '() ->,!':
return t
processed = t
else:
if len(t) == 1:
return process_type(cache, t[0])
else:
processed = t[0] + '<' + ''.join(process_type(cache, x) for x in t[1:]) + '>'
try:
return cache[processed]
except KeyError:
ident = str(len(cache) + 1)
cache[processed] = ident
print(ident, processed, '(', fl(t), ')')
return ident
def main():
subprocess.run(['cargo', 'rustc', '--', '--emit', 'llvm-ir'], check=True)
ll_files= glob.glob('target/debug/deps/*.ll')
longest_type = max(type_lines(ll_files), key=len)
actual_type = longest_type[longest_type.find('"')+1:longest_type.rfind('" = type')]
parsed = parse_type(actual_type)
cache = {}
print(process_type(cache, parsed))
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment