1/* 2 * Javassist, a Java-bytecode translator toolkit. 3 * Copyright (C) 1999-2007 Shigeru Chiba, and others. All Rights Reserved. 4 * 5 * The contents of this file are subject to the Mozilla Public License Version 6 * 1.1 (the "License"); you may not use this file except in compliance with 7 * the License. Alternatively, the contents of this file may be used under 8 * the terms of the GNU Lesser General Public License Version 2.1 or later. 9 * 10 * Software distributed under the License is distributed on an "AS IS" basis, 11 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License 12 * for the specific language governing rights and limitations under the 13 * License. 14 */ 15package javassist.bytecode.analysis; 16 17import javassist.ClassPool; 18import javassist.CtClass; 19import javassist.NotFoundException; 20 21/** 22 * Represents an array of {@link MultiType} instances. 23 * 24 * @author Jason T. Greene 25 */ 26public class MultiArrayType extends Type { 27 private MultiType component; 28 private int dims; 29 30 public MultiArrayType(MultiType component, int dims) { 31 super(null); 32 this.component = component; 33 this.dims = dims; 34 } 35 36 public CtClass getCtClass() { 37 CtClass clazz = component.getCtClass(); 38 if (clazz == null) 39 return null; 40 41 ClassPool pool = clazz.getClassPool(); 42 if (pool == null) 43 pool = ClassPool.getDefault(); 44 45 String name = arrayName(clazz.getName(), dims); 46 47 try { 48 return pool.get(name); 49 } catch (NotFoundException e) { 50 throw new RuntimeException(e); 51 } 52 } 53 54 boolean popChanged() { 55 return component.popChanged(); 56 } 57 58 public int getDimensions() { 59 return dims; 60 } 61 62 public Type getComponent() { 63 return dims == 1 ? (Type)component : new MultiArrayType(component, dims - 1); 64 } 65 66 public int getSize() { 67 return 1; 68 } 69 70 public boolean isArray() { 71 return true; 72 } 73 74 public boolean isAssignableFrom(Type type) { 75 throw new UnsupportedOperationException("Not implemented"); 76 } 77 78 public boolean isReference() { 79 return true; 80 } 81 82 public boolean isAssignableTo(Type type) { 83 if (eq(type.getCtClass(), Type.OBJECT.getCtClass())) 84 return true; 85 86 if (eq(type.getCtClass(), Type.CLONEABLE.getCtClass())) 87 return true; 88 89 if (eq(type.getCtClass(), Type.SERIALIZABLE.getCtClass())) 90 return true; 91 92 if (! type.isArray()) 93 return false; 94 95 Type typeRoot = getRootComponent(type); 96 int typeDims = type.getDimensions(); 97 98 if (typeDims > dims) 99 return false; 100 101 if (typeDims < dims) { 102 if (eq(typeRoot.getCtClass(), Type.OBJECT.getCtClass())) 103 return true; 104 105 if (eq(typeRoot.getCtClass(), Type.CLONEABLE.getCtClass())) 106 return true; 107 108 if (eq(typeRoot.getCtClass(), Type.SERIALIZABLE.getCtClass())) 109 return true; 110 111 return false; 112 } 113 114 return component.isAssignableTo(typeRoot); 115 } 116 117 public boolean equals(Object o) { 118 if (! (o instanceof MultiArrayType)) 119 return false; 120 MultiArrayType multi = (MultiArrayType)o; 121 122 return component.equals(multi.component) && dims == multi.dims; 123 } 124 125 public String toString() { 126 // follows the same detailed formating scheme as component 127 return arrayName(component.toString(), dims); 128 } 129} 130