6 public class SemanticCheck {
9 public SemanticCheck(State state) {
13 public void semanticCheck() {
14 SymbolTable classtable=state.getClassSymbolTable();
15 Iterator it=classtable.getDescriptorsIterator();
17 ClassDescriptor cd=(ClassDescriptor)it.next();
18 System.out.println("Checking class: "+cd);
19 for(Iterator field_it=cd.getFields();field_it.hasNext();) {
20 FieldDescriptor fd=(FieldDescriptor)field_it.next();
21 System.out.println("Checking field: "+fd);
25 for(Iterator method_it=cd.getMethods();method_it.hasNext();) {
26 MethodDescriptor md=(MethodDescriptor)method_it.next();
32 public void checkTypeDescriptor(TypeDescriptor td) {
36 String name=td.toString();
37 ClassDescriptor field_cd=(ClassDescriptor)state.getClassSymbolTable().get(name);
39 throw new Error("Undefined class "+name);
40 td.setClassDescriptor(field_cd);
46 public void checkField(ClassDescriptor cd, FieldDescriptor fd) {
47 checkTypeDescriptor(fd.getType());
50 public void checkMethod(ClassDescriptor cd, MethodDescriptor md) {
51 /* Check return type */
52 if (!md.getReturnType().isVoid())
53 checkTypeDescriptor(md.getReturnType());
54 for(int i=0;i<md.numParameters();i++) {
55 TypeDescriptor param_type=md.getParamType(i);
56 checkTypeDescriptor(param_type);
58 BlockNode bn=state.getMethodBody(md);
59 /* Link the naming environments */
60 md.getParameterTable().setParent(cd.getFieldTable());
61 checkBlockNode(md, md.getParameterTable(),bn);
64 public void checkBlockNode(MethodDescriptor md, SymbolTable nametable, BlockNode bn) {
65 /* Link in the naming environment */
66 bn.getVarTable().setParent(nametable);
67 for(int i=0;i<bn.size();i++) {
68 BlockStatementNode bsn=bn.get(i);
69 checkBlockStatementNode(md, bn.getVarTable(),bsn);
73 public void checkBlockStatementNode(MethodDescriptor md, SymbolTable nametable, BlockStatementNode bsn) {
75 case Kind.BlockExpressionNode:
76 checkBlockExpressionNode(md, nametable,(BlockExpressionNode)bsn);
79 case Kind.DeclarationNode:
80 checkDeclarationNode(md, nametable, (DeclarationNode)bsn);
83 case Kind.IfStatementNode:
84 checkIfStatementNode(md, nametable, (IfStatementNode)bsn);
88 checkLoopNode(md, nametable, (LoopNode)bsn);
92 checkReturnNode(md, nametable, (ReturnNode)bsn);
95 case Kind.SubBlockNode:
96 checkSubBlockNode(md, nametable, (SubBlockNode)bsn);
102 void checkBlockExpressionNode(MethodDescriptor md, SymbolTable nametable, BlockExpressionNode ben) {
103 checkExpressionNode(md, nametable, ben.getExpression(), null);
106 void checkDeclarationNode(MethodDescriptor md, SymbolTable nametable, DeclarationNode dn) {
107 VarDescriptor vd=dn.getVarDescriptor();
108 checkTypeDescriptor(vd.getType());
109 Descriptor d=nametable.get(vd.getSymbol());
111 (d instanceof FieldDescriptor)) {
114 throw new Error(vd.getSymbol()+" defined a second time");
115 checkExpressionNode(md, nametable, dn.getExpression(), vd.getType());
118 void checkSubBlockNode(MethodDescriptor md, SymbolTable nametable, SubBlockNode sbn) {
119 checkBlockNode(md, nametable, sbn.getBlockNode());
122 void checkReturnNode(MethodDescriptor md, SymbolTable nametable, ReturnNode rn) {
123 checkExpressionNode(md, nametable, rn.getReturnExpression(), md.getReturnType());
126 void checkIfStatementNode(MethodDescriptor md, SymbolTable nametable, IfStatementNode isn) {
127 checkExpressionNode(md, nametable, isn.getCondition(), new TypeDescriptor(TypeDescriptor.BOOLEAN));
128 checkBlockNode(md, nametable, isn.getTrueBlock());
129 checkBlockNode(md, nametable, isn.getFalseBlock());
132 void checkExpressionNode(MethodDescriptor md, SymbolTable nametable, ExpressionNode en, TypeDescriptor td) {
134 case Kind.AssignmentNode:
135 checkAssignmentNode(md,nametable,(AssignmentNode)en,td);
138 checkCastNode(md,nametable,(CastNode)en,td);
140 case Kind.CreateObjectNode:
141 checkCreateObjectNode(md,nametable,(CreateObjectNode)en,td);
143 case Kind.FieldAccessNode:
144 checkFieldAccessNode(md,nametable,(FieldAccessNode)en,td);
146 case Kind.LiteralNode:
147 checkLiteralNode(md,nametable,(LiteralNode)en,td);
149 case Kind.MethodInvokeNode:
150 checkMethodInvokeNode(md,nametable,(MethodInvokeNode)en,td);
153 checkNameNode(md,nametable,(NameNode)en,td);
156 checkOpNode(md,nametable,(OpNode)en,td);
162 void checkAssignmentNode(MethodDescriptor md, SymbolTable nametable, AssignmentNode an, TypeDescriptor td) {
166 void checkCastNode(MethodDescriptor md, SymbolTable nametable, CastNode cn, TypeDescriptor td) {
169 void checkCreateObjectNode(MethodDescriptor md, SymbolTable nametable, CreateObjectNode con, TypeDescriptor td) {
172 void checkFieldAccessNode(MethodDescriptor md, SymbolTable nametable, FieldAccessNode fan, TypeDescriptor td) {
175 void checkLiteralNode(MethodDescriptor md, SymbolTable nametable, LiteralNode ln, TypeDescriptor td) {
178 void checkMethodInvokeNode(MethodDescriptor md, SymbolTable nametable, MethodInvokeNode min, TypeDescriptor td) {
181 void checkNameNode(MethodDescriptor md, SymbolTable nametable, NameNode nn, TypeDescriptor td) {
184 void checkOpNode(MethodDescriptor md, SymbolTable nametable, OpNode on,TypeDescriptor td) {
187 void checkLoopNode(MethodDescriptor md, SymbolTable nametable, LoopNode ln) {