From: Tim Vieira Date: Sun, 4 Aug 2013 16:38:48 +0000 (-0400) Subject: Codegen includes ANF in generated source. X-Git-Url: https://hydra-www.ietfng.org/gitweb/?a=commitdiff_plain;h=886c2a897a39979877ee285246e9bea152687178;p=dyna2 Codegen includes ANF in generated source. --- diff --git a/src/Dyna/Backend/Python/Backend.hs b/src/Dyna/Backend/Python/Backend.hs index 43a8afe..ed0c149 100644 --- a/src/Dyna/Backend/Python/Backend.hs +++ b/src/Dyna/Backend/Python/Backend.hs @@ -28,6 +28,7 @@ import qualified Data.Maybe as MA import qualified Data.Set as S -- import qualified Debug.Trace as XT import Dyna.Analysis.ANF +import Dyna.Analysis.ANFPretty -- import Dyna.Analysis.Aggregation import Dyna.Analysis.DOpAMine import Dyna.Analysis.Mode @@ -257,7 +258,7 @@ pdope_ _ (OPWrap v vs f) = return $ pretty v <+> equals <+> "build" <> (parens $ pfas f vs <> comma - <> (sepBy "," $ map pretty vs)) + <> (sepBy "," $ map pretty vs)) pdope_ _ (OPIter v vs _ Det (Just (PDBS c))) = return $ pretty (v^.mv_var) <+> equals @@ -351,11 +352,16 @@ printInitializer :: Handle -> S.Set DFunctAr -> Rule -> Cost -> Actions PyDopeBS -> IO () printInitializer fh bc rule cost dope = do displayIO fh $ renderPretty 1.0 100 - $ "def" <+> char '_' <> tupled ["emit"] <> colon + $ "def" <+> char '_' <> tupled ["emit"] <> colon `above` (indent 4 $ printPlanHeader rule cost Nothing) `above` pdope bc dope <> line - <> "initializers.append((" <> (pretty $ r_index rule) <> ", _" <> "))" + <> "initializers.append" + <> parens (tupled [ pretty $ r_index rule + , "_" + , squotes $ prettySpanLoc $ r_span rule + , "'''" <> (renderANF rule) <> "'''" + ]) <> line <> line <> line @@ -398,7 +404,12 @@ printQuery fh bc (f,a) rule vs cost dope = do `above` pdope bc dope <> line <> "queries.append" - <> parens (tupled [pfa f a, pretty $ r_index rule, "_"]) + <> parens (tupled [pfa f a + , pretty $ r_index rule + , "_" + , squotes $ prettySpanLoc $ r_span rule + , "'''" <> (renderANF rule) <> "'''" + ]) <> line <> line <> line @@ -424,6 +435,7 @@ driver am ups is bc qp pr fh = do hPutStrLn fh "" hPutStrLn fh $ "queries = []" hPutStrLn fh $ "agg_decl = {}" + hPutStrLn fh $ "rule = []" hPutStrLn fh $ "updaters = []" hPutStrLn fh $ "initializers = []" @@ -449,9 +461,9 @@ driver am ups is bc qp pr fh = do printInitializer fh bc r c a hPutStrLn fh $ "# ==Queries==" - forM_ qp $ \(fa,r,(vs,(c,a))) -> printQuery fh bc fa r vs c a + ------------------------------------------------------------------------}}} -- Export {{{ diff --git a/src/Dyna/Backend/Python/interpreter.py b/src/Dyna/Backend/Python/interpreter.py index d6a3eb8..73ef031 100644 --- a/src/Dyna/Backend/Python/interpreter.py +++ b/src/Dyna/Backend/Python/interpreter.py @@ -5,7 +5,7 @@ from collections import defaultdict from term import Term, Cons, Nil, MapsTo, Error from chart import Chart -from utils import red, parse_attrs, read_anf, _repr, hide_ugly_filename, \ +from utils import red, ANF, span_to_src, _repr, hide_ugly_filename, \ true, false, magenta, indent, path from prioritydict import prioritydict @@ -306,13 +306,6 @@ class Interpreter(object): ('peel', peel)]: setattr(env, k, v) - anf = {} - assert path(filename + '.anf').exists() # XXX: codegen should put this is plan.py - with file(filename + '.anf') as f: - contents = f.read().strip() + '\n' - for x in read_anf(contents): - anf[x.ruleix] = x - # update parser state self.set_parser_state(env.parser_state) @@ -320,13 +313,13 @@ class Interpreter(object): self.new_fn(k, v) new_rules = set() - for _, index, h in env.queries: + for _, index, h, span, anf in env.queries: new_rules.add(index) - self.add_rule(index, query=h, anf=anf[index]) + self.add_rule(index, span, ANF.read(span, index, anf), query=h) - for index, h in env.initializers: + for index, h, span, anf in env.initializers: new_rules.add(index) - self.add_rule(index, init=h, anf=anf[index]) + self.add_rule(index, span, ANF.read(span, index, anf), init=h) for fn, r, h in env.updaters: self.new_updater(fn, r, h) @@ -419,8 +412,7 @@ class Interpreter(object): #___________________________________________________________________________ # Adding/removing rules - def add_rule(self, index, init=None, query=None, anf=None): - assert anf is not None + def add_rule(self, index, span, anf, init=None, query=None): assert index not in self.rules for (x, label, ys) in anf.unifs: @@ -432,8 +424,8 @@ class Interpreter(object): assert False, 'did not find head' self.rules[index] = rule = Rule(index) - rule.span = hide_ugly_filename(parse_attrs(init or query)['Span']) - rule.src = parse_attrs(init or query)['rule'] + rule.span = hide_ugly_filename(span) + rule.src = span_to_src(span).strip() rule.anf = anf rule.head_fn = head_fn diff --git a/src/Dyna/Backend/Python/main.py b/src/Dyna/Backend/Python/main.py index fc8aba3..5c32e87 100644 --- a/src/Dyna/Backend/Python/main.py +++ b/src/Dyna/Backend/Python/main.py @@ -43,7 +43,7 @@ def main(): if len(args.source) > 1: # concatenate files - with file(interp.tmp / 'tmp.dyna', 'wb') as g: + with file(interp.compiler.tmp / 'tmp.dyna', 'wb') as g: for f in args.source: if not f.exists(): print 'File `%s` does not exist.' % f diff --git a/src/Dyna/Backend/Python/utils.py b/src/Dyna/Backend/Python/utils.py index 6fab210..1f992c4 100644 --- a/src/Dyna/Backend/Python/utils.py +++ b/src/Dyna/Backend/Python/utils.py @@ -224,28 +224,32 @@ def pretty(t, initialindent=0): class ANF(namedtuple('ANF', 'span ruleix agg head evals unifs result')): - pass + + @staticmethod + def read(span, index, x): + def _g(x): + for var, val in x: + if isinstance(val, list): + yield (var, val[0], val[1:]) + else: + yield (var, val, []) + def g(x): + return list(_g(x)) + + [(agg, head, evals, unifs, [_, result])] = parse_sexpr(x) + + return ANF(span, + index, + agg, + head, + g(evals[1:]), + g(unifs[1:]), + result) def read_anf(e): - def _g(x): - for var, val in x: - if isinstance(val, list): - yield (var, val[0], val[1:]) - else: - yield (var, val, []) - def g(x): - return list(_g(x)) - - for span, ruleix, anf in re.findall('^;; (.*)\n;; index (\d+)\n(\([\w\W]+?)\n(?:\n|$)', e, re.MULTILINE): - for (agg, head, evals, unifs, [_,result]) in parse_sexpr(anf): - yield ANF(span, - int(ruleix), - agg, - head, - g(evals[1:]), - g(unifs[1:]), - result) + for span, ruleix, x in re.findall('^;; (.*)\n;; index (\d+)\n(\([\w\W]+?)\n(?:\n|$)', e, re.MULTILINE): + yield ANF.read(span, int(ruleix), x) def parse_attrs(fn):