| /******************************************************************************* |
| * Copyright (c) 2000, 2014 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| *******************************************************************************/ |
| package org.aspectj.org.eclipse.jdt.internal.core; |
| |
| import java.util.HashMap; |
| |
| import org.aspectj.org.eclipse.jdt.core.*; |
| import org.aspectj.org.eclipse.jdt.core.compiler.CharOperation; |
| import org.aspectj.org.eclipse.jdt.internal.compiler.env.ISourceField; |
| import org.aspectj.org.eclipse.jdt.internal.compiler.env.ISourceImport; |
| import org.aspectj.org.eclipse.jdt.internal.compiler.env.ISourceMethod; |
| import org.aspectj.org.eclipse.jdt.internal.compiler.env.ISourceType; |
| |
| /** |
| * Element info for an IType element that originated from source. |
| */ |
| @SuppressWarnings({"rawtypes", "unchecked"}) |
| public class SourceTypeElementInfo extends AnnotatableInfo implements ISourceType { |
| |
| protected static final ISourceImport[] NO_IMPORTS = new ISourceImport[0]; |
| protected static final InitializerElementInfo[] NO_INITIALIZERS = new InitializerElementInfo[0]; |
| protected static final SourceField[] NO_FIELDS = new SourceField[0]; |
| protected static final SourceMethod[] NO_METHODS = new SourceMethod[0]; |
| protected static final SourceType[] NO_TYPES = new SourceType[0]; |
| |
| protected IJavaElement[] children = JavaElement.NO_ELEMENTS; |
| |
| /** |
| * The name of the superclass for this type. This name |
| * is fully qualified for binary types and is NOT always |
| * fully qualified for source types. |
| */ |
| protected char[] superclassName; |
| |
| /** |
| * The names of the interfaces this type implements or |
| * extends. These names are fully qualified in the case |
| * of a binary type, and are NOT always fully qualified in the |
| * case of a source type |
| */ |
| protected char[][] superInterfaceNames; |
| |
| /** |
| * Backpointer to my type handle - useful for translation |
| * from info to handle. |
| */ |
| protected IType handle = null; |
| |
| /* |
| * The type parameters of this source type. Empty if none. |
| */ |
| protected ITypeParameter[] typeParameters = TypeParameter.NO_TYPE_PARAMETERS; |
| |
| /* |
| * A map from an IJavaElement (this type or a child of this type) to a String[] (the categories of this element) |
| */ |
| protected HashMap categories; |
| |
| protected void addCategories(IJavaElement element, char[][] elementCategories) { |
| if (elementCategories == null) return; |
| if (this.categories == null) |
| this.categories = new HashMap(); |
| this.categories.put(element, CharOperation.toStrings(elementCategories)); |
| } |
| |
| /* |
| * Return a map from an IJavaElement (this type or a child of this type) to a String[] (the categories of this element) |
| */ |
| public HashMap getCategories() { |
| return this.categories; |
| } |
| |
| public IJavaElement[] getChildren() { |
| return this.children; |
| } |
| |
| /** |
| * Returns the ISourceType that is the enclosing type for this |
| * type, or <code>null</code> if this type is a top level type. |
| */ |
| public ISourceType getEnclosingType() { |
| IJavaElement parent= this.handle.getParent(); |
| if (parent != null && parent.getElementType() == IJavaElement.TYPE) { |
| try { |
| return (ISourceType)((JavaElement)parent).getElementInfo(); |
| } catch (JavaModelException e) { |
| return null; |
| } |
| } else { |
| return null; |
| } |
| } |
| /** |
| * @see ISourceType |
| */ |
| public ISourceField[] getFields() { |
| SourceField[] fieldHandles = getFieldHandles(); |
| int length = fieldHandles.length; |
| ISourceField[] fields = new ISourceField[length]; |
| for (int i = 0; i < length; i++) { |
| try { |
| ISourceField field = (ISourceField) fieldHandles[i].getElementInfo(); |
| fields[i] = field; |
| } catch (JavaModelException e) { |
| // ignore |
| } |
| } |
| return fields; |
| } |
| public SourceField[] getFieldHandles() { |
| int length = this.children.length; |
| if (length == 0) return NO_FIELDS; |
| SourceField[] fields = new SourceField[length]; |
| int fieldIndex = 0; |
| for (int i = 0; i < length; i++) { |
| IJavaElement child = this.children[i]; |
| if (child instanceof SourceField) |
| fields[fieldIndex++] = (SourceField) child; |
| } |
| if (fieldIndex == 0) return NO_FIELDS; |
| if (fieldIndex < length) |
| System.arraycopy(fields, 0, fields = new SourceField[fieldIndex], 0, fieldIndex); |
| return fields; |
| } |
| /** |
| * @see org.aspectj.org.eclipse.jdt.internal.compiler.env.IDependent#getFileName() |
| */ |
| public char[] getFileName() { |
| return this.handle.getPath().toString().toCharArray(); |
| } |
| /** |
| * Returns the handle for this type info |
| */ |
| public IType getHandle() { |
| return this.handle; |
| } |
| /* |
| * Returns the InitializerElementInfos for this type. |
| * Returns an empty array if none. |
| */ |
| public InitializerElementInfo[] getInitializers() { |
| int length = this.children.length; |
| if (length == 0) return NO_INITIALIZERS; |
| InitializerElementInfo[] initializers = new InitializerElementInfo[length]; |
| int initializerIndex = 0; |
| for (int i = 0; i < length; i++) { |
| IJavaElement child = this.children[i]; |
| if (child instanceof Initializer) { |
| try { |
| InitializerElementInfo initializer = (InitializerElementInfo)((Initializer)child).getElementInfo(); |
| initializers[initializerIndex++] = initializer; |
| } catch (JavaModelException e) { |
| // ignore |
| } |
| } |
| } |
| if (initializerIndex == 0) return NO_INITIALIZERS; |
| System.arraycopy(initializers, 0, initializers = new InitializerElementInfo[initializerIndex], 0, initializerIndex); |
| return initializers; |
| } |
| /** |
| * @see ISourceType |
| */ |
| public char[][] getInterfaceNames() { |
| if (this.handle.getElementName().length() == 0) { // if anonymous type |
| return null; |
| } |
| return this.superInterfaceNames; |
| } |
| |
| /** |
| * @see ISourceType |
| */ |
| public ISourceType[] getMemberTypes() { |
| SourceType[] memberTypeHandles = getMemberTypeHandles(); |
| int length = memberTypeHandles.length; |
| ISourceType[] memberTypes = new ISourceType[length]; |
| for (int i = 0; i < length; i++) { |
| try { |
| ISourceType type = (ISourceType) memberTypeHandles[i].getElementInfo(); |
| memberTypes[i] = type; |
| } catch (JavaModelException e) { |
| // ignore |
| } |
| } |
| return memberTypes; |
| } |
| public SourceType[] getMemberTypeHandles() { |
| int length = this.children.length; |
| if (length == 0) return NO_TYPES; |
| SourceType[] memberTypes = new SourceType[length]; |
| int typeIndex = 0; |
| for (int i = 0; i < length; i++) { |
| IJavaElement child = this.children[i]; |
| if (child instanceof SourceType) |
| memberTypes[typeIndex++] = (SourceType)child; |
| } |
| if (typeIndex == 0) return NO_TYPES; |
| if (typeIndex < length) |
| System.arraycopy(memberTypes, 0, memberTypes = new SourceType[typeIndex], 0, typeIndex); |
| return memberTypes; |
| } |
| /** |
| * @see ISourceType |
| */ |
| public ISourceMethod[] getMethods() { |
| SourceMethod[] methodHandles = getMethodHandles(); |
| int length = methodHandles.length; |
| ISourceMethod[] methods = new ISourceMethod[length]; |
| int methodIndex = 0; |
| for (int i = 0; i < length; i++) { |
| try { |
| ISourceMethod method = (ISourceMethod) methodHandles[i].getElementInfo(); |
| methods[methodIndex++] = method; |
| } catch (JavaModelException e) { |
| // ignore |
| } |
| } |
| return methods; |
| } |
| public SourceMethod[] getMethodHandles() { |
| int length = this.children.length; |
| if (length == 0) return NO_METHODS; |
| SourceMethod[] methods = new SourceMethod[length]; |
| int methodIndex = 0; |
| for (int i = 0; i < length; i++) { |
| IJavaElement child = this.children[i]; |
| if (child instanceof SourceMethod) |
| methods[methodIndex++] = (SourceMethod) child; |
| } |
| if (methodIndex == 0) return NO_METHODS; |
| if (methodIndex < length) |
| System.arraycopy(methods, 0, methods = new SourceMethod[methodIndex], 0, methodIndex); |
| return methods; |
| } |
| /** |
| * @see org.aspectj.org.eclipse.jdt.internal.compiler.env.ISourceType#getName() |
| */ |
| public char[] getName() { |
| return this.handle.getElementName().toCharArray(); |
| } |
| /** |
| * @see ISourceType |
| */ |
| public char[] getSuperclassName() { |
| if (this.handle.getElementName().length() == 0) { // if anonymous type |
| char[][] interfaceNames = this.superInterfaceNames; |
| if (interfaceNames != null && interfaceNames.length > 0) { |
| return interfaceNames[0]; |
| } |
| } |
| return this.superclassName; |
| } |
| public char[][][] getTypeParameterBounds() { |
| int length = this.typeParameters.length; |
| char[][][] typeParameterBounds = new char[length][][]; |
| for (int i = 0; i < length; i++) { |
| try { |
| TypeParameterElementInfo info = (TypeParameterElementInfo) ((JavaElement)this.typeParameters[i]).getElementInfo(); |
| typeParameterBounds[i] = info.bounds; |
| } catch (JavaModelException e) { |
| // type parameter does not exist: ignore |
| } |
| } |
| return typeParameterBounds; |
| } |
| public char[][] getTypeParameterNames() { |
| int length = this.typeParameters.length; |
| if (length == 0) return CharOperation.NO_CHAR_CHAR; |
| char[][] typeParameterNames = new char[length][]; |
| for (int i = 0; i < length; i++) { |
| typeParameterNames[i] = this.typeParameters[i].getElementName().toCharArray(); |
| } |
| return typeParameterNames; |
| } |
| /** |
| * @see ISourceType |
| */ |
| public boolean isBinaryType() { |
| return false; |
| } |
| /* |
| * Returns whether the source type is an anonymous type of a member type. |
| */ |
| public boolean isAnonymousMember() { |
| return false; |
| } |
| /** |
| * Sets the handle for this type info |
| */ |
| protected void setHandle(IType handle) { |
| this.handle = handle; |
| } |
| /** |
| * Sets the (unresolved) name of this type's superclass |
| */ |
| protected void setSuperclassName(char[] superclassName) { |
| this.superclassName = superclassName; |
| } |
| /** |
| * Sets the (unresolved) names of the interfaces this type implements or extends |
| */ |
| protected void setSuperInterfaceNames(char[][] superInterfaceNames) { |
| this.superInterfaceNames = superInterfaceNames; |
| } |
| public String toString() { |
| return "Info for " + this.handle.toString(); //$NON-NLS-1$ |
| } |
| } |