// If this is an assignment, just check the rhs portion of it.
// This is a bit hacky but prevents verification from balking about new
// vars declared in the lhs.
if (parsedLine instanceof Assignment) {
new Reducer(parsedLine).reduce();
Assignment assignment = (Assignment) parsedLine;
// Strip the lhs of the assignment if this is a simple variable setter
// as that will happen after the fact in a where-block.
// However we still do have Assignment nodes that assign "in-place", i.e.
// mutate the state of existing variables (example: a.b = c), and these need
// to continue untouched.
if (assignment.lhs() instanceof Variable)
func.children().add(assignment.rhs());
else
func.children().add(parsedLine);
} else
func.children().add(parsedLine);
// Compress nodes and eliminate redundancies.
new Reducer(func).reduce();
shellScope.loadDeps("<shell>");
executable.runMain(true);
executable.compileExpression(shellScope);
if (executable.hasErrors()) {
executable.printStaticErrorsIfNecessary();
return "";
}
} catch (Exception e) {
e.printStackTrace();
return new LoopError("malformed expression " + rawLine);
}
try {
Object result = Loop.safeEval(executable, null);
if (addToWhereBlock && parsedLine instanceof Assignment) {
Assignment assignment = (Assignment) parsedLine;
boolean shouldReplace = false, shouldAddToWhere = true;
if (assignment.lhs() instanceof Variable) {
String name = ((Variable) assignment.lhs()).name;
shellContext.put(name, result);
// Look up the value of the RHS of the variable from the shell context,
// if this is the second reference to the same variable.
assignment.setRhs(new LexprParser(new Tokenizer(
"`loop.LoopShell`.shellObtain('" + name + "')").tokenize()).parse());
shouldReplace = true;
} else
shouldAddToWhere = false; // Do not add state-mutating assignments to where block.