1 24 25 package org.aspectj.compiler.base.ast; 26 27 import org.aspectj.compiler.base.*; 28 29 import java.util.*; 30 31 import org.aspectj.compiler.base.bcg.CodeBuilder; 32 33 35 public class ArrayType extends RefType { 36 private Type componentType; 37 private int arrayDimCount; 38 39 public ArrayType(JavaCompiler compiler, Type componentType) { 40 super(compiler); 41 this.componentType = componentType; 42 this.arrayDimCount = 1 + componentType.getArrayDimCount(); 43 } 44 45 public Type getComponentType() { 46 return componentType; 47 } 48 public int getArrayDimCount() { 49 return arrayDimCount; 50 } 51 52 public Type getBaseComponentType() { 53 return getComponentType().getBaseComponentType(); 54 } 55 56 57 58 public Expr getClassExpr() { 59 return getAST().makeLiteral(this); } 61 62 public Expr fromObject(Expr expr) { 63 return getAST().makeCast(this, expr); } 65 66 public Expr makeObject(Expr expr) { return expr; } 67 public Expr getNullExpr() { return getAST().makeNull(); } 68 public Type getRefType() { return this; } 69 70 71 72 private final FieldDec lengthFieldDec = 73 getAST().makeField(getAST().makeModifiers(Modifiers.PUBLIC), 74 getTypeManager().intType, "length", null); 75 { 76 lengthFieldDec.setAllEnclosingTypes(this); 77 } 78 private final Field lengthField = (Field)lengthFieldDec.getCorrespondingSemanticObject(); 79 80 boolean checkAccess(ASTObject fromWhere, boolean showError) { 81 if (this.isAccessible(fromWhere)) return true; 82 83 if (showError) { 84 fromWhere.showError("array " + getPrettyString() + " is not accessible here"); 85 } 86 return false; 87 } 88 89 public Field getField(String id, ASTObject fromWhere, boolean showError) { 90 if (id.equals("length")) { 91 if (!checkAccess(fromWhere, showError)) return null; 92 return lengthField; 93 } 94 if (showError) { 95 getCompiler().showError(fromWhere, "no field " + id + " on arrays"); 96 } 97 return null; } 99 100 private final MethodDec cloneMethodDec = 101 getAST().makeMethod(getAST().makeModifiers(Modifiers.PUBLIC), 102 getTypeManager().getObjectType(), "clone", getAST().makeFormals(), null); 103 { 104 cloneMethodDec.setAllEnclosingTypes(this); 105 } 106 private final Method cloneMethod = (Method)cloneMethodDec.getCorrespondingSemanticObject(); 107 108 public Method getMethod(String id, ASTObject fromWhere, Exprs params, 109 boolean showError) 110 { 111 if (!checkAccess(fromWhere, showError)) return null; 112 if (id.equals("clone") && params.size() == 0) { 114 return cloneMethod; 115 } 116 return getTypeManager().getObjectType().getMethod(id, fromWhere, params, showError); 117 } 118 119 public SemanticObject findMatchingSemanticObject(SemanticObject o) { 120 if (o == cloneMethod) return cloneMethod; 121 else if (o == lengthField) return lengthField; 122 else return getTypeManager().getObjectType().findMatchingSemanticObject(o); 123 } 124 125 { 126 addDirectSuperType(getTypeManager().getObjectType()); 127 } 128 129 130 public String getString() { 131 return componentType.getString()+"[]"; 132 } 133 134 public String toShortString() { 135 return componentType.toShortString()+"[]"; 136 } 137 138 public void unparse(CodeWriter writer) { 139 writer.write(componentType.getString()); 140 writer.write("[]"); 141 } 142 143 public boolean isEquivalent(Type _other) { 145 if (!(_other instanceof ArrayType)) return false; 146 return ((ArrayType)_other).componentType.isEquivalent(componentType); 147 } 148 149 150 public boolean isSubtypeOf(Type other) { 151 return other.isObject() 152 || other == getTypeManager().getCloneableType() 153 || other == getTypeManager().getSerializableType(); 154 } 155 156 public boolean isAssignableFrom(Type _other) { 157 if (_other.isAnyType()) return true; 158 if (_other instanceof NullType) return true; 159 160 if (!(_other instanceof ArrayType)) return false; 161 ArrayType other = (ArrayType)_other; 162 if (this.isEquivalent(other)) return true; 163 if (componentType.isReferenceType() && other.getComponentType().isReferenceType()) { 165 return componentType.isAssignableFrom(other.getComponentType()); 166 } else { 167 return false; 168 } 169 } 170 171 public boolean isCoercableTo(Type _other) { 172 if (_other.isAssignableFrom(this)) return true; 173 if (this.isAssignableFrom(_other)) return true; 174 175 if (!(_other instanceof ArrayType)) return false; 176 ArrayType other = (ArrayType)_other; 177 if (this.isEquivalent(other)) return true; 178 if (componentType.isReferenceType() && other.getComponentType().isReferenceType()) { 180 return componentType.isCoercableTo(other.getComponentType()); 181 } else { 182 return false; 183 } 184 185 } 186 187 public boolean isCloneable() { return true; } 188 189 192 void emitMultiNewarray(CodeBuilder cb, int filledDims) { 193 cb.emitMULTIANEWARRAY(this, filledDims); 194 } 195 196 private String externalName; 199 private String internalName; 200 private String descriptor; 201 202 public synchronized String getExternalName() { 203 if (externalName == null) { 204 externalName = getDescriptor().replace('/', '.'); 205 } 206 return externalName; 207 } 208 209 public String getInternalName() { 210 return getDescriptor(); 211 } 212 213 public synchronized String getDescriptor() { 214 if (descriptor == null) { 215 descriptor = "[" + getComponentType().getDescriptor(); 216 } 217 return descriptor; 218 } 219 } 220 | Popular Tags |