#include "AST.h" #include "llist.h" static PointNode *slice( const TreeListNode &args, int index, SourcePosn where ) { llist< TreeNode * > *exprs = 0; for (int sweep = args.arity(); sweep--; ) { const TreeNode &arg = *args.child( sweep ); assert( arg.arity() >= 2 ); assert( arg.arity() <= 3 ); push( exprs, args.child( sweep )->child( index ) ); } return new PointNode( exprs, where ); } TreeNode *DomainNode::rewrite( const FieldContext *context ) { TreeNode::rewrite( context ); TreeNode *lower; TreeNode *upper; TreeNode *stride = 0; if (args()->child(0)->child(0)->type()->isPointType()) { // preassembled points assert( args()->arity() == 1 ); assert( args()->child(0)->arity() >= 2 ); assert( args()->child(0)->arity() <= 3 ); const TreeNode &arg = *args()->child(0); lower = arg.child(0); upper = arg.child(1); if (arg.arity() == 3) stride = arg.child(2); } else { // assemble points ourselves lower = slice( *args(), 0, where ); upper = slice( *args(), 1, where ); if (args()->child(0)->arity() == 3) stride = slice( *args(), 2, where ); } // create a default unit stride if none was given if (!stride) { Literal one( (int32) 1 ); llist< TreeNode * > *ones = 0; for (unsigned dimension = type()->tiArity(); dimension--; ) push( ones, (TreeNode *) new PrimitiveLitNode( one, where ) ); stride = new PointNode( ones, where ); } llist< TreeNode * > * domainArgs = 0; push( domainArgs, stride ); push( domainArgs, upper ); push( domainArgs, lower ); TreeNode *args = new TreeListNode( domainArgs, where ); DomainNode *replacement = new DomainNode( cons( args ), where ); return replacement; }