// `For' is a little trickier since it has so many elements. We'll first
// transform it to a While stmt, i.e.:
//
// for (init; cond; next) stmt;
// =>
// init;
// while (cond) {
// stmt;
// next;
// }
//
// and then apply the loop peeling code for While.
Node * LoopPeelingChanger::peel_for_loop (forNode *p) {
// Transform the For loop into a While loop.
// Everything goes in a new block:
// { }
blockNode *newblock = new blockNode (NULL, NULL);
// First, insert the initialization of the For:
// { init; }
newblock->stmts().push_back (new exprstmtNode (
(exprNode *) clone_changer::clone(p->init())));
// Now build the body of a new While loop...
blockNode *whilebody = new blockNode (NULL, NULL);
// ...from the body of the For:
// { stmt; }
whilebody->stmts().push_back (
(stmtNode *) clone_changer::clone(p->body()));
// ...and the next from the For:
// { stmt; next; }
whilebody->stmts().push_back (new exprstmtNode (
(exprNode *) clone_changer::clone(p->next())));
// Now we wrap this body up in a While using the For condition:
// while (expr) { stmt; next; }
whileNode *newwhile = new whileNode (
(exprNode *) clone_changer::clone(p->cond()),
whilebody);
// Do loop peeling on the while loop, inserting the result after the
// init in the block we made before.
newblock->stmts().push_back (
(stmtNode *) peel_while_loop (newwhile));
return newblock;
}