from datetime import datetime
from textwrap import indent, dedent
from ast import *
from util import *
@linewise
def expr_kind_match(d, mode):
yield 'match self {'
for v, path in variants_paths(d):
yield ' %s => {' % struct_pattern(v, path, bind_mode='')
for f in v.fields:
if 'lvalue_mut' in f.attrs:
yield ' %s.fold_lvalue_mut(lr);' % f.name
elif 'lvalue_imm' in f.attrs:
yield ' %s.fold_lvalue(lr);' % f.name
elif 'lr_propagate' in f.attrs:
yield ' %s.fold_%s(lr);' % (f.name, mode)
elif 'lvalue_kind' in f.attrs:
yield ' match %s {' % f.attrs['lvalue_kind']
yield ' Mutability::Mutable =>'
yield ' %s.fold_lvalue_mut(lr),' % f.name
yield ' Mutability::Immutable =>'
yield ' %s.fold_lvalue(lr),' % f.name
yield ' }'
else:
yield ' %s.fold_rvalue(lr);' % f.name
yield ' }'
yield '}'
@linewise
def expr_kind_impl(d):
yield '#[allow(unused)]'
yield 'impl LRExpr for %s {' % d.name
yield ' fn fold_rvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield indent(expr_kind_match(d, 'rvalue'), ' ')
yield ' }'
yield ' fn fold_lvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield indent(expr_kind_match(d, 'lvalue'), ' ')
yield ' }'
yield ' fn fold_lvalue_mut<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield indent(expr_kind_match(d, 'lvalue_mut'), ' ')
yield ' }'
yield '}'
@linewise
def expr_impl(d):
yield '#[allow(unused)]'
yield 'impl LRExpr for %s {' % d.name
yield ' fn fold_rvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' self.node.fold_rvalue(lr);'
yield ' lr.fold_rvalue(self)'
yield ' }'
yield ' fn fold_lvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' self.node.fold_lvalue(lr);'
yield ' lr.fold_lvalue(self)'
yield ' }'
yield ' fn fold_lvalue_mut<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' self.node.fold_lvalue_mut(lr);'
yield ' lr.fold_lvalue_mut(self)'
yield ' }'
yield '}'
@linewise
def null_impl(d):
yield '#[allow(unused)]'
yield 'impl LRExpr for %s {' % d.name
yield ' fn fold_rvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' }'
yield ' fn fold_lvalue<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' }'
yield ' fn fold_lvalue_mut<LR: LRRewrites>(&mut self, lr: &mut LR) {'
yield ' }'
yield '}'
@linewise
def generate(decls):
yield '// AUTOMATICALLY GENERATED - DO NOT EDIT'
yield '// Produced %s by process_ast.py' % (datetime.now(),)
yield ''
for d in decls:
if d.name == 'Expr':
pass
elif d.name == 'ExprKind':
yield expr_kind_impl(d)
else:
yield null_impl(d)