Source code for benchbuild.utils.schedule_tree

""" Parsing utilities for Polly's ScheduleTree representation. """
import logging
import textwrap as t

import attr
import pyparsing as p

LOG = logging.getLogger(__name__)


[docs]@attr.s class Node: tok = attr.ib()
[docs] def indent(self, level=0, idt=' '): val = self.tok[2] if not isinstance(self.tok[2], str): val = self.tok[2].indent(1) return t.indent('"{:s}": "{:s}"'.format(self.tok[0], val), level * idt)
[docs]@attr.s class CoincidenceNode(Node):
[docs] def indent(self, level=0, idt=' '): ret = [str(child) for child in self.tok[3]] ret = ",".join(ret) return t.indent('"{:s}": [{:s}]'.format(self.tok[0], ret), level * idt)
[docs]@attr.s class RootNode(Node):
[docs] def indent(self, level=0, idt=' '): ret = [] ret = [child.indent(level + 2) for child in self.tok[1]] ret = ",\n".join(ret) return t.indent('{{\n{:s}\n}}'.format(ret), level * idt)
def __str__(self): return self.indent(0)
[docs]@attr.s class ChildNode(Node):
[docs] def indent(self, level=0, idt=' '): ret = self.tok[0].indent(level) return ret
[docs]@attr.s class SequenceNode(Node):
[docs] def indent(self, level=0, idt=' '): ret = '"{:s}": [\n'.format(self.tok[0]) for child in self.tok[3]: ret += child.indent(0) + ',\n' ret += '\n]' return t.indent(ret, level * idt)
NUM = p.Word(p.nums, max=1) NUM_LIST = p.Group(p.delimitedList(NUM)) STR = p.QuotedString('"') KW_CHILD = p.Keyword("child") KW_COINCIDENT = p.Keyword("coincident") KW_DOMAIN = p.Keyword("domain") KW_FILTER = p.Keyword("filter") KW_MARK = p.Keyword("mark") KW_OPTIONS = p.Keyword("options") KW_PERMUTABLE = p.Keyword("permutable") KW_SCHEDULE = p.Keyword("schedule") KW_EXTENSION = p.Keyword("extension") KW_SEQUENCE = p.Keyword("sequence") CHILD_NODE = p.Forward() ROOT = p.Forward() DOMAIN = KW_DOMAIN + ":" + STR SCHEDULE = KW_SCHEDULE + ":" + STR FILTER = KW_FILTER + ":" + STR MARK = KW_MARK + ":" + STR PERMUTABLE = KW_PERMUTABLE + ":" + NUM COINCIDENT = KW_COINCIDENT + ":" + "[" + NUM_LIST + "]" OPTIONS = KW_OPTIONS + ":" + STR EXTENSION = KW_EXTENSION + ":" + STR SEQ_ELEM_LIST = p.delimitedList(ROOT) SEQUENCE = KW_SEQUENCE + ":" + "[" + p.Group(p.delimitedList(ROOT)) + "]" CHILD = KW_CHILD + ":" + ROOT CHILD_NODE << (CHILD | COINCIDENT | DOMAIN | EXTENSION | FILTER | MARK | OPTIONS | PERMUTABLE | SCHEDULE | SEQUENCE) ROOT << ("{" + p.Group(p.delimitedList(CHILD_NODE)) + "}") CHILD.addParseAction(Node) CHILD_NODE.addParseAction(ChildNode) COINCIDENT.addParseAction(CoincidenceNode) DOMAIN.addParseAction(Node) FILTER.addParseAction(Node) MARK.addParseAction(Node) OPTIONS.addParseAction(Node) PERMUTABLE.addParseAction(Node) ROOT.addParseAction(RootNode) EXTENSION.addParseAction(Node) SCHEDULE.addParseAction(Node) SEQUENCE.addParseAction(SequenceNode)
[docs]def parse_schedule_tree(tree_str): if tree_str is None: return "No Input" try: ret = ROOT.parseString(tree_str) return str(ret[0]) except p.ParseException as ex: LOG.warning("Failed to parse:") LOG.warning(str(ex)) LOG.warning(tree_str) return None