/*
* Copyright 2004 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Header:$
*/
package org.apache.beehive.netui.compiler.xdoclet.typesystem.impl.declaration;
import org.apache.beehive.netui.compiler.JpfLanguageConstants;
import org.apache.beehive.netui.compiler.typesystem.declaration.AnnotationInstance;
import org.apache.beehive.netui.compiler.typesystem.declaration.AnnotationTypeDeclaration;
import org.apache.beehive.netui.compiler.typesystem.declaration.AnnotationTypeElementDeclaration;
import org.apache.beehive.netui.compiler.typesystem.declaration.AnnotationValue;
import org.apache.beehive.netui.compiler.typesystem.declaration.Declaration;
import org.apache.beehive.netui.compiler.typesystem.declaration.Modifier;
import org.apache.beehive.netui.compiler.typesystem.type.AnnotationType;
import org.apache.beehive.netui.compiler.typesystem.type.ClassType;
import org.apache.beehive.netui.compiler.typesystem.type.PrimitiveType;
import org.apache.beehive.netui.compiler.typesystem.type.TypeInstance;
import org.apache.beehive.netui.compiler.typesystem.type.ArrayType;
import org.apache.beehive.netui.compiler.typesystem.type.DeclaredType;
import org.apache.beehive.netui.compiler.typesystem.util.SourcePosition;
import org.apache.beehive.netui.compiler.xdoclet.typesystem.impl.DelegatingImpl;
import org.apache.beehive.netui.compiler.xdoclet.typesystem.impl.env.SourcePositionImpl;
import org.apache.beehive.netui.compiler.xdoclet.typesystem.impl.type.AnnotationTypeImpl;
import org.apache.beehive.netui.xdoclet.XDocletCompilerUtils;
import xjavadoc.XDoc;
import xjavadoc.XProgramElement;
import xjavadoc.XTag;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.io.StreamTokenizer;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.StringTokenizer;
public class DeclarationImpl
extends DelegatingImpl
implements Declaration, JpfLanguageConstants
{
private static final String VALIDATION_ERROR_FORWARD_TAG_NAME = "ValidationErrorForward";
private static final HashMap MODIFIERS = new HashMap();
private static final HashMap MEMBER_ARRAY_ANNOTATIONS = new HashMap();
private static final HashMap MEMBER_ANNOTATIONS = new HashMap();
private static final HashSet MEMBER_OR_TOPLEVEL_ANNOTATIONS = new HashSet();
static
{
MODIFIERS.put( "abstract", Modifier.ABSTRACT );
MODIFIERS.put( "private", Modifier.PRIVATE );
MODIFIERS.put( "protected", Modifier.PROTECTED );
MODIFIERS.put( "public", Modifier.PUBLIC );
MODIFIERS.put( "static", Modifier.STATIC );
MODIFIERS.put( "transient", Modifier.TRANSIENT );
MODIFIERS.put( "final", Modifier.FINAL );
MODIFIERS.put( "synchronized", Modifier.SYNCHRONIZED );
MODIFIERS.put( "native", Modifier.NATIVE );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + FORWARD_TAG_NAME, FORWARDS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + CATCH_TAG_NAME, CATCHES_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + SIMPLE_ACTION_TAG_NAME, SIMPLE_ACTIONS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + ACTION_OUTPUT_TAG_NAME, ACTION_OUTPUTS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + CONDITIONAL_FORWARD_TAG_NAME, CONDITIONAL_FORWARDS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + MESSAGE_BUNDLE_TAG_NAME, MESSAGE_BUNDLES_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + MESSAGE_ARG_TAG_NAME, MESSAGE_ARGS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_CUSTOM_RULE_TAG_NAME, VALIDATE_CUSTOM_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_CUSTOM_VARIABLE_TAG_NAME, VARIABLES_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATION_LOCALE_RULES_TAG_NAME, LOCALE_RULES_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATABLE_PROPERTY_TAG_NAME, VALIDATABLE_PROPERTIES_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATABLE_BEAN_TAG_NAME, VALIDATABLE_BEANS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + RAISE_ACTION_TAG_NAME, RAISE_ACTIONS_ATTR );
MEMBER_ARRAY_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + SHARED_FLOW_REF_TAG_NAME, SHARED_FLOW_REFS_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATION_ERROR_FORWARD_TAG_NAME, VALIDATION_ERROR_FORWARD_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_REQUIRED_TAG_NAME, VALIDATE_REQUIRED_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_MIN_LENGTH_TAG_NAME, VALIDATE_MIN_LENGTH_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_MAX_LENGTH_TAG_NAME, VALIDATE_MAX_LENGTH_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_MASK_TAG_NAME, VALIDATE_MASK_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_TYPE_TAG_NAME, VALIDATE_TYPE_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_DATE_TAG_NAME, VALIDATE_DATE_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_RANGE_TAG_NAME, VALIDATE_RANGE_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_CREDIT_CARD_TAG_NAME, VALIDATE_CREDIT_CARD_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_EMAIL_TAG_NAME, VALIDATE_EMAIL_ATTR );
MEMBER_ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATE_VALID_WHEN_TAG_NAME, VALIDATE_VALID_WHEN_ATTR );
MEMBER_OR_TOPLEVEL_ANNOTATIONS.add( ANNOTATION_INTERFACE_PREFIX + VALIDATABLE_PROPERTY_TAG_NAME );
}
private HashSet _modifiers;
private AnnotationInstance[] _annotations;
public DeclarationImpl( XProgramElement delegate )
{
super( delegate );
ArrayList annotations = getAnnotations( delegate );
_annotations = ( AnnotationInstance[] ) annotations.toArray( new AnnotationInstance[ annotations.size() ] );
}
public String getDocComment()
{
return getDelegateXProgramElement().getDoc().getCommentText();
}
public AnnotationInstance[] getAnnotationInstances()
{
return _annotations;
}
public Set getModifiers()
{
if ( _modifiers == null )
{
HashSet modifiers = new HashSet();
StringTokenizer tok = new StringTokenizer( getDelegateXProgramElement().getModifiers() );
while ( tok.hasMoreTokens() )
{
String modifierString = tok.nextToken();
Modifier modifier = ( Modifier ) MODIFIERS.get( modifierString );
assert modifier != null : "unrecognized modifier: " + modifierString;
modifiers.add( modifier );
}
_modifiers = modifiers;
}
return _modifiers;
}
public String getSimpleName()
{
String name = getDelegateXProgramElement().getName();
int lastDot = name.lastIndexOf( '.' );
return lastDot != -1 ? name.substring( lastDot + 1 ) : name;
}
public SourcePosition getPosition()
{
return SourcePositionImpl.get( getDelegateXProgramElement() );
}
public boolean hasModifier( Modifier modifier )
{
return getModifiers().contains( modifier );
}
protected XProgramElement getDelegateXProgramElement()
{
return ( XProgramElement ) super.getDelegate();
}
/** Map of String intermediate-name (e.g., "Jpf.Action") to AnnotationTypeDeclaration */
private static HashMap ANNOTATIONS = new HashMap();
private static AnnotationTypeDeclaration[] ALL_ANNOTATIONS;
static
{
parseAnnotations();
ALL_ANNOTATIONS = ( AnnotationTypeDeclaration[] )
ANNOTATIONS.values().toArray( new AnnotationTypeDeclaration[ ANNOTATIONS.size() ] );
}
public static AnnotationTypeDeclaration[] getAllAnnotations()
{
return ALL_ANNOTATIONS;
}
private static StreamTokenizer getJavaTokenizer( Reader reader )
{
StreamTokenizer tok = new StreamTokenizer( reader );
tok.eolIsSignificant( false );
tok.lowerCaseMode( false );
tok.parseNumbers();
tok.slashSlashComments( true );
tok.slashStarComments( true );
tok.wordChars( '_', '_' );
tok.wordChars( '@', '@' );
tok.wordChars( '[', '[' );
tok.wordChars( ']', ']' );
tok.wordChars( '.', '.' );
tok.wordChars( '"', '"' );
tok.wordChars( '-', '-' );
return tok;
}
private static void parseAnnotations()
{
try
{
String annotationsSource = ANNOTATIONS_CLASSNAME.replace( '.', '/' ) + ".java";
InputStream in = DeclarationImpl.class.getClassLoader().getResourceAsStream( annotationsSource );
assert in != null : "annotations source not found: " + annotationsSource;
BufferedReader reader = new BufferedReader( new InputStreamReader( in ) );
HashMap enums = new HashMap(); // String enumTypeName -> HashSet values
StreamTokenizer tok = getJavaTokenizer( reader );
String interfaceQualifier = null;
String packageName = null;
while ( tok.nextToken() != StreamTokenizer.TT_EOF )
{
switch ( tok.ttype )
{
case StreamTokenizer.TT_WORD:
String str = tok.sval;
if ( packageName == null && str.equals( "package" ) )
{
packageName = assertWord( tok );
}
else if ( str.equals( "public" ) )
{
str = assertWord( tok );
if ( str.equals( "interface" ) )
{
interfaceQualifier = assertWord( tok ) + '.';
assertChar( tok, '{' );
}
else if ( str.equals( "@interface" ) )
{
AnnotationTypeDeclarationImpl ann =
readAnnotation( tok, interfaceQualifier, packageName, enums );
ANNOTATIONS.put( ann.getIntermediateName(), ann );
//
// Special case:
// validationErrorForward=@Jpf.Forward(...)
// looks like this in our world:
// @Jpf.ValidationErrorForward(...)
// Here we dynamically create a new ValidationErrorForward annotation based on Forward.
//
if ( ann.getSimpleName().equals( FORWARD_TAG_NAME ) )
{
AnnotationTypeDeclarationImpl validationErrorForwardAnn =
new AnnotationTypeDeclarationImpl( ann, VALIDATION_ERROR_FORWARD_TAG_NAME,
interfaceQualifier );
ANNOTATIONS.put( ANNOTATION_INTERFACE_PREFIX + VALIDATION_ERROR_FORWARD_TAG_NAME,
validationErrorForwardAnn );
}
}
else if ( str.equals( "enum" ) )
{
readEnum( tok, enums );
}
}
else if ( str.charAt( 0 ) == '@' )
{
ignoreAnnotation( tok );
}
break;
case StreamTokenizer.TT_NUMBER:
break;
default:
char c = ( char ) tok.ttype;
if ( c == '}' )
{
assert interfaceQualifier != null;
interfaceQualifier = null;
}
}
}
reader.close();
}
catch ( IOException e )
{
assert false : e;
}
}
private static String assertWord( StreamTokenizer tok )
throws IOException
{
tok.nextToken();
assert tok.ttype == StreamTokenizer.TT_WORD : tok.ttype;
return tok.sval;
}
private static void assertChar( StreamTokenizer tok, char c )
throws IOException
{
tok.nextToken();
assert tok.ttype == c : tok.ttype;
}
private static AnnotationTypeDeclarationImpl readAnnotation( StreamTokenizer tok, String interfaceQualifier,
String packageName, HashMap enums )
throws IOException
{
String annotationName = assertWord( tok );
ArrayList memberDecls = new ArrayList();
assertChar( tok, '{' );
while ( tok.nextToken() == StreamTokenizer.TT_WORD )
{
String memberType = tok.sval;
HashSet enumVals = ( HashSet ) enums.get( memberType );
tok.nextToken();
if ( tok.ttype == '<' ) // ignore generics
{
while ( tok.nextToken() != '>' )
{
assert tok.ttype != StreamTokenizer.TT_EOF;
assert tok.ttype != ';';
}
tok.nextToken();
}
assert tok.ttype == StreamTokenizer.TT_WORD;
String memberName = tok.sval;
assertChar( tok, '(' );
assertChar( tok, ')' );
Object defaultVal = null;
if ( tok.nextToken() == StreamTokenizer.TT_WORD )
{
assert tok.sval.equals( "default" );
tok.nextToken();
if ( tok.ttype == '{' )
{
assertChar( tok, '}' );
defaultVal = new ArrayList();
}
else
{
assert tok.ttype == StreamTokenizer.TT_WORD || tok.ttype == StreamTokenizer.TT_NUMBER : tok.ttype;
if ( tok.ttype == StreamTokenizer.TT_NUMBER )
{
defaultVal = getNumericDefaultVal( memberType, tok.nval );
}
else
{
String defaultString = tok.sval;
if ( defaultString.charAt( 0 ) == '@' )
{
// It's a default value that is an annotation. We ignore these for now.
ignoreAnnotation( tok );
}
else
{
if ( memberType.equals( "String" ) )
{
assert defaultString.charAt( 0 ) == '"' : defaultString;
int len = defaultString.length();
assert len > 1 && defaultString.charAt( len - 1 ) == '"' : defaultString;
defaultVal = defaultString.substring( 0, len - 1 );
}
else if ( memberType.equals( "boolean" ) )
{
defaultVal = Boolean.valueOf( defaultString );
}
else if ( memberType.equals( "Class") )
{
assert defaultString.endsWith( ".class" );
defaultVal = defaultString.substring( 0, defaultString.indexOf( ".class" ) );
}
else
{
defaultVal = readDefaultEnumVal( defaultString, memberType, enumVals );
}
}
}
}
tok.nextToken();
}
assert tok.ttype == ';';
if ( enumVals != null ) memberType = "String";
memberDecls.add( new AnnotationTypeElementDeclarationImpl( memberName, memberType, defaultVal, enumVals ) );
}
assert tok.ttype == '}';
AnnotationTypeElementDeclaration[] memberArray = ( AnnotationTypeElementDeclaration[] )
memberDecls.toArray( new AnnotationTypeElementDeclaration[ memberDecls.size() ] );
return new AnnotationTypeDeclarationImpl( annotationName, interfaceQualifier, packageName, memberArray );
}
private static String readDefaultEnumVal( String defaultString, String memberType, HashSet enumVals )
{
int dot = defaultString.indexOf( '.' );
assert dot != -1 : "expected an enum value: " + defaultString;
String type = defaultString.substring( 0, dot );
assert type.equals( memberType ) : "expected enum " + memberType + ", got " + type;
assert enumVals != null : "no enum " + memberType
+ " defined; currently, enum must be defined before its use";
String defaultVal = defaultString.substring( dot + 1 );
assert enumVals.contains( defaultVal ) :
"invalid enum field " + defaultVal + " on enum " + type;
return defaultVal;
}
private static Object getNumericDefaultVal( String expectedType, double defaultNumber )
{
if ( expectedType.equals( "int" ) )
{
return new Integer( ( int ) defaultNumber );
}
else if ( expectedType.equals( "long" ) )
{
return new Long( ( long ) defaultNumber );
}
else if ( expectedType.equals( "float" ) )
{
return new Float( ( float ) defaultNumber );
}
else if ( expectedType.equals( "double" ) )
{
return new Double( defaultNumber );
}
assert false : "type " + expectedType + " cannot accept value " + defaultNumber;
return null;
}
private static void ignoreAnnotation( StreamTokenizer tok )
throws IOException
{
while ( tok.nextToken() != ')' )
{
assert tok.ttype != StreamTokenizer.TT_EOF;
assert tok.ttype != ';';
}
}
private static void readEnum( StreamTokenizer tok, HashMap enums )
throws IOException
{
String enumName = assertWord( tok );
assertChar( tok, '{' );
HashSet fieldNames = new HashSet();
while ( true )
{
fieldNames.add( assertWord( tok ) );
tok.nextToken();
if ( tok.ttype == '}' ) break;
assert tok.ttype == ',' : tok.ttype; // for now, we only do very simple enums.
}
enums.put( enumName, fieldNames );
}
/**
* Get all the annotations for the given element.
* @param element the element (class, method, etc.) to examine
* @return an ArrayList of AnnotationInstances.
*/
private static ArrayList getAnnotations( XProgramElement element )
{
XDoc doc = element.getDoc();
ArrayList annotations = new ArrayList();
List tags = doc != null ? doc.getTags() : null;
ArrayList parentAnnotations = new ArrayList(); // hierarchy of parent annotations, e.g., Action -> Forward -> ...
if ( tags == null ) return annotations;
for ( Iterator i = tags.iterator(); i.hasNext(); )
{
XTag tag = ( XTag ) i.next();
AnnotationTypeDeclaration decl = ( AnnotationTypeDeclaration ) ANNOTATIONS.get( tag.getName() );
if ( decl != null )
{
AnnotationType type = new AnnotationTypeImpl( decl );
Collection attrNames = tag.getAttributeNames();
HashMap elementValues = new HashMap();
for ( Iterator j = attrNames.iterator(); j.hasNext(); )
{
String attrName = ( String ) j.next();
AnnotationTypeElementDeclaration memberDecl = decl.getMember( attrName );
SourcePositionImpl pos = SourcePositionImpl.get( tag, attrName, element );
Object val = parseValue( memberDecl, tag.getAttributeValue( attrName ), pos );
AnnotationValue value = new AnnotationValueImpl( val, pos, memberDecl );
elementValues.put( memberDecl, value );
}
AnnotationInstanceImpl ann = new AnnotationInstanceImpl( tag, element, type, elementValues );
String memberName = ( String ) MEMBER_ARRAY_ANNOTATIONS.get( tag.getName() );
if ( memberName != null )
{
if ( ! addAnnotationToParent( annotations, ann, memberName, true, parentAnnotations ) )
{
annotations.add( ann );
}
}
else if ( ( memberName = ( String ) MEMBER_ANNOTATIONS.get( tag.getName() ) ) != null )
{
if ( ! addAnnotationToParent( annotations, ann, memberName, false, parentAnnotations ) )
{
annotations.add( ann );
}
}
else
{
annotations.add( ann );
}
for ( int j = 0, len = parentAnnotations.size(); j < len; ++j )
{
AnnotationInstanceImpl parentAnn = ( AnnotationInstanceImpl ) parentAnnotations.get( j );
if ( parentAnn.getAnnotationType().equals( ann.getAnnotationType() ) )
{
// We found an annotation of this type in the hierarchy of parent annotations.
// Replace it and blow away everything after it.
for ( int k = j; k < len; ++k )
{
parentAnnotations.remove( j );
}
break;
}
}
parentAnnotations.add( ann );
}
}
return annotations;
}
private static boolean addAnnotationToParent( ArrayList annotations, AnnotationInstanceImpl ann, String memberArrayName,
boolean memberIsArray, ArrayList parentAnnotations )
{
if ( annotations.size() == 0 )
{
String annName = ann.getDelegateXTag().getName();
if ( MEMBER_OR_TOPLEVEL_ANNOTATIONS.contains( annName ) ) return false;
XDocletCompilerUtils.addError( ann.getPosition(), "error.no-parent-annotation",
new String[]{ ann.getAnnotationType().getAnnotationTypeDeclaration().getQualifiedName() } );
}
else
{
AnnotationInstanceImpl foundTheRightParent = null;
//
// Look through the hierarchy of parent annotations, for the first one that can accept the given annotation
// as a child.
//
for ( int i = parentAnnotations.size() - 1; i >= 0; --i )
{
AnnotationInstanceImpl parentAnnotation = ( AnnotationInstanceImpl ) parentAnnotations.get( i );
AnnotationTypeElementDeclaration elementDecl =
parentAnnotation.getAnnotationType().getAnnotationTypeDeclaration().getMember( memberArrayName );
if ( elementDecl != null )
{
foundTheRightParent = parentAnnotation;
//
// Blow away everything past the found parent annotation in the hierarchy.
//
for ( int j = i + 1, len = parentAnnotations.size(); j < len; ++j )
{
parentAnnotations.remove( i + 1 );
}
break;
}
}
if ( foundTheRightParent != null )
{
foundTheRightParent.addElementValue( memberArrayName, memberIsArray, ann, ann.getPosition() );
}
else
{
String annName = ann.getDelegateXTag().getName();
if ( MEMBER_OR_TOPLEVEL_ANNOTATIONS.contains( annName ) ) return false;
XDocletCompilerUtils.addError( ann.getPosition(), "error.no-parent-annotation",
new String[]{ ann.getAnnotationType().getAnnotationTypeDeclaration().getQualifiedName() } );
}
}
return true;
}
private static Object parseValue( AnnotationTypeElementDeclaration memberDecl, String strValue, SourcePositionImpl pos )
{
TypeInstance type = memberDecl.getReturnType();
if ( type instanceof ClassType )
{
ClassType classType = ( ClassType ) type;
String typeName = classType.getClassTypeDeclaration().getQualifiedName();
if ( typeName.equals( "java.lang.String" ) )
{
return strValue;
}
else if ( typeName.equals( "java.lang.Class" ) )
{
TypeInstance retVal = XDocletCompilerUtils.resolveType( strValue, false, pos.getOuterClass() );
if ( retVal == null )
{
XDocletCompilerUtils.addError( pos, "error.unknown-class",
new String[]{ strValue, memberDecl.getSimpleName() } );
}
return XDocletCompilerUtils.resolveType( strValue, true, pos.getOuterClass() );
}
else
{
assert false : "unexpected type in annotation declaration: " + typeName;
}
}
else if ( type instanceof ArrayType )
{
ArrayType arrayType = ( ArrayType ) type;
TypeInstance componentType = arrayType.getComponentType();
// We only handle an array of strings -- nothing else at this point.
assert componentType instanceof DeclaredType : componentType.getClass().getName();
assert ( ( DeclaredType ) componentType ).getDeclaration().getQualifiedName().equals( String.class.getName() )
: ( ( DeclaredType ) componentType ).getDeclaration().getQualifiedName();
StringTokenizer tok = new StringTokenizer( strValue, "," );
ArrayList arrayValues = new ArrayList();
while ( tok.hasMoreTokens() )
{
arrayValues.add( new AnnotationValueImpl( tok.nextToken().trim(), pos, memberDecl ) );
}
return arrayValues;
}
assert type instanceof PrimitiveType : type.getClass().getName();
switch ( ( ( PrimitiveType ) type ).getKind().asInt() )
{
case PrimitiveType.Kind.INT_BOOLEAN:
return Boolean.valueOf( strValue );
case PrimitiveType.Kind.INT_BYTE:
return new Byte( strValue );
case PrimitiveType.Kind.INT_SHORT:
return new Short( strValue );
case PrimitiveType.Kind.INT_INT:
return new Integer( strValue );
case PrimitiveType.Kind.INT_LONG:
return new Long( strValue );
case PrimitiveType.Kind.INT_FLOAT:
return new Float( strValue );
case PrimitiveType.Kind.INT_DOUBLE:
return new Double( strValue );
}
assert false : "unrecognized type: " + type.toString();
return null;
}
}