- } else {
- ForthBlock b2 = new ForthBlock(curLine, sourceName);
- b.add(b.SCOPE, b2);
- b.add(b.POP);
-
- ForthBlock e1 = startExpr();
- if (e1 == null) e1 = new ForthBlock(curLine, sourceName, b.LITERAL, null);
-
- b2.add(b.EXPR, e1);
- b2.add(b.POP);
- consume(SEMI);
- ForthBlock e2 = startExpr();
- consume(SEMI);
- ForthBlock e3 = startExpr();
- consume(RP);
-
- if (e2 == null) e2 = new ForthBlock(curLine, sourceName, b.LITERAL, null);
- if (e3 == null) e3 = new ForthBlock(curLine, sourceName, b.LITERAL, null);
-
- ForthBlock b3 = new ForthBlock(curLine, sourceName);
- b2.add(b.LOOP, b3);
- b2.add(b.LITERAL, null);
- b3.add(b.JT, new Integer(3));
- b3.add(b.EXPR, e3);
- b3.add(b.POP);
- b3.add(b.EXPR, e2);
- b3.add(b.JT, new Integer(2));
- b3.add(BREAK);
- parseStatement(false, b3);
- b3.add(BREAK);
- break;
+ tok = getToken();
+ boolean hadVar = false;
+ if (tok == VAR) { hadVar = true; tok = getToken(); }
+ String varName = string;
+ boolean forIn = peekToken() == IN;
+ pushBackToken(tok, varName);
+
+ if (forIn) {
+ // FIXME: break needs to work in here
+ consume(NAME);
+ consume(IN);
+ startExpr(-1, b);
+ b.add(line, PUSHKEYS);
+ b.add(line, LITERAL, "length");
+ b.add(line, GET);
+ consume(RP);
+ CompiledFunction b2 = new CompiledFunction(sourceName, line, null);
+
+ b.add(line, NEWSCOPE);
+
+ b.add(line, LITERAL, new Integer(1));
+ b.add(line, SUB);
+ b.add(line, DUP);
+ b.add(line, LITERAL, new Integer(0));
+ b.add(line, LT);
+ b.add(line, JT, new Integer(7));
+ b.add(line, GET_PRESERVE);
+ b.add(line, LITERAL, varName);
+ b.add(line, LITERAL, varName);
+ b.add(line, DECLARE);
+ b.add(line, PUT);
+ parseStatement(false, b);
+
+ b.add(line, OLDSCOPE);
+
+ break;
+
+ } else {
+ if (hadVar) pushBackToken(VAR, null);
+ b.add(line, NEWSCOPE);
+
+ parseStatement(false, b);
+ CompiledFunction e2 = new CompiledFunction(sourceName, line, null);
+ startExpr(-1, e2);
+ consume(SEMI);
+ if (e2 == null) e2 = new CompiledFunction(sourceName, line, null).add(line, b.LITERAL, Boolean.TRUE);
+
+ if (label != null) b.add(line, LABEL, label);
+ b.add(line, LOOP);
+ int size2 = b.size();
+
+ b.add(line, JT, new Integer(0));
+ int size = b.size();
+ startExpr(-1, b);
+ if (b.size() > size) b.add(line, POP);
+ b.set(size - 1, new Integer(b.size() - size + 1));
+ consume(RP);
+
+ b.paste(e2);
+ b.add(line, JT, new Integer(2));
+ b.add(line, BREAK);
+ parseStatement(false, b);
+ b.add(line, CONTINUE);
+ b.set(size2 - 1, new Integer(b.size() - size2 + 1)); // end of the loop
+
+ b.add(line, OLDSCOPE);
+ break;
+ }