Export invocation numbers to JSON file

Co-authored-by: Ivan Velickovic <i.velickovic@unsw.edu.au>
Signed-off-by: Alwin Joshy <joshyalwin@gmail.com>

tmp
This commit is contained in:
Alwin Joshy
2024-10-03 16:03:56 +10:00
committed by Indan Zupancic
parent 85aa104eb4
commit bd1c392409
3 changed files with 140 additions and 0 deletions

View File

@@ -40,3 +40,46 @@ def condition_to_cpp(conditions):
raise Exception("Unrecognized element `{}` in condition".format(expr.tagName))
return helper(children[0])
def expr_to_bool(expr, values) -> bool:
if expr.tagName == "and":
for child in expr.childNodes:
if not expr_to_bool(child, values):
return False
return True
elif expr.tagName == "or":
for chlid in expr.childNodes:
if expr_to_bool(child, values):
return True
return False
elif expr.tagName == "not":
assert len(expr.childNodes) == 1
return not expr_to_bool(expr.childNodes[0], values)
elif expr.tagName == "config":
cfg_var = expr.getAttribute("var")
if not cfg_var:
raise Exception("Missing or empty config variable")
return values[cfg_var.removeprefix("CONFIG_")]
raise Exception("Unrecognized element `{}` in condition".format(expr.tagName))
# values to match on conditions and resolve them
def condition_to_bool(conditions, values) -> bool:
n = len(conditions)
# Expect zero or one <condition> tag in the conditions list.
assert n <= 1
if n == 0:
return True
remove_ws_comments(conditions[0])
children = conditions[0].childNodes
if not children or len(children) == 0:
return True
# Expect that a condition tag has exactly one child node.
assert len(children) == 1
remove_ws_comments(children[0])
return expr_to_bool(children[0], values)

View File

@@ -0,0 +1,65 @@
#!/usr/bin/env python3
#
# Copyright 2024, UNSW Sydney
#
# SPDX-License-Identifier: BSD-2-Clause or GPL-2.0-only
#
import argparse
import json
import xml.dom.minidom
from condition import condition_to_bool
def parse_args():
parser = argparse.ArgumentParser(description='Generate JSON file containing list of seL4 \
invocations.')
parser.add_argument('--gen_config', type=argparse.FileType('r'),
help="Location of gen_config JSON file", required=True)
parser.add_argument('--invocations', type=argparse.FileType('r'),
help='Location of XML file with invocation definitions', required=True)
parser.add_argument('--arch_invocations', type=argparse.FileType('r'),
help='Location of XML file with arch invocation defintions', required=True)
parser.add_argument('--sel4_arch_invocations', type=argparse.FileType('r'),
help='Location of XML file with seL4 arch invocation definitions', required=True)
parser.add_argument('--dest', type=argparse.FileType('w+'),
help='Location of JSON file to store invocations', required=True)
return parser.parse_args()
def xml_to_json_invocations(xml, gen_config, counter, invocations_dict, ):
for method in xml.getElementsByTagName("method"):
label = str(method.getAttribute("id"))
exists = condition_to_bool(method.getElementsByTagName("condition"), gen_config)
if exists:
invocations_dict[label] = counter
counter += 1
return counter
if __name__ == "__main__":
args = parse_args()
try:
invocations = xml.dom.minidom.parse(args.invocations)
arch_invocations = xml.dom.minidom.parse(args.arch_invocations)
sel4_arch_invocations = xml.dom.minidom.parse(args.sel4_arch_invocations)
except:
print('Error: invalid XML file provided', file=sys.stderr)
sys.exit(1)
try:
gen_config = json.load(args.gen_config)
except:
print('Error: invalid JSON file provided', file=sys.stderr)
sys.exit(1)
invocations_dict = {}
counter = 1
counter = xml_to_json_invocations(invocations, gen_config, counter, invocations_dict)
counter = xml_to_json_invocations(sel4_arch_invocations, gen_config, counter, invocations_dict)
counter = xml_to_json_invocations(arch_invocations, gen_config, counter, invocations_dict)
json.dump(invocations_dict, args.dest)