- public void queueEmptyReductions() {
- if (!reducing) return;
- state.invokeReductions(token, this, null, null);
+
+ public void reduce(Position r, int pos, Phase target, Node only) {
+ Forest[] holder = r.holder;
+ Forest old = holder[pos];
+
+ HashSet<Forest> rr = new HashSet<Forest>();
+ for(Forest result : results()) rr.add(result);
+ for(Forest result : rr)
+ for(Node child : ((Forest.Ref<?>)result).parents) {
+ if (only != null && child!=only) continue;
+ holder[pos] = result;
+ if (pos==0) child.finish(r, r.rewrite(new Input.Region(child.phase().getLocation(), phase().getLocation())), target);
+ else child.reduce(r, pos-1, target, null);
+ }
+
+ holder[pos] = old;
+ }
+
+ public void finish(Position r, Forest result, Phase<Tok> target) {
+ Parser.Table<Tok>.State<Tok> state0 = state.gotoSetNonTerminals.get(r.owner());
+ if (result==null) throw new Error();
+ if (state0!=null)
+ target.newNode(this, result, state0, r.pos<=0, r);