Mercurial > hg > CbC > old > CbC_scripts
view meta_connector/meta_connector.py @ 23:e22a82d584c6
minor fix
author | Kaito Tokumori <e105711@ie.u-ryukyu.ac.jp> |
---|---|
date | Sat, 31 Oct 2015 17:43:39 +0900 |
parents | c32994789739 |
children | 569b28c699d9 |
line wrap: on
line source
#!/usr/bin/env python3 # -*- coding: utf-8 -*- import sys import argparse import re # parse arguments and return arguments list. def get_args(): parser = argparse.ArgumentParser( formatter_class=argparse.RawDescriptionHelpFormatter, description="""\ Parse meta connect syntax. Default output is stdout. sample) __code code0(struct Data data1, ...){ goto code1(data1, data2, ...); \t| \tV __code code0(struct Context* context, struct Data data1, ...){ goto meta_code1(context, data1, data2, ..., Code1); """) parser.add_argument('input_file',\ nargs=None,\ type=str,\ help='input file path.') parser.add_argument('-o', dest='output',\ nargs=1,\ type=str,\ metavar='<file>',\ help='write output to <file>') return parser.parse_args() # parse input file and create meta connection list def parse_meta_syntax(lines,file): comment_out = False caller_name = '' isMetaOrStub = False defaultMetaIsNotExist = True for i,l in enumerate(lines): regexed_l = re.search(r"[a-zA-Z0-9_]+ *\(",l) # get caller code segment name if re.search(r"^ *__code",l) is not None: isMetaOrStub = False caller_name = regexed_l.group(0).rstrip('(') if caller_name == 'meta': defaultMetaIsNotExist = False if re.search(r"^ *meta_*|stub$",caller_name) is not None: # meta code segment or stub isMetaOrStub = True file.write(l) elif re.search(r"struct Context\* context",l) is None: file.write("/*-- generated by script */\n") file.write('// '+l) file.write('__code {0:s}(struct Context* context{1:s}) {{\n'.format(caller_name,get_args_from_line(l))) else: file.write(l) elif not isMetaOrStub and regexed_l is not None and re.search(r"^ *goto",l): callee_name = regexed_l.group(0).rstrip('(') if callee_name == 'start_code' or re.match('meta_|meta$',callee_name): file.write(l) elif re.search(r"\(context", l) is None: file.write("/*-- connected by script */\n") file.write('// '+l) meta_name = 'meta_'+caller_name if cs_search(lines, 'meta_'+callee_name) else 'meta' file.write("goto {0:s}(context{1:s}, {2:s});\n".format(meta_name, get_args_from_line(l),\ callee_name.capitalize())) else: file.write(l) else: file.write(l) if defaultMetaIsNotExist: create_default_metacs(file) def create_default_metacs(file): file.write(''' __code meta(struct Context* context, enum Code next) { goto (context->code[next])(context); } ''') def get_args_from_line(line): args = line.split('(')[1].rsplit(')')[0].strip() args = ', ' + args if args else '' return args def create_stub(file,name): file.write('''__code {0:s}_stub(struct Context* context) {{ goto {0:s}(context'''.format(name)) file.write(');\n}\n') # search meta code segment. # Find it : __code meta_'name' def cs_search(lines, name): for l in lines: if re.search(r"^ *__code {0:s}\(".format(name),l) is not None: return True return False def main(): args = get_args() output = sys.stdout try: f = open(args.input_file,'r') except IOError: print("cannot open file %s" % input_file) if args.output is not None: try: output = open(args.output[0],'w') except IOError: print("cannot open file %s" % args.output) lines = f.readlines() connect_list = parse_meta_syntax(lines, output) main()