📄 checker.java
字号:
package edu.ustc.cs.compile.parser;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.ListIterator;
import org.eclipse.jdt.core.dom.AST;
import org.eclipse.jdt.core.dom.ASTNode;
import org.eclipse.jdt.core.dom.ASTVisitor;
import org.eclipse.jdt.core.dom.ArrayAccess;
import org.eclipse.jdt.core.dom.ArrayInitializer;
import org.eclipse.jdt.core.dom.ArrayType;
import org.eclipse.jdt.core.dom.Assignment;
import org.eclipse.jdt.core.dom.Block;
import org.eclipse.jdt.core.dom.BooleanLiteral;
import org.eclipse.jdt.core.dom.CompilationUnit;
import org.eclipse.jdt.core.dom.Expression;
import org.eclipse.jdt.core.dom.FieldDeclaration;
import org.eclipse.jdt.core.dom.IfStatement;
import org.eclipse.jdt.core.dom.InfixExpression;
import org.eclipse.jdt.core.dom.MethodDeclaration;
import org.eclipse.jdt.core.dom.MethodInvocation;
import org.eclipse.jdt.core.dom.NumberLiteral;
import org.eclipse.jdt.core.dom.ParenthesizedExpression;
import org.eclipse.jdt.core.dom.PrefixExpression;
import org.eclipse.jdt.core.dom.PrimitiveType;
import org.eclipse.jdt.core.dom.QualifiedName;
import org.eclipse.jdt.core.dom.ReturnStatement;
import org.eclipse.jdt.core.dom.SimpleName;
import org.eclipse.jdt.core.dom.StringLiteral;
import org.eclipse.jdt.core.dom.Type;
import org.eclipse.jdt.core.dom.VariableDeclarationFragment;
import org.eclipse.jdt.core.dom.VariableDeclarationStatement;
import org.eclipse.jdt.core.dom.WhileStatement;
import edu.ustc.cs.compile.platform.interfaces.CheckerException;
import edu.ustc.cs.compile.platform.interfaces.CheckerInterface;
import edu.ustc.cs.compile.platform.interfaces.InterRepresent;
public class Checker implements CheckerInterface {
public boolean check(InterRepresent ir) throws CheckerException {
CompilationUnit cu = (CompilationUnit)ir.getIR();
myTable t = ((myHIR)ir).getTable();
CheckerVisitor visitor = new CheckerVisitor();
visitor.setIR(ir);
visitor.setTable(t);
cu.accept(visitor);
if (!visitor.success()) System.exit(-1);
return visitor.success();
}
public static void main(String[] args) {
InterRepresent ir = null;
CompilationUnit cu = (CompilationUnit)ir.getIR();
CheckerVisitor visitor = new CheckerVisitor();
visitor.setIR(ir);
cu.accept(visitor);
if (visitor.success()) {
System.out.println("Checker has not found any errors.");
} else {
System.out.println("Checker has found some errors.");
}
}
}
class CheckerVisitor extends ASTVisitor {
private boolean success = true;
private AST ast = AST.newAST(AST.JLS3);
private InterRepresent ir = null;
private myTable table;
private HashMap curTable = new HashMap();
private HashMap methodTable = new HashMap();
private LinkedList runStack = new LinkedList();
private String methodTag = new String();
private LinkedList before = new LinkedList();
private boolean methodF;
public boolean success() {
return success;
}
private void checkError(String s,ASTNode x){
System.out.println("[LINE."+x.getStartPosition()+"]Error:"+s);
success = false;
}
private void checkWarning(String s,ASTNode x){
System.out.println("[LINE."+x.getStartPosition()+"]Warning:"+s);
}
private boolean match(ASTNode x,ASTNode y){
Type tx = (Type)x.getProperty("type");
Type ty = (Type)y.getProperty("type");
return submatch(tx,ty);
}
private boolean submatch(Type tx,Type ty){
if (tx.isArrayType()&&ty.isArrayType())
return submatch(((ArrayType)tx).getComponentType(),((ArrayType)ty).getComponentType());
if (tx.isSimpleType()&&ty.isSimpleType()) return true;
if (tx.isPrimitiveType()&&ty.isPrimitiveType())
return (((PrimitiveType)tx).getPrimitiveTypeCode()==((PrimitiveType)ty).getPrimitiveTypeCode());
else return false;
}
private boolean isIntOP(InfixExpression.Operator op){
if (op==InfixExpression.Operator.PLUS
||op== InfixExpression.Operator.MINUS
||op== InfixExpression.Operator.TIMES
||op== InfixExpression.Operator.DIVIDE
||op== InfixExpression.Operator.REMAINDER)
return true;
else return false;
}
private boolean isBIop(InfixExpression.Operator op){
if (op==InfixExpression.Operator.GREATER
||op==InfixExpression.Operator.GREATER_EQUALS
||op==InfixExpression.Operator.LESS
||op==InfixExpression.Operator.LESS_EQUALS
||op==InfixExpression.Operator.EQUALS
||op==InfixExpression.Operator.NOT_EQUALS)
return true;
else return false;
}
private boolean isBBop(InfixExpression.Operator op){
if (op==InfixExpression.Operator.CONDITIONAL_AND||op==InfixExpression.Operator.CONDITIONAL_OR
||op==InfixExpression.Operator.EQUALS||op==InfixExpression.Operator.NOT_EQUALS)
return true;
else return false;
}
private boolean isInt(Type t){
if (!t.isPrimitiveType()) return false;
else
if (((PrimitiveType)t).getPrimitiveTypeCode()==PrimitiveType.INT) return true;
else return false;
}
private boolean isBool(Type t){
if (!t.isPrimitiveType()) return false;
else
if (((PrimitiveType)t).getPrimitiveTypeCode()==PrimitiveType.BOOLEAN) return true;
else return false;
}
private Integer compute(InfixExpression e){
if (e.getLeftOperand().getProperty("value")==null||e.getLeftOperand().getProperty("value")==null)
return null;
else {
InfixExpression.Operator op = e.getOperator();
Integer l = (Integer)e.getLeftOperand().getProperty("value");
Integer r = (Integer)e.getRightOperand().getProperty("value");
if (op==InfixExpression.Operator.PLUS) return l+r;
else if (op==InfixExpression.Operator.MINUS) return l-r;
else if (op==InfixExpression.Operator.TIMES) return l*r;
else if (op==InfixExpression.Operator.DIVIDE) return l/r;
else return l%r;
}
}
private Integer compute(PrefixExpression e){
if (e.getOperand().getProperty("value")==null) return null;
else {
PrefixExpression.Operator op = e.getOperator();
Integer x = (Integer)e.getOperand().getProperty("value");
if (op==PrefixExpression.Operator.PLUS) return x;
else return -x;
}
}
private Integer finalvisit(Expression e){
if (e.getProperty("value")!=null) return (Integer)e.getProperty("value");
CheckerVisitor subv = new CheckerVisitor();
subv.setTable(table);
subv.setStack(runStack, curTable);
e.accept(subv);
return (Integer)e.getProperty("value");
}
private void dumpList(LinkedList t){
Iterator iter = t.iterator();
while (iter.hasNext()){
SimpleName n = (SimpleName)iter.next();
checkError("\""+n.toString()+"\""+" referenced before been Initialized",n);
}
t.clear();
}
public void setIR(InterRepresent ir) {
this.ir = ir;
}
public void setTable(myTable t){
table = t;
curTable = (HashMap)table.getVtable().get(new Integer(0));
methodTable = (HashMap)table.getMtable();
runStack.add(curTable);
LinkedList pacList = new LinkedList();
pacList.add(ast.newPrimitiveType(PrimitiveType.VOID));
methodTable.put("print", pacList);
methodTable.put("read", pacList);
}
public void setStack(LinkedList kStack,HashMap kTable){
runStack.addAll(kStack);
curTable = kTable;
}
public boolean visit(MethodDeclaration n) {
methodTag = n.getName().getIdentifier();
runStack.add(curTable);
curTable = (HashMap)table.getVtable().get(n.getBody().getProperty("tag"));
methodF = true;
return super.visit(n);
}
public void endVisit(MethodDeclaration n) {
if (n.getBody().getProperty("return")==null&&
!submatch(ast.newPrimitiveType(PrimitiveType.VOID),(Type)((LinkedList)methodTable.get(n.getName().getIdentifier())).get(0)))
checkWarning("Method "+n.getName()+" doen't has returnstatement",n.getName());
super.endVisit(n);
}
public boolean visit(Block n) {
if (methodF){
methodF = false;
return super.visit(n);
}
Integer tag = (Integer)n.getProperty("tag");
runStack.add(curTable);
curTable = (HashMap)table.getVtable().get(tag);
return super.visit(n);
}
public void endVisit(Block n) {
curTable = (HashMap)runStack.removeLast();
if (n.getParent() instanceof Block) n.getParent().setProperty("return", n.getProperty("return"));
super.endVisit(n);
}
public void endVisit(FieldDeclaration n) {
Type t = n.getType();
Iterator iter = n.fragments().iterator();
while (iter.hasNext()) {
VariableDeclarationFragment temp = (VariableDeclarationFragment)iter.next();
if (temp.getInitializer()!=null)
if (temp.getInitializer().getProperty("type")!=null){
if (!submatch(t,(Type)temp.getInitializer().getProperty("type")))
checkError("\""+temp.getName().toString()+"\""+" has the wrong type initializer",temp.getName());
}
else
if (temp.getInitializer().getProperty("size")!=null&&t.isArrayType())
if (t.getProperty("size")!=null&&((Expression)t.getProperty("size")).getProperty("value")!=null)
if (((Integer)((Expression)t.getProperty("size")).getProperty("value")).intValue()!=((Integer)temp.getInitializer().getProperty("size")).intValue())
checkError("\""+temp.getName().toString()+"\""+" has wrong array size ("+t.getProperty("size")+" compare to "+temp.getInitializer().getProperty("size")+")",temp.getName());
else {
Iterator it = ((ArrayInitializer)temp.getInitializer()).expressions().iterator();
while (it.hasNext()){
Expression e = (Expression)it.next();
if (e.getProperty("type")!=null)
if (!submatch(((ArrayType)t).getComponentType(),(Type)e.getProperty("type")))
checkError("\""+temp.getName().toString()+"\""+" initialized with wrong array element type (Element:"+e.toString()+")",temp.getName());
}
}
if (t.isArrayType()&&t.getProperty("size")==null&&temp.getInitializer()==null)
checkError("\""+temp.getName()+"\" array initial should figur the size out",temp.getName());
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -