Commit c0dd9f52 authored by Austin Clements's avatar Austin Clements

Make the statement compiler not use the AST visitor.

In the process, I made error handling in the statement
compiler much saner.  Instead of separately tracking various
error flags with weird relations, I just track if any error
messages have been produced.

R=rsc
APPROVED=rsc
DELTA=308  (98 added, 135 deleted, 75 changed)
OCL=33870
CL=33961
parent 4b409289
......@@ -24,13 +24,21 @@ type positioned interface {
// case it should be package compiler.
type compiler struct {
errors scanner.ErrorHandler;
numErrors int;
silentErrors int;
}
func (a *compiler) diagAt(pos positioned, format string, args ...) {
a.errors.Error(pos.Pos(), fmt.Sprintf(format, args));
a.numErrors++;
}
func (a *compiler) numError() int {
return a.numErrors + a.silentErrors;
}
// TODO(austin) These can all go in stmt.go now
type label struct {
name string;
desc string;
......@@ -61,7 +69,6 @@ type funcCompiler struct {
*codeBuf;
flow *flowBuf;
labels map[string] *label;
err bool;
}
// A blockCompiler captures information used throughout the compilation
......
......@@ -615,6 +615,7 @@ func (a *exprCompiler) compile(x ast.Expr) *expr {
// Remaining expressions
case *ast.BadExpr:
// Error already reported by parser
a.silentErrors++;
return nil;
case *ast.BinaryExpr:
......@@ -740,6 +741,7 @@ func (a *exprInfo) compileIdent(b *block, constant bool, name string) *expr {
func (a *exprInfo) compileVariable(level int, v *Variable) *expr {
if v.Type == nil {
// Placeholder definition from an earlier error
a.silentErrors++;
return nil;
}
expr := a.newExpr(v.Type, "variable");
......@@ -1614,7 +1616,12 @@ func (a *compiler) compileArrayLen(b *block, expr ast.Expr) (int64, bool) {
func (a *compiler) compileExpr(b *block, constant bool, expr ast.Expr) *expr {
ec := &exprCompiler{a, b, constant};
return ec.compile(expr);
nerr := a.numError();
e := ec.compile(expr);
if e == nil && nerr == a.numError() {
log.Crashf("expression compilation failed without reporting errors");
}
return e;
}
// extractEffect separates out any effects that the expression may
......@@ -1698,7 +1705,7 @@ func (expr *Expr) Eval(f *Frame) Value {
func CompileExpr(scope *Scope, expr ast.Expr) (*Expr, os.Error) {
errors := scanner.NewErrorVector();
cc := &compiler{errors};
cc := &compiler{errors, 0, 0};
ec := cc.compileExpr(scope.block, false, expr);
if ec == nil {
......
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment