Some of the TypeOracle changes to support generics. Changes to JsniInjector to support generics. Reverting custom field serializers to use raw types for now. Removing Serializable from Enums until RPC properly supports it. Other miscellaneous stuff.
Hopefully the trunk is basically usable now.
Patch by: scottb, jat, mmendez
git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@1448 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JAbstractMethod.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JAbstractMethod.java
index 096cffd..be5ebca 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JAbstractMethod.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JAbstractMethod.java
@@ -23,7 +23,8 @@
/**
* Common superclass for {@link JMethod} and {@link JConstructor}.
*/
-public abstract class JAbstractMethod implements HasAnnotations, HasMetaData {
+public abstract class JAbstractMethod implements HasAnnotations, HasMetaData,
+ HasTypeParameters {
private final Annotations annotations = new Annotations();
@@ -35,6 +36,8 @@
private final int declStart;
+ private boolean isVarArgs = false;
+
private final HasMetaData metaData = new MetaData();
private int modifierBits;
@@ -45,9 +48,12 @@
private final List<JType> thrownTypes = new ArrayList<JType>();
+ private final List<JTypeParameter> typeParams = new ArrayList<JTypeParameter>();
+
// Only the builder can construct
JAbstractMethod(String name, int declStart, int declEnd, int bodyStart,
- int bodyEnd, Map<Class<? extends Annotation>, Annotation> declaredAnnotations) {
+ int bodyEnd,
+ Map<Class<? extends Annotation>, Annotation> declaredAnnotations) {
this.name = name;
this.declStart = declStart;
this.declEnd = declEnd;
@@ -132,6 +138,10 @@
return thrownTypes.toArray(TypeOracle.NO_JTYPES);
}
+ public JTypeParameter[] getTypeParameters() {
+ return typeParams.toArray(new JTypeParameter[typeParams.size()]);
+ }
+
public JAnnotationMethod isAnnotationMethod() {
return null;
}
@@ -160,20 +170,36 @@
return 0 != (modifierBits & TypeOracle.MOD_PUBLIC);
}
+ public boolean isVarArgs() {
+ return isVarArgs;
+ }
+
+ public void setVarArgs() {
+ isVarArgs = true;
+ }
+
protected int getModifierBits() {
return modifierBits;
}
- protected void toStringParamsAndThrows(StringBuffer sb) {
+ protected void toStringParamsAndThrows(StringBuilder sb) {
sb.append("(");
boolean needComma = false;
- for (JParameter param : params) {
+ for (int i = 0, c = params.size(); i < c; ++i) {
+ JParameter param = params.get(i);
if (needComma) {
sb.append(", ");
} else {
needComma = true;
}
- sb.append(param.getType().getParameterizedQualifiedSourceName());
+ if (isVarArgs() && i == c - 1) {
+ JArrayType arrayType = param.getType().isArray();
+ assert (arrayType != null);
+ sb.append(arrayType.getComponentType().getParameterizedQualifiedSourceName());
+ sb.append("...");
+ } else {
+ sb.append(param.getType().getParameterizedQualifiedSourceName());
+ }
sb.append(" ");
sb.append(param.getName());
}
@@ -193,10 +219,29 @@
}
}
+ protected void toStringTypeParams(StringBuilder sb) {
+ sb.append("<");
+ boolean needComma = false;
+ for (JTypeParameter typeParam : typeParams) {
+ if (needComma) {
+ sb.append(", ");
+ } else {
+ needComma = true;
+ }
+ sb.append(typeParam.getName());
+ sb.append(typeParam.getBounds().toString());
+ }
+ sb.append(">");
+ }
+
void addParameter(JParameter param) {
params.add(param);
}
+ void addTypeParameter(JTypeParameter typeParameter) {
+ typeParams.add(typeParameter);
+ }
+
boolean hasParamTypes(JType[] paramTypes) {
if (params.size() != paramTypes.length) {
return false;
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JAnnotationType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JAnnotationType.java
index 19ae577..fbec74e 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JAnnotationType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JAnnotationType.java
@@ -20,7 +20,7 @@
/**
* Type representing an annotation type.
*/
-public class JAnnotationType extends JClassType {
+public class JAnnotationType extends JRealClassType {
public JAnnotationType(TypeOracle oracle, CompilationUnitProvider cup,
JPackage declaringPackage, JClassType enclosingType, boolean isLocalType,
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JArrayType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JArrayType.java
index a9277f2..d7e6694 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JArrayType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JArrayType.java
@@ -15,10 +15,15 @@
*/
package com.google.gwt.core.ext.typeinfo;
+import com.google.gwt.core.ext.UnableToCompleteException;
+
+import java.lang.annotation.Annotation;
+import java.util.Map;
+
/**
* Type representing a Java array.
*/
-public class JArrayType extends JType {
+public class JArrayType extends JClassType {
private JType componentType;
@@ -26,14 +31,126 @@
private String lazySimpleName;
- JArrayType(JType componentType) {
+ private final TypeOracle oracle;
+
+ JArrayType(JType componentType, TypeOracle oracle) {
this.componentType = componentType;
+ this.oracle = oracle;
+ }
+
+ @Override
+ public void addImplementedInterface(JClassType intf) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ public void addMetaData(String tagName, String[] values) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ public void addModifierBits(int bits) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ public JConstructor findConstructor(JType[] paramTypes) {
+ return null;
+ }
+
+ @Override
+ public JField findField(String name) {
+ // TODO length
+ return null;
+ }
+
+ @Override
+ public JMethod findMethod(String name, JType[] paramTypes) {
+ // TODO Object
+ return null;
+ }
+
+ @Override
+ public JClassType findNestedType(String typeName) {
+ return null;
+ }
+
+ @Override
+ public <T extends Annotation> T getAnnotation(Class<T> annotationClass) {
+ return null;
+ }
+
+ @Override
+ public Annotation[] getAnnotations() {
+ return TypeOracle.NO_ANNOTATIONS;
+ }
+
+ @Override
+ public int getBodyEnd() {
+ return 0;
+ }
+
+ @Override
+ public int getBodyStart() {
+ return 0;
+ }
+
+ @Override
+ public CompilationUnitProvider getCompilationUnit() {
+ return null;
}
public JType getComponentType() {
return componentType;
}
+ @Override
+ public JConstructor getConstructor(JType[] paramTypes)
+ throws NotFoundException {
+ return null;
+ }
+
+ @Override
+ public JConstructor[] getConstructors() {
+ return null;
+ }
+
+ @Override
+ public Annotation[] getDeclaredAnnotations() {
+ return TypeOracle.NO_ANNOTATIONS;
+ }
+
+ @Override
+ public JClassType getEnclosingType() {
+ return null;
+ }
+
+ @Override
+ public JClassType getErasedType() {
+ // TODO array of component type
+ return this;
+ }
+
+ @Override
+ public JField getField(String name) {
+ // TODO length
+ return null;
+ }
+
+ @Override
+ public JField[] getFields() {
+ // TODO length
+ return null;
+ }
+
+ @Override
+ public JClassType[] getImplementedInterfaces() {
+ return TypeOracle.NO_JCLASSES;
+ }
+
public String getJNISignature() {
return "[" + componentType.getJNISignature();
}
@@ -42,6 +159,68 @@
return componentType.getLeafType();
}
+ @Override
+ public String[][] getMetaData(String tagName) {
+ return TypeOracle.NO_STRING_ARR_ARR;
+ }
+
+ @Override
+ public String[] getMetaDataTags() {
+ return TypeOracle.NO_STRINGS;
+ }
+
+ @Override
+ public JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException {
+ // TODO Object
+ return null;
+ }
+
+ @Override
+ public JMethod[] getMethods() {
+ // TODO Object
+ return null;
+ }
+
+ @Override
+ public String getName() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JClassType getNestedType(String typeName) throws NotFoundException {
+ throw new NotFoundException();
+ }
+
+ @Override
+ public JClassType[] getNestedTypes() {
+ return TypeOracle.NO_JCLASSES;
+ }
+
+ @Override
+ public TypeOracle getOracle() {
+ return oracle;
+ }
+
+ @Override
+ public JMethod[] getOverloads(String name) {
+ // TODO Object
+ return null;
+ }
+
+ @Override
+ public JMethod[] getOverridableMethods() {
+ // TODO Object
+ return null;
+ }
+
+ @Override
+ public JPackage getPackage() {
+ // TODO
+ return null;
+ }
+
public String getParameterizedQualifiedSourceName() {
return getComponentType().getParameterizedQualifiedSourceName() + "[]";
}
@@ -69,20 +248,80 @@
return lazySimpleName;
}
+ @Override
+ public JClassType[] getSubtypes() {
+ // TODO
+ return TypeOracle.NO_JCLASSES;
+ }
+
+ @Override
+ public JClassType getSuperclass() {
+ // TODO Object?
+ return null;
+ }
+
+ @Override
+ public String getTypeHash() throws UnableToCompleteException {
+ // TODO
+ return null;
+ }
+
+ @Override
+ public boolean isAbstract() {
+ return false;
+ }
+
+ @Override
+ public boolean isAnnotationPresent(Class<? extends Annotation> annotationClass) {
+ return false;
+ }
+
public JArrayType isArray() {
return this;
}
+ @Override
+ public boolean isAssignableFrom(JClassType possibleSubtype) {
+ // TODO
+ return false;
+ }
+
+ @Override
+ public boolean isAssignableTo(JClassType possibleSupertype) {
+ // TODO
+ return false;
+ }
+
public JClassType isClass() {
// intentional null
return null;
}
+ @Override
+ public boolean isDefaultInstantiable() {
+ return true;
+ }
+
+ @Override
+ public JGenericType isGenericType() {
+ return null;
+ }
+
public JClassType isInterface() {
// intentional null
return null;
}
+ @Override
+ public boolean isLocalType() {
+ return false;
+ }
+
+ @Override
+ public boolean isMemberType() {
+ return false;
+ }
+
public JParameterizedType isParameterized() {
// intentional null
return null;
@@ -93,6 +332,31 @@
return null;
}
+ @Override
+ public boolean isPrivate() {
+ return false;
+ }
+
+ @Override
+ public boolean isProtected() {
+ return false;
+ }
+
+ @Override
+ public boolean isPublic() {
+ return true;
+ }
+
+ @Override
+ public JRawType isRawType() {
+ return null;
+ }
+
+ @Override
+ public boolean isStatic() {
+ return true;
+ }
+
public void setLeafType(JType type) {
JArrayType componentTypeIsArray = componentType.isArray();
if (componentTypeIsArray != null) {
@@ -102,7 +366,79 @@
}
}
+ @Override
+ public void setSuperclass(JClassType type) {
+ }
+
public String toString() {
return getQualifiedSourceName();
}
+
+ @Override
+ protected void acceptSubtype(JClassType me) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ protected int getModifierBits() {
+ return 0;
+ }
+
+ @Override
+ protected void getOverridableMethodsOnSuperclassesAndThisClass(
+ Map<String, JMethod> methodsBySignature) {
+ // TODO Object
+ }
+
+ @Override
+ protected void getOverridableMethodsOnSuperinterfacesAndMaybeThisInterface(
+ Map<String, JMethod> methodsBySignature) {
+ // TODO Object
+ }
+
+ @Override
+ protected void notifySuperTypesOf(JClassType me) {
+ }
+
+ @Override
+ protected void removeSubtype(JClassType me) {
+ }
+
+ @Override
+ void addConstructor(JConstructor ctor) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ void addField(JField field) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ void addMethod(JMethod method) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ void addNestedType(JClassType type) {
+ throw new UnsupportedOperationException("modifying a "
+ + getClass().getSimpleName());
+ }
+
+ @Override
+ JClassType findNestedTypeImpl(String[] typeName, int index) {
+ return null;
+ }
+
+ @Override
+ void notifySuperTypes() {
+ }
+
+ @Override
+ void removeFromSupertypes() {
+ }
}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JBound.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JBound.java
new file mode 100644
index 0000000..a59fc01
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JBound.java
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ *
+ */
+public class JBound {
+
+ private final JClassType firstBound;
+ private final List<JClassType> lowerBounds = new ArrayList<JClassType>();
+ private final List<JClassType> upperBounds = new ArrayList<JClassType>();
+
+ public JBound(JClassType firstBound) {
+ this.firstBound = firstBound;
+ }
+
+ public void addLowerBound(JClassType bound) {
+ lowerBounds.add(bound);
+ }
+
+ public void addUpperBound(JClassType bound) {
+ upperBounds.add(bound);
+ }
+
+ public JClassType getFirstBound() {
+ return firstBound;
+ }
+
+ @Override
+ public String toString() {
+ return " extends " + firstBound.getParameterizedQualifiedSourceName();
+ }
+
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JClassType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JClassType.java
index 483cc3b..276a179 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JClassType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JClassType.java
@@ -16,284 +16,81 @@
package com.google.gwt.core.ext.typeinfo;
import com.google.gwt.core.ext.UnableToCompleteException;
-import com.google.gwt.dev.util.Util;
-import java.io.UnsupportedEncodingException;
import java.lang.annotation.Annotation;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
import java.util.Map;
-import java.util.Set;
-import java.util.TreeMap;
/**
* Type representing a Java class or interface type.
*/
-public class JClassType extends JType implements HasAnnotations, HasMetaData {
+public abstract class JClassType extends JType implements HasAnnotations,
+ HasMetaData {
- private final Set<JClassType> allSubtypes = new HashSet<JClassType>();
+ public abstract void addImplementedInterface(JClassType intf);
- private final Annotations annotations = new Annotations();
+ public abstract void addMetaData(String tagName, String[] values);
- private final int bodyEnd;
+ public abstract void addModifierBits(int bits);
- private final int bodyStart;
+ public abstract JConstructor findConstructor(JType[] paramTypes);
- private JMethod[] cachedOverridableMethods;
+ public abstract JField findField(String name);
- private final List<JConstructor> constructors = new ArrayList<JConstructor>();
+ public abstract JMethod findMethod(String name, JType[] paramTypes);
- private final CompilationUnitProvider cup;
+ public abstract JClassType findNestedType(String typeName);
- private final JPackage declaringPackage;
+ public abstract <T extends Annotation> T getAnnotation(
+ Class<T> annotationClass);
- private final int declEnd;
+ public abstract Annotation[] getAnnotations();
- private final int declStart;
+ public abstract int getBodyEnd();
- private final JClassType enclosingType;
+ public abstract int getBodyStart();
- private final Map<String, JField> fields = new HashMap<String, JField>();
+ public abstract CompilationUnitProvider getCompilationUnit();
- private final List<JClassType> interfaces = new ArrayList<JClassType>();
+ public abstract JConstructor getConstructor(JType[] paramTypes)
+ throws NotFoundException;
- private final boolean isInterface;
+ public abstract JConstructor[] getConstructors();
- private final boolean isLocalType;
+ public abstract Annotation[] getDeclaredAnnotations();
- private String lazyHash;
+ public abstract JClassType getEnclosingType();
- private String lazyQualifiedName;
+ public abstract JClassType getErasedType();
- private final HasMetaData metaData = new MetaData();
+ public abstract JField getField(String name);
- private final Map<String, List<JMethod>> methods = new HashMap<String, List<JMethod>>();
+ public abstract JField[] getFields();
- private int modifierBits;
+ public abstract JClassType[] getImplementedInterfaces();
- private final String name;
+ public abstract String[][] getMetaData(String tagName);
- private final String nestedName;
+ public abstract String[] getMetaDataTags();
- private final Map<String, JClassType> nestedTypes = new HashMap<String, JClassType>();
-
- private final TypeOracle oracle;
-
- private JClassType superclass;
-
- public JClassType(TypeOracle oracle, CompilationUnitProvider cup,
- JPackage declaringPackage, JClassType enclosingType, boolean isLocalType,
- String name, int declStart, int declEnd, int bodyStart, int bodyEnd,
- boolean isInterface) {
- oracle.recordTypeInCompilationUnit(cup, this);
- this.oracle = oracle;
- this.cup = cup;
- this.declaringPackage = declaringPackage;
- this.enclosingType = enclosingType;
- this.isLocalType = isLocalType;
- this.name = name;
- this.declStart = declStart;
- this.declEnd = declEnd;
- this.bodyStart = bodyStart;
- this.bodyEnd = bodyEnd;
- this.isInterface = isInterface;
- if (enclosingType == null) {
- // Add myself to my package.
- //
- declaringPackage.addType(this);
- // The nested name of a top-level class is its simple name.
- //
- nestedName = name;
- } else {
- // Add myself to my enclosing type.
- //
- enclosingType.addNestedType(this);
- // Compute my "nested name".
- //
- JClassType enclosing = enclosingType;
- String nn = name;
- do {
- nn = enclosing.getSimpleSourceName() + "." + nn;
- enclosing = enclosing.getEnclosingType();
- } while (enclosing != null);
- nestedName = nn;
- }
- }
-
- public void addAnnotations(
- Map<Class<? extends Annotation>, Annotation> declaredAnnotations) {
- annotations.addAnnotations(declaredAnnotations);
- }
-
- public void addImplementedInterface(JClassType intf) {
- assert (intf != null);
- interfaces.add(intf);
- }
-
- public void addMetaData(String tagName, String[] values) {
- metaData.addMetaData(tagName, values);
- }
-
- public void addModifierBits(int bits) {
- modifierBits |= bits;
- }
-
- public JConstructor findConstructor(JType[] paramTypes) {
- JConstructor[] ctors = getConstructors();
- for (int i = 0; i < ctors.length; i++) {
- JConstructor candidate = ctors[i];
- if (candidate.hasParamTypes(paramTypes)) {
- return candidate;
- }
- }
- return null;
- }
-
- public JField findField(String name) {
- return fields.get(name);
- }
-
- public JMethod findMethod(String name, JType[] paramTypes) {
- JMethod[] overloads = getOverloads(name);
- for (int i = 0; i < overloads.length; i++) {
- JMethod candidate = overloads[i];
- if (candidate.hasParamTypes(paramTypes)) {
- return candidate;
- }
- }
- return null;
- }
-
- public JClassType findNestedType(String typeName) {
- String[] parts = typeName.split("\\.");
- return findNestedTypeImpl(parts, 0);
- }
-
- public <T extends Annotation> T getAnnotation(Class<T> annotationClass) {
- return annotations.getAnnotation(annotationClass);
- }
-
- public Annotation[] getAnnotations() {
- return annotations.getAnnotations();
- }
-
- public int getBodyEnd() {
- return bodyEnd;
- }
-
- public int getBodyStart() {
- return bodyStart;
- }
-
- public CompilationUnitProvider getCompilationUnit() {
- return cup;
- }
-
- public JConstructor getConstructor(JType[] paramTypes)
- throws NotFoundException {
- JConstructor result = findConstructor(paramTypes);
- if (result == null) {
- throw new NotFoundException();
- }
- return result;
- }
-
- public JConstructor[] getConstructors() {
- return constructors.toArray(TypeOracle.NO_JCTORS);
- }
-
- public Annotation[] getDeclaredAnnotations() {
- return annotations.getDeclaredAnnotations();
- }
-
- public JClassType getEnclosingType() {
- return enclosingType;
- }
-
- public JField getField(String name) {
- JField field = findField(name);
- assert (field != null);
- return field;
- }
-
- public JField[] getFields() {
- return fields.values().toArray(TypeOracle.NO_JFIELDS);
- }
-
- public JClassType[] getImplementedInterfaces() {
- return interfaces.toArray(TypeOracle.NO_JCLASSES);
- }
-
- @Override
- public String getJNISignature() {
- String typeName = nestedName.replace('.', '$');
- String packageName = getPackage().getName().replace('.', '/');
- if (packageName.length() > 0) {
- packageName += "/";
- }
- return "L" + packageName + typeName + ";";
- }
-
- public String[][] getMetaData(String tagName) {
- return metaData.getMetaData(tagName);
- }
-
- public String[] getMetaDataTags() {
- return metaData.getMetaDataTags();
- }
-
- public JMethod getMethod(String name, JType[] paramTypes)
- throws NotFoundException {
- JMethod result = findMethod(name, paramTypes);
- if (result == null) {
- throw new NotFoundException();
- }
- return result;
- }
+ public abstract JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException;
/*
* Returns the declared methods of this class (not any superclasses or
* superinterfaces).
*/
- public JMethod[] getMethods() {
- List<JMethod> resultMethods = new ArrayList<JMethod>();
- for (List<JMethod> overloads : methods.values()) {
- resultMethods.addAll(overloads);
- }
- return resultMethods.toArray(TypeOracle.NO_JMETHODS);
- }
+ public abstract JMethod[] getMethods();
- public String getName() {
- return nestedName;
- }
+ public abstract String getName();
- public JClassType getNestedType(String typeName) throws NotFoundException {
- JClassType result = findNestedType(typeName);
- if (result == null) {
- throw new NotFoundException();
- }
- return result;
- }
+ public abstract JClassType getNestedType(String typeName)
+ throws NotFoundException;
- public JClassType[] getNestedTypes() {
- return nestedTypes.values().toArray(TypeOracle.NO_JCLASSES);
- }
+ public abstract JClassType[] getNestedTypes();
- public TypeOracle getOracle() {
- return oracle;
- }
+ public abstract TypeOracle getOracle();
- public JMethod[] getOverloads(String name) {
- List<?> resultMethods = methods.get(name);
- if (resultMethods != null) {
- return resultMethods.toArray(TypeOracle.NO_JMETHODS);
- } else {
- return TypeOracle.NO_JMETHODS;
- }
- }
+ public abstract JMethod[] getOverloads(String name);
/**
* Iterates over the most-derived declaration of each unique overridable
@@ -312,103 +109,24 @@
* @return an array of {@link JMethod} objects representing overridable
* methods
*/
- public JMethod[] getOverridableMethods() {
- if (cachedOverridableMethods == null) {
- Map<String, JMethod> methodsBySignature = new TreeMap<String, JMethod>();
- getOverridableMethodsOnSuperinterfacesAndMaybeThisInterface(methodsBySignature);
- if (isClass() != null) {
- getOverridableMethodsOnSuperclassesAndThisClass(methodsBySignature);
- }
- int size = methodsBySignature.size();
- Collection<JMethod> leafMethods = methodsBySignature.values();
- cachedOverridableMethods = leafMethods.toArray(new JMethod[size]);
- }
- return cachedOverridableMethods;
- }
+ public abstract JMethod[] getOverridableMethods();
- public JPackage getPackage() {
- return declaringPackage;
- }
+ public abstract JPackage getPackage();
- @Override
- public String getQualifiedSourceName() {
- if (lazyQualifiedName == null) {
- JPackage pkg = getPackage();
- if (!pkg.isDefault()) {
- lazyQualifiedName = pkg.getName() + "." + makeCompoundName(this);
- } else {
- lazyQualifiedName = makeCompoundName(this);
- }
- }
- return lazyQualifiedName;
- }
+ public abstract JClassType[] getSubtypes();
- @Override
- public String getSimpleSourceName() {
- return name;
- }
+ public abstract JClassType getSuperclass();
- public JClassType[] getSubtypes() {
- return allSubtypes.toArray(TypeOracle.NO_JCLASSES);
- }
+ public abstract String getTypeHash() throws UnableToCompleteException;
- public JClassType getSuperclass() {
- return superclass;
- }
+ public abstract boolean isAbstract();
- public String getTypeHash() throws UnableToCompleteException {
- if (lazyHash == null) {
- char[] source = cup.getSource();
- int length = declEnd - declStart + 1;
- String s = new String(source, declStart, length);
- try {
- lazyHash = Util.computeStrongName(s.getBytes(Util.DEFAULT_ENCODING));
- } catch (UnsupportedEncodingException e) {
- // Details, details...
- throw new UnableToCompleteException();
- }
- }
- return lazyHash;
- }
+ public abstract boolean isAnnotationPresent(
+ Class<? extends Annotation> annotationClass);
- public boolean isAbstract() {
- return 0 != (modifierBits & TypeOracle.MOD_ABSTRACT);
- }
+ public abstract boolean isAssignableFrom(JClassType possibleSubtype);
- public boolean isAnnotationPresent(Class<? extends Annotation> annotationClass) {
- return annotations.isAnnotationPresent(annotationClass);
- }
-
- @Override
- public JArrayType isArray() {
- // intentional null
- return null;
- }
-
- public boolean isAssignableFrom(JClassType possibleSubtype) {
- if (possibleSubtype == this) {
- return true;
- }
- if (allSubtypes.contains(possibleSubtype)) {
- return true;
- } else if (this == getOracle().getJavaLangObject()) {
- // This case handles the odd "every interface is an Object"
- // but doesn't actually have Object as a superclass.
- //
- return true;
- } else {
- return false;
- }
- }
-
- public boolean isAssignableTo(JClassType possibleSupertype) {
- return possibleSupertype.isAssignableFrom(this);
- }
-
- @Override
- public JClassType isClass() {
- return isInterface ? null : this;
- }
+ public abstract boolean isAssignableTo(JClassType possibleSupertype);
/**
* Determines if the class can be constructed using a simple <code>new</code>
@@ -422,24 +140,12 @@
* @return <code>true</code> if the type is default instantiable, or
* <code>false</code> otherwise
*/
- public boolean isDefaultInstantiable() {
- if (isInterface() != null) {
- return false;
- }
- if (constructors.isEmpty()) {
- return true;
- }
- JConstructor ctor = findConstructor(TypeOracle.NO_JTYPES);
- if (ctor != null) {
- return true;
- }
- return false;
- }
+ public abstract boolean isDefaultInstantiable();
+
+ public abstract JGenericType isGenericType();
@Override
- public JClassType isInterface() {
- return isInterface ? this : null;
- }
+ public abstract JClassType isInterface();
/**
* Tests if this type is a local type (within a method).
@@ -447,9 +153,7 @@
* @return true if this type is a local type, whether it is named or
* anonymous.
*/
- public boolean isLocalType() {
- return isLocalType;
- }
+ public abstract boolean isLocalType();
/**
* Tests if this type is contained within another type.
@@ -457,148 +161,29 @@
* @return true if this type has an enclosing type, false if this type is a
* top-level type
*/
- public boolean isMemberType() {
- return enclosingType != null;
- }
+ public abstract boolean isMemberType();
- @Override
- public JParameterizedType isParameterized() {
- // intentional null
- return null;
- }
+ public abstract boolean isPrivate();
- @Override
- public JPrimitiveType isPrimitive() {
- // intentional null
- return null;
- }
+ public abstract boolean isProtected();
- public boolean isPrivate() {
- return 0 != (modifierBits & TypeOracle.MOD_PRIVATE);
- }
+ public abstract boolean isPublic();
- public boolean isProtected() {
- return 0 != (modifierBits & TypeOracle.MOD_PROTECTED);
- }
+ public abstract boolean isStatic();
- public boolean isPublic() {
- return 0 != (modifierBits & TypeOracle.MOD_PUBLIC);
- }
-
- public boolean isStatic() {
- return 0 != (modifierBits & TypeOracle.MOD_STATIC);
- }
-
- public void setSuperclass(JClassType type) {
- assert (type != null);
- assert (isInterface() == null);
- this.superclass = type;
- annotations.setParent(type.annotations);
- }
+ public abstract void setSuperclass(JClassType type);
@Override
public String toString() {
- if (isInterface) {
- return "interface " + getQualifiedSourceName();
- } else {
- return "class " + getQualifiedSourceName();
- }
+ return this.getQualifiedSourceName();
}
- protected int getModifierBits() {
- return modifierBits;
- }
+ protected abstract void acceptSubtype(JClassType me);
- void addConstructor(JConstructor ctor) {
- assert (!constructors.contains(ctor));
- constructors.add(ctor);
- }
+ protected abstract int getModifierBits();
- void addField(JField field) {
- Object existing = fields.put(field.getName(), field);
- assert (existing == null);
- }
-
- void addMethod(JMethod method) {
- String methodName = method.getName();
- List<JMethod> overloads = methods.get(methodName);
- if (overloads == null) {
- overloads = new ArrayList<JMethod>();
- methods.put(methodName, overloads);
- }
- overloads.add(method);
- }
-
- void addNestedType(JClassType type) {
- nestedTypes.put(type.getSimpleSourceName(), type);
- }
-
- JClassType findNestedTypeImpl(String[] typeName, int index) {
- JClassType found = nestedTypes.get(typeName[index]);
- if (found == null) {
- return null;
- } else if (index < typeName.length - 1) {
- return found.findNestedTypeImpl(typeName, index + 1);
- } else {
- return found;
- }
- }
-
- void notifySuperTypes() {
- notifySuperTypesOf(this);
- }
-
- /**
- * Removes references to this instance from all of its super types.
- */
- void removeFromSupertypes() {
- removeSubtype(this);
- }
-
- private void acceptSubtype(JClassType me) {
- allSubtypes.add(me);
- notifySuperTypesOf(me);
- }
-
- private String computeInternalSignature(JMethod method) {
- StringBuffer sb = new StringBuffer();
- sb.setLength(0);
- sb.append(method.getName());
- JParameter[] params = method.getParameters();
- for (int j = 0; j < params.length; j++) {
- JParameter param = params[j];
- sb.append("/");
- sb.append(param.getType().getQualifiedSourceName());
- }
- return sb.toString();
- }
-
- private void getOverridableMethodsOnSuperclassesAndThisClass(
- Map<String, JMethod> methodsBySignature) {
- assert (isClass() != null);
-
- // Recurse first so that more derived methods will clobber less derived
- // methods.
- JClassType superClass = getSuperclass();
- if (superClass != null) {
- superClass.getOverridableMethodsOnSuperclassesAndThisClass(methodsBySignature);
- }
-
- JMethod[] declaredMethods = getMethods();
- for (int i = 0; i < declaredMethods.length; i++) {
- JMethod method = declaredMethods[i];
-
- // Ensure that this method is overridable.
- if (method.isFinal() || method.isPrivate()) {
- // We cannot override this method, so skip it.
- continue;
- }
-
- // We can override this method, so record it.
- String sig = computeInternalSignature(method);
- methodsBySignature.put(sig, method);
- }
- }
+ protected abstract void getOverridableMethodsOnSuperclassesAndThisClass(
+ Map<String, JMethod> methodsBySignature);
/**
* Gets the methods declared in interfaces that this type extends. If this
@@ -608,72 +193,40 @@
*
* @param methodsBySignature
*/
- private void getOverridableMethodsOnSuperinterfacesAndMaybeThisInterface(
- Map<String, JMethod> methodsBySignature) {
- // Recurse first so that more derived methods will clobber less derived
- // methods.
- JClassType[] superIntfs = getImplementedInterfaces();
- for (int i = 0; i < superIntfs.length; i++) {
- JClassType superIntf = superIntfs[i];
- superIntf.getOverridableMethodsOnSuperinterfacesAndMaybeThisInterface(methodsBySignature);
- }
+ protected abstract void getOverridableMethodsOnSuperinterfacesAndMaybeThisInterface(
+ Map<String, JMethod> methodsBySignature);
- if (isInterface() == null) {
- // This is not an interface, so we're done after having visited its
- // implemented interfaces.
- return;
- }
-
- JMethod[] declaredMethods = getMethods();
- for (int i = 0; i < declaredMethods.length; i++) {
- JMethod method = declaredMethods[i];
-
- String sig = computeInternalSignature(method);
- JMethod existing = methodsBySignature.get(sig);
- if (existing != null) {
- JClassType existingType = existing.getEnclosingType();
- JClassType thisType = method.getEnclosingType();
- if (thisType.isAssignableFrom(existingType)) {
- // The existing method is in a more-derived type, so don't replace it.
- continue;
- }
- }
- methodsBySignature.put(sig, method);
- }
- }
-
- private String makeCompoundName(JClassType type) {
- if (type.enclosingType == null) {
- return type.name;
+ protected final String makeCompoundName(JClassType type) {
+ if (type.getEnclosingType() == null) {
+ return type.getSimpleSourceName();
} else {
- return makeCompoundName(type.enclosingType) + "." + type.name;
+ return makeCompoundName(type.getEnclosingType()) + "."
+ + type.getSimpleSourceName();
}
}
/**
* Tells this type's superclasses and superinterfaces about it.
*/
- private void notifySuperTypesOf(JClassType me) {
- if (superclass != null) {
- superclass.acceptSubtype(me);
- }
- for (int i = 0, n = interfaces.size(); i < n; ++i) {
- JClassType intf = interfaces.get(i);
- intf.acceptSubtype(me);
- }
- }
+ protected abstract void notifySuperTypesOf(JClassType me);
- private void removeSubtype(JClassType me) {
- allSubtypes.remove(me);
+ protected abstract void removeSubtype(JClassType me);
- if (superclass != null) {
- superclass.removeSubtype(me);
- }
+ abstract void addConstructor(JConstructor ctor);
- for (int i = 0, n = interfaces.size(); i < n; ++i) {
- JClassType intf = interfaces.get(i);
+ abstract void addField(JField field);
- intf.removeSubtype(me);
- }
- }
+ abstract void addMethod(JMethod method);
+
+ abstract void addNestedType(JClassType type);
+
+ abstract JClassType findNestedTypeImpl(String[] typeName, int index);
+
+ abstract void notifySuperTypes();
+
+ /**
+ * Removes references to this instance from all of its super types.
+ */
+ abstract void removeFromSupertypes();
+
}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JConstructor.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JConstructor.java
index f3ae15c..feb2044 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JConstructor.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JConstructor.java
@@ -34,7 +34,7 @@
Map<Class<? extends Annotation>, Annotation> declaredAnnotations) {
super(name, declStart, declEnd, bodyStart, bodyEnd, declaredAnnotations);
this.enclosingType = enclosingType;
- enclosingType.addConstructor(this);
+ enclosingType.addConstructor(this);
}
public JClassType getEnclosingType() {
@@ -43,11 +43,15 @@
public String getReadableDeclaration() {
String[] names = TypeOracle.modifierBitsToNames(getModifierBits());
- StringBuffer sb = new StringBuffer();
+ StringBuilder sb = new StringBuilder();
for (int i = 0; i < names.length; i++) {
sb.append(names[i]);
sb.append(" ");
}
+ if (getTypeParameters().length > 0) {
+ toStringTypeParams(sb);
+ sb.append(" ");
+ }
sb.append(getName());
toStringParamsAndThrows(sb);
return sb.toString();
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericMethod.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericMethod.java
new file mode 100644
index 0000000..9d7956f
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericMethod.java
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+/**
+ *
+ */
+public class JGenericMethod {
+
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericType.java
new file mode 100644
index 0000000..c49ef9b
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JGenericType.java
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ *
+ */
+public class JGenericType extends JRealClassType implements HasTypeParameters {
+ private JRawType lazyRawType = null;
+ private final List<JTypeParameter> typeParams = new ArrayList<JTypeParameter>();
+
+ public JGenericType(TypeOracle oracle, CompilationUnitProvider cup,
+ JPackage declaringPackage, JClassType enclosingType, boolean isLocalType,
+ String name, int declStart, int declEnd, int bodyStart, int bodyEnd,
+ boolean isInterface) {
+ super(oracle, cup, declaringPackage, enclosingType, isLocalType, name,
+ declStart, declEnd, bodyStart, bodyEnd, isInterface);
+ }
+
+ @Override
+ public JClassType getErasedType() {
+ return getRawType();
+ }
+
+ @Override
+ public String getParameterizedQualifiedSourceName() {
+ StringBuffer sb = new StringBuffer();
+ sb.append(getQualifiedSourceName());
+
+ sb.append('<');
+ boolean needComma = false;
+ for (JClassType typeParam : typeParams) {
+ if (needComma) {
+ sb.append(", ");
+ } else {
+ needComma = true;
+ }
+ sb.append(typeParam.getParameterizedQualifiedSourceName());
+ }
+ sb.append('>');
+ return sb.toString();
+ }
+
+ public JRawType getRawType() {
+ if (lazyRawType == null) {
+ lazyRawType = new JRawType(this);
+ }
+ return lazyRawType;
+ }
+
+ public JTypeParameter[] getTypeParameters() {
+ return typeParams.toArray(new JTypeParameter[typeParams.size()]);
+ }
+
+ @Override
+ public JGenericType isGenericType() {
+ return this;
+ }
+
+ void addTypeParameter(JTypeParameter typeParameter) {
+ typeParams.add(typeParameter);
+ }
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JMethod.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JMethod.java
index 2eaeaa2..6afd46f 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JMethod.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JMethod.java
@@ -112,11 +112,15 @@
String getReadableDeclaration(int modifierBits) {
String[] names = TypeOracle.modifierBitsToNames(modifierBits);
- StringBuffer sb = new StringBuffer();
+ StringBuilder sb = new StringBuilder();
for (int i = 0; i < names.length; i++) {
sb.append(names[i]);
sb.append(" ");
}
+ if (getTypeParameters().length > 0) {
+ toStringTypeParams(sb);
+ sb.append(" ");
+ }
sb.append(returnType.getParameterizedQualifiedSourceName());
sb.append(" ");
sb.append(getName());
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedMethod.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedMethod.java
new file mode 100644
index 0000000..c161df2
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedMethod.java
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+/**
+ *
+ */
+public class JParameterizedMethod {
+
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedType.java
index 7b2e0ae..ed82ba9 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JParameterizedType.java
@@ -21,38 +21,68 @@
/**
* Represents a parameterized type in a declaration.
*/
-public class JParameterizedType extends JType {
+public class JParameterizedType extends JDelegatingClassType {
- private final JClassType parameterized;
+ private final List<JClassType> typeArgs = new ArrayList<JClassType>();
- private final List<JType> typeArgs = new ArrayList<JType>();
+ JParameterizedType(JGenericType baseType) {
+ super.setBaseType(baseType);
+ }
- JParameterizedType(JClassType parameterized) {
- this.parameterized = parameterized;
+ @Override
+ public JField findField(String name) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JMethod findMethod(String name, JType[] paramTypes) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ public JGenericType getBaseType() {
+ return (JGenericType) baseType;
+ }
+
+ @Override
+ public JField getField(String name) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JField[] getFields() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JMethod[] getMethods() {
+ // TODO Auto-generated method stub
+ return null;
}
/**
- * The signature of the raw type.
+ * @deprecated see {@link #getQualifiedSourceName()}
*/
- public String getJNISignature() {
- return getRawType().getJNISignature();
- }
-
- public JType getLeafType() {
- return parameterized;
- }
-
- /*
- * Get the name of this type without all of the parameterized information
- */
+ @Deprecated
public String getNonParameterizedQualifiedSourceName() {
- return parameterized.getQualifiedSourceName();
+ return getQualifiedSourceName();
}
@Override
public String getParameterizedQualifiedSourceName() {
StringBuffer sb = new StringBuffer();
- sb.append(parameterized.getQualifiedSourceName());
+ sb.append(getQualifiedSourceName());
+
sb.append('<');
boolean needComma = false;
for (JType typeArg : typeArgs) {
@@ -72,46 +102,42 @@
* signature.
*/
public String getQualifiedSourceName() {
- return parameterized.getQualifiedSourceName();
+ return getBaseType().getQualifiedSourceName();
}
public JClassType getRawType() {
- return parameterized;
+ return getBaseType().getRawType();
}
/**
* In this case, the raw type name.
*/
public String getSimpleSourceName() {
- return parameterized.getSimpleSourceName();
+ return getRawType().getSimpleSourceName();
}
- public JType[] getTypeArgs() {
- return (JType[]) typeArgs.toArray(TypeOracle.NO_JTYPES);
+ public JClassType[] getTypeArgs() {
+ return typeArgs.toArray(TypeOracle.NO_JCLASSES);
}
- public JArrayType isArray() {
+ @Override
+ public JGenericType isGenericType() {
return null;
}
- public JClassType isClass() {
- return parameterized.isClass();
- }
-
- public JClassType isInterface() {
- return parameterized.isInterface();
- }
-
+ @Override
public JParameterizedType isParameterized() {
return this;
}
- public JPrimitiveType isPrimitive() {
+ @Override
+ public JRawType isRawType() {
return null;
}
- void addTypeArg(JType type) {
+ void addTypeArg(JClassType type) {
assert (type.isPrimitive() == null);
typeArgs.add(type);
}
+
}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JPrimitiveType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JPrimitiveType.java
index 6719d29..fbbb82c 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JPrimitiveType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JPrimitiveType.java
@@ -63,6 +63,11 @@
}
@Override
+ public JType getErasedType() {
+ return this;
+ }
+
+ @Override
public String getJNISignature() {
return jni;
}
@@ -105,4 +110,10 @@
public JPrimitiveType isPrimitive() {
return this;
}
+
+ @Override
+ public JRawType isRawType() {
+ // intentional null
+ return null;
+ }
}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JRawType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JRawType.java
new file mode 100644
index 0000000..7779711
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JRawType.java
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+/**
+ *
+ */
+public class JRawType extends JDelegatingClassType {
+
+ public JRawType(JGenericType genericType) {
+ super.setBaseType(genericType);
+ }
+
+ @Override
+ public JField findField(String name) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JMethod findMethod(String name, JType[] paramTypes) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ public JGenericType getBaseType() {
+ return (JGenericType) baseType;
+ }
+
+ @Override
+ public JField getField(String name) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JField[] getFields() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ public JGenericType getGenericType() {
+ return getBaseType();
+ }
+
+ @Override
+ public JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public JMethod[] getMethods() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public String getParameterizedQualifiedSourceName() {
+ return getQualifiedSourceName();
+ }
+
+ @Override
+ public String getQualifiedSourceName() {
+ return baseType.getQualifiedSourceName();
+ }
+
+ @Override
+ public String getSimpleSourceName() {
+ return baseType.getSimpleSourceName();
+ }
+
+ @Override
+ public JGenericType isGenericType() {
+ return null;
+ }
+
+ @Override
+ public JParameterizedType isParameterized() {
+ return null;
+ }
+
+ @Override
+ public JRawType isRawType() {
+ return this;
+ }
+
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JType.java
index 24ab78b..2ed4aad 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/JType.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JType.java
@@ -19,6 +19,9 @@
* Abstract superclass for types.
*/
public abstract class JType {
+
+ public abstract JType getErasedType();
+
public abstract String getJNISignature();
public JType getLeafType() {
@@ -61,4 +64,7 @@
public abstract JParameterizedType isParameterized();
public abstract JPrimitiveType isPrimitive();
+
+ public abstract JRawType isRawType();
+
}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JTypeParameter.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JTypeParameter.java
new file mode 100644
index 0000000..cfea518
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JTypeParameter.java
@@ -0,0 +1,132 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+/**
+ * Represents one of the type parameters in a generic type.
+ */
+public class JTypeParameter extends JDelegatingClassType implements HasBounds {
+ private JBound bounds;
+ private final JGenericType declaringClass;
+ private final JAbstractMethod declaringMethod;
+ private final String typeName;
+
+ public JTypeParameter(String typeName, JAbstractMethod declaringMethod) {
+ this.typeName = typeName;
+ this.declaringMethod = declaringMethod;
+ this.declaringClass = null;
+ declaringMethod.addTypeParameter(this);
+ }
+
+ public JTypeParameter(String typeName, JGenericType declaringClass) {
+ this.typeName = typeName;
+ this.declaringClass = declaringClass;
+ this.declaringMethod = null;
+ declaringClass.addTypeParameter(this);
+ }
+
+ @Override
+ public JField findField(String name) {
+ return baseType.findField(name);
+ }
+
+ @Override
+ public JMethod findMethod(String name, JType[] paramTypes) {
+ return baseType.findMethod(name, paramTypes);
+ }
+
+ public JBound getBounds() {
+ return bounds;
+ }
+
+ public JRealClassType getDeclaringClass() {
+ return declaringClass;
+ }
+
+ @Override
+ public JField getField(String name) {
+ return baseType.getField(name);
+ }
+
+ @Override
+ public JField[] getFields() {
+ return baseType.getFields();
+ }
+
+ public JClassType getFirstBound() {
+ return baseType;
+ }
+
+ @Override
+ public JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException {
+ return baseType.getMethod(name, paramTypes);
+ }
+
+ @Override
+ public JMethod[] getMethods() {
+ return baseType.getMethods();
+ }
+
+ @Override
+ public String getName() {
+ return typeName;
+ }
+
+ @Override
+ public String getParameterizedQualifiedSourceName() {
+ return typeName;
+ }
+
+ @Override
+ public String getQualifiedSourceName() {
+ return typeName;
+ }
+
+ @Override
+ public String getSimpleSourceName() {
+ return typeName;
+ }
+
+ @Override
+ public JGenericType isGenericType() {
+ return null;
+ }
+
+ @Override
+ public JParameterizedType isParameterized() {
+ return null;
+ }
+
+ @Override
+ public JRawType isRawType() {
+ return null;
+ }
+
+ public void setBounds(JBound bounds) {
+ this.bounds = bounds;
+ super.setBaseType(bounds.getFirstBound());
+ }
+
+ @Override
+ public String toString() {
+ if (baseType.isInterface() != null) {
+ return "interface " + getQualifiedSourceName();
+ } else {
+ return "class " + getQualifiedSourceName();
+ }
+ }
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/JWildcardType.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/JWildcardType.java
new file mode 100644
index 0000000..2cece8a
--- /dev/null
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/JWildcardType.java
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+/**
+ * Represents a wildcard type argument to a parameterized type.
+ */
+public class JWildcardType extends JDelegatingClassType implements HasBounds {
+
+ private final JBound bounds;
+
+ public JWildcardType(JBound bounds) {
+ this.bounds = bounds;
+ super.setBaseType(bounds.getFirstBound());
+ }
+
+ @Override
+ public JField findField(String name) {
+ return baseType.findField(name);
+ }
+
+ @Override
+ public JMethod findMethod(String name, JType[] paramTypes) {
+ return baseType.findMethod(name, paramTypes);
+ }
+
+ public JBound getBounds() {
+ return bounds;
+ }
+
+ @Override
+ public JField getField(String name) {
+ return baseType.getField(name);
+ }
+
+ @Override
+ public JField[] getFields() {
+ return baseType.getFields();
+ }
+
+ public JClassType getFirstBound() {
+ return baseType;
+ }
+
+ @Override
+ public JMethod getMethod(String name, JType[] paramTypes)
+ throws NotFoundException {
+ return baseType.getMethod(name, paramTypes);
+ }
+
+ @Override
+ public JMethod[] getMethods() {
+ return baseType.getMethods();
+ }
+
+ @Override
+ public String getQualifiedSourceName() {
+ return "?";
+ }
+
+ @Override
+ public String getSimpleSourceName() {
+ return "?";
+ }
+
+ @Override
+ public JGenericType isGenericType() {
+ return null;
+ }
+
+ @Override
+ public JParameterizedType isParameterized() {
+ return null;
+ }
+
+ @Override
+ public JRawType isRawType() {
+ return null;
+ }
+}
diff --git a/dev/core/src/com/google/gwt/core/ext/typeinfo/TypeOracle.java b/dev/core/src/com/google/gwt/core/ext/typeinfo/TypeOracle.java
index 0c0f52c..d657e71 100644
--- a/dev/core/src/com/google/gwt/core/ext/typeinfo/TypeOracle.java
+++ b/dev/core/src/com/google/gwt/core/ext/typeinfo/TypeOracle.java
@@ -18,6 +18,7 @@
import com.google.gwt.core.ext.TreeLogger;
import com.google.gwt.core.ext.UnableToCompleteException;
+import java.lang.annotation.Annotation;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
@@ -70,6 +71,7 @@
static final int MOD_TRANSIENT = 0x00000080;
static final int MOD_VOLATILE = 0x00000100;
+ static final Annotation[] NO_ANNOTATIONS = new Annotation[0];
static final JClassType[] NO_JCLASSES = new JClassType[0];
static final JConstructor[] NO_JCTORS = new JConstructor[0];
static final JField[] NO_JFIELDS = new JField[0];
@@ -146,7 +148,7 @@
Set<JClassType> invalidTypes) {
if (type instanceof JParameterizedType) {
JParameterizedType parameterizedType = (JParameterizedType) type;
- if (isInvalidatedTypeRecursive(parameterizedType.getRawType(),
+ if (isInvalidatedTypeRecursive(parameterizedType.getBaseType(),
invalidTypes)) {
return true;
}
@@ -248,13 +250,13 @@
* calls to this method with the same argument return the same object.
*
* @param componentType the component type of the array, which can itself be
- * an array type
+ * an array type
* @return a type object representing an array of the component type
*/
public JArrayType getArrayType(JType componentType) {
JArrayType arrayType = arrayTypes.get(componentType);
if (arrayType == null) {
- arrayType = new JArrayType(componentType);
+ arrayType = new JArrayType(componentType, this);
arrayTypes.put(componentType, arrayType);
}
return arrayType;
@@ -317,17 +319,16 @@
* has a stable identity so as to guarantee that all calls to this method with
* the same arguments return the same object.
*
- * @param rawType the raw type of the array, which must be a class or
- * interface type and cannot be a primitive, array, or another
- * parameterized type
- * @param typeArgs the type arguments bound to the specified raw type
+ * @param genericType a generic base class
+ * @param typeArgs the type arguments bound to the specified generic type
* @return a type object representing this particular binding of type
- * arguments to the specified raw type
+ * arguments to the specified generic
*/
- public JType getParameterizedType(JClassType rawType, JType[] typeArgs) {
+ public JParameterizedType getParameterizedType(JGenericType genericType,
+ JClassType[] typeArgs) {
// Uses the generated string signature to intern parameterized types.
//
- JParameterizedType parameterized = new JParameterizedType(rawType);
+ JParameterizedType parameterized = new JParameterizedType(genericType);
for (int i = 0; i < typeArgs.length; i++) {
parameterized.addTypeArg(typeArgs[i]);
}
@@ -750,7 +751,7 @@
String rawTypeName = type.substring(0, bracket);
JType rawType = parseImpl(rawTypeName);
if (rawType.isParameterized() != null) {
- // The raw type cannot itself be parmeterized.
+ // The raw type cannot itself be parameterized.
//
throw new BadTypeArgsException(
"Only non-parameterized classes and interface can be parameterized");
@@ -767,11 +768,12 @@
// Resolve each type argument.
//
String typeArgContents = type.substring(bracket + 1, type.length() - 1);
- JType[] typeArgs = parseTypeArgContents(typeArgContents);
+ JClassType[] typeArgs = parseTypeArgContents(typeArgContents);
// Intern this type.
//
- return getParameterizedType(rawType.isClassOrInterface(), typeArgs);
+ return getParameterizedType(rawType.isClassOrInterface().isGenericType(),
+ typeArgs);
}
JType result = JPrimitiveType.valueOf(type);
@@ -787,7 +789,7 @@
throw new NotFoundException(type);
}
- private void parseTypeArgComponent(List<JType> typeArgList,
+ private void parseTypeArgComponent(List<JClassType> typeArgList,
String typeArgComponent) throws NotFoundException, ParseException,
BadTypeArgsException {
JType typeArg = parseImpl(typeArgComponent);
@@ -799,16 +801,16 @@
+ " cannot be used in this context");
}
- typeArgList.add(typeArg);
+ typeArgList.add((JClassType) typeArg);
}
/**
* Returns an array of types specified inside of a gwt.typeArgs javadoc
* annotation.
*/
- private JType[] parseTypeArgContents(String typeArgContents)
+ private JClassType[] parseTypeArgContents(String typeArgContents)
throws ParseException, NotFoundException, BadTypeArgsException {
- List<JType> typeArgList = new ArrayList<JType>();
+ List<JClassType> typeArgList = new ArrayList<JClassType>();
int start = 0;
for (int offset = 0, length = typeArgContents.length(); offset < length; ++offset) {
@@ -845,7 +847,7 @@
String typeArgComponent = typeArgContents.substring(start);
parseTypeArgComponent(typeArgList, typeArgComponent);
- JType[] typeArgs = typeArgList.toArray(new JType[typeArgList.size()]);
+ JClassType[] typeArgs = typeArgList.toArray(new JClassType[typeArgList.size()]);
return typeArgs;
}
diff --git a/dev/core/src/com/google/gwt/dev/GWTShell.java b/dev/core/src/com/google/gwt/dev/GWTShell.java
index e8a34ac..acd2103 100644
--- a/dev/core/src/com/google/gwt/dev/GWTShell.java
+++ b/dev/core/src/com/google/gwt/dev/GWTShell.java
@@ -66,22 +66,27 @@
*/
protected class ArgHandlerBlacklist extends ArgHandlerString {
+ @Override
public String[] getDefaultArgs() {
return new String[] {"-blacklist", ""};
}
+ @Override
public String getPurpose() {
return "Prevents the user browsing URLs that match the specified regexes (comma or space separated)";
}
+ @Override
public String getTag() {
return "-blacklist";
}
+ @Override
public String[] getTagArgs() {
return new String[] {"blacklist-string"};
}
+ @Override
public boolean setString(String blacklistStr) {
return BrowserWidgetHostChecker.blacklistRegexes(blacklistStr);
}
@@ -91,14 +96,17 @@
* handles the -noserver command line flag.
*/
protected class ArgHandlerNoServerFlag extends ArgHandlerFlag {
+ @Override
public String getPurpose() {
return "Prevents the embedded Tomcat server from running, even if a port is specified";
}
+ @Override
public String getTag() {
return "-noserver";
}
+ @Override
public boolean setFlag() {
runTomcat = false;
return true;
@@ -110,22 +118,27 @@
*/
protected class ArgHandlerPort extends ArgHandlerString {
+ @Override
public String[] getDefaultArgs() {
return new String[] {"-port", "8888"};
}
+ @Override
public String getPurpose() {
return "Runs an embedded Tomcat instance on the specified port (defaults to 8888)";
}
+ @Override
public String getTag() {
return "-port";
}
+ @Override
public String[] getTagArgs() {
return new String[] {"port-number | \"auto\""};
}
+ @Override
public boolean setString(String value) {
if (value.equals("auto")) {
port = 0;
@@ -143,19 +156,43 @@
}
/**
+ * handles the -saveJsni command line flag.
+ */
+ protected class ArgHandlerSaveJsni extends ArgHandlerFlag {
+ @Override
+ public String getPurpose() {
+ return "Save generated JSNI source in the supplied gen directory (if any)";
+ }
+
+ @Override
+ public String getTag() {
+ return "-saveJsni";
+ }
+
+ @Override
+ public boolean setFlag() {
+ saveJsni = true;
+ return true;
+ }
+ }
+
+ /**
* Handles the list of startup urls that can be passed on the command line.
*/
protected class ArgHandlerStartupURLs extends ArgHandlerExtra {
+ @Override
public boolean addExtraArg(String arg) {
addStartupURL(arg);
return true;
}
+ @Override
public String getPurpose() {
return "Automatically launches the specified URL";
}
+ @Override
public String[] getTagArgs() {
return new String[] {"url"};
}
@@ -166,22 +203,27 @@
*/
protected class ArgHandlerWhitelist extends ArgHandlerString {
+ @Override
public String[] getDefaultArgs() {
return new String[] {"-whitelist", ""};
}
+ @Override
public String getPurpose() {
return "Allows the user to browse URLs that match the specified regexes (comma or space separated)";
}
+ @Override
public String getTag() {
return "-whitelist";
}
+ @Override
public String[] getTagArgs() {
return new String[] {"whitelist-string"};
}
+ @Override
public boolean setString(String whitelistStr) {
return BrowserWidgetHostChecker.whitelistRegexes(whitelistStr);
}
@@ -331,28 +373,30 @@
private BrowserWidgetHostImpl browserHost = new BrowserWidgetHostImpl();
- private ShellMainWindow mainWnd;
-
- private boolean runTomcat = true;
-
private final List<Shell> browserShells = new ArrayList<Shell>();
- private final List<String> startupUrls = new ArrayList<String>();
-
private File genDir;
private boolean headlessMode = false;
private TreeLogger.Type logLevel;
+ private ShellMainWindow mainWnd;
+
private boolean obfuscate;
private int port;
private boolean prettyNames;
+ private boolean runTomcat = true;
+
+ private boolean saveJsni = false;
+
private boolean started;
+ private final List<String> startupUrls = new ArrayList<String>();
+
public GWTShell() {
this(false, false);
}
@@ -364,45 +408,55 @@
registerHandler(new ArgHandlerNoServerFlag());
}
+ registerHandler(new ArgHandlerSaveJsni());
registerHandler(new ArgHandlerWhitelist());
registerHandler(new ArgHandlerBlacklist());
registerHandler(new ArgHandlerLogLevel() {
+ @Override
public String[] getDefaultArgs() {
return new String[] {getTag(), doGetDefaultLogLevel()};
}
+ @Override
public void setLogLevel(Type level) {
logLevel = level;
}
});
registerHandler(new ArgHandlerGenDir() {
+ @Override
public void setDir(File dir) {
genDir = dir;
}
});
+ registerHandler(new ArgHandlerSaveJsni());
+
if (!noURLs) {
registerHandler(new ArgHandlerStartupURLs());
}
registerHandler(new ArgHandlerOutDir() {
+ @Override
public void setDir(File dir) {
outDir = dir;
}
});
registerHandler(new ArgHandlerScriptStyle() {
+ @Override
public void setStyleDetailed() {
obfuscate = false;
prettyNames = false;
}
+ @Override
public void setStyleObfuscated() {
obfuscate = true;
}
+ @Override
public void setStylePretty() {
obfuscate = false;
prettyNames = true;
@@ -416,7 +470,7 @@
public void closeAllBrowserWindows() {
while (!browserShells.isEmpty()) {
- ((Shell) browserShells.get(0)).dispose();
+ browserShells.get(0).dispose();
}
}
@@ -612,7 +666,7 @@
TreeLogger logger, TypeOracle typeOracle, ModuleDef moduleDef,
File genDir, File outDir) {
return new ShellModuleSpaceHost(logger, typeOracle, moduleDef, genDir,
- outDir);
+ outDir, saveJsni);
}
/**
diff --git a/dev/core/src/com/google/gwt/dev/jdt/TypeOracleBuilder.java b/dev/core/src/com/google/gwt/dev/jdt/TypeOracleBuilder.java
index 9c80e86..8fe6503 100644
--- a/dev/core/src/com/google/gwt/dev/jdt/TypeOracleBuilder.java
+++ b/dev/core/src/com/google/gwt/dev/jdt/TypeOracleBuilder.java
@@ -23,15 +23,20 @@
import com.google.gwt.core.ext.typeinfo.JAnnotationMethod;
import com.google.gwt.core.ext.typeinfo.JAnnotationType;
import com.google.gwt.core.ext.typeinfo.JArrayType;
+import com.google.gwt.core.ext.typeinfo.JBound;
import com.google.gwt.core.ext.typeinfo.JClassType;
import com.google.gwt.core.ext.typeinfo.JConstructor;
import com.google.gwt.core.ext.typeinfo.JField;
+import com.google.gwt.core.ext.typeinfo.JGenericType;
import com.google.gwt.core.ext.typeinfo.JMethod;
import com.google.gwt.core.ext.typeinfo.JPackage;
import com.google.gwt.core.ext.typeinfo.JParameter;
import com.google.gwt.core.ext.typeinfo.JParameterizedType;
import com.google.gwt.core.ext.typeinfo.JPrimitiveType;
+import com.google.gwt.core.ext.typeinfo.JRealClassType;
import com.google.gwt.core.ext.typeinfo.JType;
+import com.google.gwt.core.ext.typeinfo.JTypeParameter;
+import com.google.gwt.core.ext.typeinfo.JWildcardType;
import com.google.gwt.core.ext.typeinfo.TypeOracle;
import com.google.gwt.dev.util.Empty;
import com.google.gwt.dev.util.Util;
@@ -63,11 +68,15 @@
import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
import org.eclipse.jdt.internal.compiler.ast.NullLiteral;
import org.eclipse.jdt.internal.compiler.ast.NumberLiteral;
+import org.eclipse.jdt.internal.compiler.ast.ParameterizedQualifiedTypeReference;
+import org.eclipse.jdt.internal.compiler.ast.ParameterizedSingleTypeReference;
import org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference;
import org.eclipse.jdt.internal.compiler.ast.StringLiteral;
import org.eclipse.jdt.internal.compiler.ast.TrueLiteral;
import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
+import org.eclipse.jdt.internal.compiler.ast.TypeParameter;
import org.eclipse.jdt.internal.compiler.ast.TypeReference;
+import org.eclipse.jdt.internal.compiler.ast.Wildcard;
import org.eclipse.jdt.internal.compiler.env.ICompilationUnit;
import org.eclipse.jdt.internal.compiler.env.IGenericType;
import org.eclipse.jdt.internal.compiler.lookup.ArrayBinding;
@@ -85,6 +94,7 @@
import org.eclipse.jdt.internal.compiler.lookup.TypeBinding;
import org.eclipse.jdt.internal.compiler.lookup.TypeIds;
import org.eclipse.jdt.internal.compiler.lookup.TypeVariableBinding;
+import org.eclipse.jdt.internal.compiler.lookup.WildcardBinding;
import java.io.BufferedReader;
import java.io.CharArrayReader;
@@ -140,7 +150,7 @@
JParameterizedType parameterizedType = type.isParameterized();
if (parameterizedType != null) {
- return computeBinaryClassName(parameterizedType.getRawType());
+ return computeBinaryClassName(parameterizedType.getBaseType());
}
JClassType classType = type.isClassOrInterface();
@@ -488,6 +498,46 @@
cud.traverse(new ASTVisitor() {
@Override
+ public boolean visit(
+ ParameterizedQualifiedTypeReference parameterizedQualifiedTypeReference,
+ BlockScope scope) {
+ ParameterizedTypeBinding jparameterizedType = (ParameterizedTypeBinding) parameterizedQualifiedTypeReference.resolvedType;
+ processParameterizedType(jparameterizedType);
+ return true; // do nothing by default, keep traversing
+ }
+
+ @Override
+ public boolean visit(
+ ParameterizedQualifiedTypeReference parameterizedQualifiedTypeReference,
+ ClassScope scope) {
+ ParameterizedTypeBinding jparameterizedType = (ParameterizedTypeBinding) parameterizedQualifiedTypeReference.resolvedType;
+ processParameterizedType(jparameterizedType);
+ return true; // do nothing by default, keep traversing
+ }
+
+ @Override
+ public boolean visit(
+ ParameterizedSingleTypeReference parameterizedSingleTypeReference,
+ BlockScope scope) {
+ if (parameterizedSingleTypeReference.resolvedType instanceof ParameterizedTypeBinding) {
+ ParameterizedTypeBinding jparameterizedType = (ParameterizedTypeBinding) parameterizedSingleTypeReference.resolvedType;
+ processParameterizedType(jparameterizedType);
+ } else if (parameterizedSingleTypeReference.resolvedType instanceof SourceTypeBinding) {
+ // nothing to do
+ } else {
+ assert false;
+ }
+ return true; // do nothing by default, keep traversing
+ }
+
+ @Override
+ public boolean visit(
+ ParameterizedSingleTypeReference parameterizedSingleTypeReference,
+ ClassScope scope) {
+ return true; // do nothing by default, keep traversing
+ }
+
+ @Override
public boolean visit(TypeDeclaration typeDecl, BlockScope scope) {
JClassType enclosingType = identityMapper.get(typeDecl.binding.enclosingType());
processType(typeDecl, enclosingType, true);
@@ -507,6 +557,7 @@
processType(typeDecl, null, false);
return true;
}
+
}, cud.scope);
}
@@ -558,6 +609,22 @@
return oracle;
}
+ private JBound createTypeVariableBounds(TreeLogger logger,
+ TypeVariableBinding tvBinding) {
+ TypeBinding firstBound = tvBinding.firstBound;
+ if (firstBound == null) {
+ firstBound = tvBinding.superclass;
+ }
+ JClassType firstBoundType = (JClassType) resolveType(logger, firstBound);
+ JBound bounds = new JBound(firstBoundType);
+ for (ReferenceBinding ref : tvBinding.superInterfaces()) {
+ JClassType bound = (JClassType) resolveType(logger, ref);
+ assert (bound.isInterface() != null);
+ bounds.addUpperBound(bound);
+ }
+ return bounds;
+ }
+
private Object evaluateAnnotationExpression(TreeLogger logger,
Expression expression) {
Annotation annotation = (Annotation) expression;
@@ -745,6 +812,15 @@
}
/**
+ * Maps a ParameterizedTypeBinding into a JParameterizedType.
+ */
+ private void processParameterizedType(ParameterizedTypeBinding binding) {
+ TypeOracle oracle = cacheManager.getTypeOracle();
+ // TODO Get the JParameterized type for the current binding, fill it out
+ // as you would a JClassType.
+ }
+
+ /**
* Maps a TypeDeclaration into a JClassType.
*/
private void processType(TypeDeclaration typeDecl, JClassType enclosingType,
@@ -796,17 +872,26 @@
int bodyStart = typeDecl.bodyStart;
int bodyEnd = typeDecl.bodyEnd;
- JClassType type;
+ JRealClassType type;
if (jclassIsAnnonation) {
- type = new JAnnotationType(oracle, cup, pkg, enclosingType,
- isLocalType, jclassName, declStart, declEnd, bodyStart, bodyEnd,
- jclassIsIntf);
+ type = new JAnnotationType(oracle, cup, pkg, enclosingType, isLocalType,
+ jclassName, declStart, declEnd, bodyStart, bodyEnd, jclassIsIntf);
+ } else if (typeDecl.typeParameters != null
+ && typeDecl.typeParameters.length > 0) {
+ type = new JGenericType(oracle, cup, pkg, enclosingType, isLocalType,
+ jclassName, declStart, declEnd, bodyStart, bodyEnd, jclassIsIntf);
+ for (TypeParameter jtypeParameter : typeDecl.typeParameters) {
+ JTypeParameter typeParameter = new JTypeParameter(
+ String.valueOf(jtypeParameter.name), (JGenericType) type);
+ cacheManager.setTypeForBinding(jtypeParameter.binding, typeParameter);
+ }
} else {
- type = new JClassType(oracle, cup, pkg, enclosingType,
- isLocalType, jclassName, declStart, declEnd, bodyStart, bodyEnd,
- jclassIsIntf);
+ type = new JRealClassType(oracle, cup, pkg, enclosingType, isLocalType,
+ jclassName, declStart, declEnd, bodyStart, bodyEnd, jclassIsIntf);
}
+ // TODO: enums?
+
cacheManager.setTypeForBinding(binding, type);
}
@@ -944,6 +1029,24 @@
bodyStart, bodyEnd, declaredAnnotations);
}
+ // Add declared type parameters.
+ if (jmethod.typeParameters() != null) {
+ for (TypeParameter jtypeParameter : jmethod.typeParameters()) {
+ JTypeParameter typeParameter = new JTypeParameter(
+ String.valueOf(jtypeParameter.name), method);
+ cacheManager.getIdentityMapper().put(jtypeParameter.binding,
+ typeParameter);
+ }
+ JTypeParameter[] typeParameters = method.getTypeParameters();
+ for (TypeParameter jtypeParameter : jmethod.typeParameters()) {
+ JTypeParameter typeParameter = (JTypeParameter) cacheManager.getIdentityMapper().get(
+ jtypeParameter.binding);
+ JBound bounds = createTypeVariableBounds(logger,
+ jtypeParameter.binding);
+ typeParameter.setBounds(bounds);
+ }
+ }
+
// Add the return type if necessary.
TypeBinding jreturnType = ((MethodDeclaration) jmethod).returnType.resolvedType;
JType returnType = resolveType(logger, jreturnType);
@@ -1002,8 +1105,7 @@
return true;
}
- private boolean resolvePackage(TreeLogger logger,
- TypeDeclaration jclass) {
+ private boolean resolvePackage(TreeLogger logger, TypeDeclaration jclass) {
SourceTypeBinding binding = jclass.binding;
TypeOracle oracle = cacheManager.getTypeOracle();
@@ -1048,7 +1150,9 @@
String name = String.valueOf(jparam.name);
new JParameter(method, type, name, declaredAnnotations);
-
+ if (jparam.isVarArgs()) {
+ method.setVarArgs();
+ }
return true;
}
@@ -1178,12 +1282,78 @@
// Check for parameterized.
if (binding instanceof ParameterizedTypeBinding) {
ParameterizedTypeBinding ptBinding = (ParameterizedTypeBinding) binding;
- return resolveType(logger, ptBinding.erasure());
+ JClassType[] typeArguments = new JClassType[ptBinding.arguments.length];
+ for (int i = 0; i < typeArguments.length; ++i) {
+ typeArguments[i] = (JClassType) resolveType(logger,
+ ptBinding.arguments[i]);
+ }
+
+ JGenericType baseType = (JGenericType) resolveType(logger, ptBinding.type);
+ return oracle.getParameterizedType(baseType, typeArguments);
}
if (binding instanceof TypeVariableBinding) {
TypeVariableBinding tvBinding = (TypeVariableBinding) binding;
- return resolveType(logger, tvBinding.erasure());
+ JTypeParameter typeParameter = (JTypeParameter) cacheManager.getTypeForBinding(tvBinding);
+ assert (typeParameter != null);
+
+ if (typeParameter.getBounds() == null) {
+ // Setup a dummy bound to prevent recursion
+ typeParameter.setBounds(new JBound(null));
+ JBound bounds = createTypeVariableBounds(logger, tvBinding);
+ typeParameter.setBounds(bounds);
+ }
+ return typeParameter;
+ }
+
+ if (binding instanceof WildcardBinding) {
+ WildcardBinding wcBinding = (WildcardBinding) binding;
+ JBound bounds;
+ switch (wcBinding.boundKind) {
+ case Wildcard.EXTENDS: {
+ JClassType firstBoundType = (JClassType) resolveType(logger,
+ wcBinding.bound);
+ bounds = new JBound(firstBoundType);
+ if (wcBinding.otherBounds != null) {
+ for (TypeBinding bound : wcBinding.otherBounds) {
+ JClassType boundType = (JClassType) resolveType(logger, bound);
+ bounds.addUpperBound(boundType);
+ }
+ }
+ }
+ break;
+ case Wildcard.SUPER: {
+ // TODO: verify
+ JClassType firstBoundType = (JClassType) resolveType(logger,
+ wcBinding.erasure());
+ assert (firstBoundType.getQualifiedSourceName().equals("java.lang.Object"));
+ bounds = new JBound(firstBoundType);
+
+ assert (wcBinding.bound != null);
+ JClassType boundType = (JClassType) resolveType(logger,
+ wcBinding.bound);
+ bounds.addLowerBound(boundType);
+ if (wcBinding.otherBounds != null) {
+ for (TypeBinding bound : wcBinding.otherBounds) {
+ boundType = (JClassType) resolveType(logger, bound);
+ bounds.addLowerBound(boundType);
+ }
+ }
+ }
+ break;
+ case Wildcard.UNBOUND: {
+ JClassType firstBoundType = (JClassType) resolveType(logger,
+ wcBinding.erasure());
+ assert (firstBoundType.getQualifiedSourceName().equals("java.lang.Object"));
+ bounds = new JBound(firstBoundType);
+ }
+ break;
+ default:
+ assert false : "WildcardBinding of unknown boundKind???";
+ return null;
+ }
+ JWildcardType wcType = new JWildcardType(bounds);
+ return wcType;
}
// Log other cases we know about that don't make sense.
@@ -1219,7 +1389,7 @@
}
// Just resolve the type.
- JClassType type = (JClassType) resolveType(logger, binding);
+ JRealClassType type = (JRealClassType) resolveType(logger, binding);
if (type == null) {
// Failed to resolve.
//
@@ -1239,6 +1409,13 @@
}
type.addAnnotations(declaredAnnotations);
+ // Resolve type parameters
+ List<JTypeParameter> typeParameters = new ArrayList<JTypeParameter>();
+ if (!resolveTypeParameters(logger, jclass.typeParameters, typeParameters)) {
+ // Failed to resolve
+ return false;
+ }
+
// Resolve superclass (for classes only).
//
if (type.isInterface() == null) {
@@ -1290,4 +1467,24 @@
return true;
}
+
+ private boolean resolveTypeParameter(TreeLogger logger,
+ TypeParameter jtypeParameter, List<JTypeParameter> typeParameters) {
+ JTypeParameter typeParameter = (JTypeParameter) cacheManager.getIdentityMapper().get(
+ jtypeParameter.binding);
+ typeParameters.add(typeParameter);
+ return true;
+ }
+
+ private boolean resolveTypeParameters(TreeLogger logger,
+ TypeParameter[] jtypeParameters, List<JTypeParameter> typeParameters) {
+ if (jtypeParameters != null) {
+ for (int i = 0; i < jtypeParameters.length; ++i) {
+ if (!resolveTypeParameter(logger, jtypeParameters[i], typeParameters)) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
}
diff --git a/dev/core/src/com/google/gwt/dev/shell/HostedModeSourceOracle.java b/dev/core/src/com/google/gwt/dev/shell/HostedModeSourceOracle.java
index d4b6162..64547c5 100644
--- a/dev/core/src/com/google/gwt/dev/shell/HostedModeSourceOracle.java
+++ b/dev/core/src/com/google/gwt/dev/shell/HostedModeSourceOracle.java
@@ -23,6 +23,7 @@
import com.google.gwt.dev.jdt.StaticCompilationUnitProvider;
import com.google.gwt.util.tools.Utility;
+import java.io.File;
import java.io.IOException;
/**
@@ -32,10 +33,12 @@
public class HostedModeSourceOracle extends StandardSourceOracle {
private final JsniInjector injector;
+ private final File jsniSaveDirectory;
- public HostedModeSourceOracle(TypeOracle typeOracle) {
+ public HostedModeSourceOracle(TypeOracle typeOracle, File jsniSaveDirectory) {
super(typeOracle);
this.injector = new JsniInjector(typeOracle);
+ this.jsniSaveDirectory = jsniSaveDirectory;
}
@Override
@@ -65,7 +68,8 @@
// Otherwise, it's a regular translatable type, but we want to make sure
// its JSNI stuff, if any, gets handled.
//
- CompilationUnitProvider jsnified = injector.inject(logger, existing);
+ CompilationUnitProvider jsnified = injector.inject(logger, existing,
+ jsniSaveDirectory);
return jsnified;
}
}
diff --git a/dev/core/src/com/google/gwt/dev/shell/JsniInjector.java b/dev/core/src/com/google/gwt/dev/shell/JsniInjector.java
index 91798e7..ca13137 100644
--- a/dev/core/src/com/google/gwt/dev/shell/JsniInjector.java
+++ b/dev/core/src/com/google/gwt/dev/shell/JsniInjector.java
@@ -29,7 +29,9 @@
import com.google.gwt.dev.js.ast.JsBlock;
import com.google.gwt.dev.util.Jsni;
import com.google.gwt.dev.util.StringCopier;
+import com.google.gwt.dev.util.Util;
+import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.IdentityHashMap;
@@ -47,10 +49,10 @@
* atomically.
*/
private class CoreTypes {
- static final String PKG_JSOBJECT = "com.google.gwt.core.client";
static final String CLS_JSOBJECT = "JavaScriptObject";
- static final String PKG_STRING = "java.lang";
static final String CLS_STRING = "String";
+ static final String PKG_JSOBJECT = "com.google.gwt.core.client";
+ static final String PKG_STRING = "java.lang";
public final JClassType javaLangString;
@@ -102,10 +104,10 @@
}
}
- private final TypeOracle oracle;
-
private CoreTypes coreTypes;
+ private final TypeOracle oracle;
+
private final Map<JMethod, JsBlock> parsedJsByMethod = new IdentityHashMap<JMethod, JsBlock>();
public JsniInjector(TypeOracle oracle) {
@@ -113,7 +115,8 @@
}
public CompilationUnitProvider inject(TreeLogger logger,
- CompilationUnitProvider cup) throws UnableToCompleteException {
+ CompilationUnitProvider cup, File jsniSaveDirectory)
+ throws UnableToCompleteException {
logger = logger.branch(TreeLogger.SPAM,
"Checking for JavaScript native methods", null);
@@ -126,7 +129,8 @@
// Analyze the source and build a list of changes.
char[] source = cup.getSource();
List<Replacement> changes = new ArrayList<Replacement>();
- rewriteCompilationUnit(logger, source, changes, cup);
+ rewriteCompilationUnit(logger, source, changes, cup,
+ jsniSaveDirectory != null);
// Sort and apply the changes.
int n = changes.size();
@@ -141,6 +145,17 @@
char[] results = copier.finish();
+ if (jsniSaveDirectory != null) {
+ String originalPath = cup.getLocation().replace(File.separatorChar, '/');
+ String suffix = cup.getPackageName().replace('.', '/');
+ int pos = originalPath.indexOf(suffix);
+ if (pos >= 0) {
+ String filePath = originalPath.substring(pos);
+ File out = new File(jsniSaveDirectory, filePath);
+ Util.writeCharsAsFile(logger, out, results);
+ }
+ }
+
return new CompilationUnitProviderWithAlternateSource(cup, results);
} else {
// No changes were made, so we return the original.
@@ -212,15 +227,28 @@
* @param method
* @param expectedHeaderLines
* @param expectedBodyLines
+ * @param prettyPrint true if the output should be prettier
* @return a String of the Java code to call a JSNI method, using
* JavaScriptHost.invokeNative*
*/
private String genNonNativeVersionOfJsniMethod(JMethod method,
- int expectedBodyLines) {
+ int expectedHeaderLines, int expectedBodyLines, boolean pretty) {
StringBuffer sb = new StringBuffer();
+ String nl = pretty ? "\n " : "";
+ // Add extra lines at the start to match comments + declaration
+ if (!pretty) {
+ for (int i = 0; i < expectedHeaderLines; ++i) {
+ sb.append('\n');
+ }
+ }
+
+ String methodDecl = method.getReadableDeclaration(false, true, false,
+ false, false);
+
+ sb.append(methodDecl + " {" + nl);
// wrap the call in a try-catch block
- sb.append("{ try {");
+ sb.append("try {" + nl);
// Write the Java call to the property invoke method, adding
// downcasts where necessary.
@@ -229,7 +257,7 @@
JPrimitiveType primType;
if (isJavaScriptObject) {
// Add a downcast from Handle to the originally-declared type.
- String returnTypeName = returnType.getQualifiedSourceName();
+ String returnTypeName = returnType.getParameterizedQualifiedSourceName();
sb.append("return (" + returnTypeName + ")" + Jsni.JAVASCRIPTHOST_NAME
+ ".invokeNativeHandle");
} else if (null != (primType = returnType.isPrimitive())) {
@@ -250,7 +278,7 @@
} else {
// Some reference type.
// We need to add a downcast to the originally-declared type.
- String returnTypeName = returnType.getQualifiedSourceName();
+ String returnTypeName = returnType.getParameterizedQualifiedSourceName();
sb.append("return (");
sb.append(returnTypeName);
sb.append(")");
@@ -270,7 +298,7 @@
if (isJavaScriptObject) {
// Handle-oriented calls also need the return type as an argument.
- String returnTypeName = returnType.getQualifiedSourceName();
+ String returnTypeName = returnType.getErasedType().getQualifiedSourceName();
sb.append(returnTypeName);
sb.append(".class, ");
}
@@ -283,25 +311,29 @@
// Build an array containing the arguments based on the names of the
// parameters.
sb.append(Jsni.buildArgList(method));
- sb.append(");");
+ sb.append(");" + nl);
// Catch exceptions; rethrow if the exception is RTE or declared.
- sb.append("} catch (java.lang.Throwable __gwt_exception) {");
- sb.append("if (__gwt_exception instanceof java.lang.RuntimeException) throw (java.lang.RuntimeException) __gwt_exception;");
+ sb.append("} catch (java.lang.Throwable __gwt_exception) {" + nl);
+ sb.append("if (__gwt_exception instanceof java.lang.RuntimeException) throw (java.lang.RuntimeException) __gwt_exception;"
+ + nl);
JType[] throwTypes = method.getThrows();
for (int i = 0; i < throwTypes.length; ++i) {
String typeName = throwTypes[i].getQualifiedSourceName();
sb.append("if (__gwt_exception instanceof " + typeName + ") throw ("
- + typeName + ") __gwt_exception;");
+ + typeName + ") __gwt_exception;" + nl);
}
- sb.append("throw new java.lang.RuntimeException(\"Undeclared checked exception thrown out of JavaScript; web mode behavior may differ.\", __gwt_exception);");
+ sb.append("throw new java.lang.RuntimeException(\"Undeclared checked exception thrown out of JavaScript; web mode behavior may differ.\", __gwt_exception);"
+ + nl);
+ sb.append("}" + nl);
- // Close try block and method body.
- sb.append("} }");
+ sb.append("}" + nl);
// Add extra lines at the end to match JSNI body.
- for (int i = 0; i < expectedBodyLines; ++i) {
- sb.append('\n');
+ if (!pretty) {
+ for (int i = 0; i < expectedBodyLines; ++i) {
+ sb.append('\n');
+ }
}
return sb.toString();
@@ -337,41 +369,20 @@
}
}
- private void replaceNativeKeywords(char[] source, List<Replacement> changes,
- int start, int end) {
- String nativeKeyword = "native";
- char[] whitespace = " ".toCharArray();
- assert (whitespace.length == nativeKeyword.length());
- String header = String.valueOf(source, start, end - start);
- for (int pos = header.indexOf(nativeKeyword); pos >= 0; pos = header.indexOf(
- nativeKeyword, pos + 1)) {
- if (pos > 0 && !Character.isWhitespace(header.charAt(pos - 1))) {
- // not a keyword
- continue;
- }
- if (pos + 6 < header.length()
- && !Character.isWhitespace(header.charAt(pos + 6))) {
- // not a keyword
- continue;
- }
- changes.add(new Replacement(start + pos, start + pos + 6, whitespace));
- }
- }
-
private void rewriteCompilationUnit(TreeLogger logger, char[] source,
- List<Replacement> changes, CompilationUnitProvider cup)
+ List<Replacement> changes, CompilationUnitProvider cup, boolean pretty)
throws UnableToCompleteException {
// Hit all the types in the compilation unit.
JClassType[] types = oracle.getTypesInCompilationUnit(cup);
for (int i = 0; i < types.length; i++) {
JClassType type = types[i];
- rewriteType(logger, source, changes, type);
+ rewriteType(logger, source, changes, type, pretty);
}
}
private void rewriteType(TreeLogger logger, char[] source,
- List<Replacement> changes, JClassType type)
+ List<Replacement> changes, JClassType type, boolean pretty)
throws UnableToCompleteException {
String loc = type.getCompilationUnit().getLocation();
@@ -395,20 +406,19 @@
// Remember this as being a valid JSNI method.
parsedJsByMethod.put(method, body);
+ // Replace the method.
+ final int declStart = method.getDeclStart();
+ final int declEnd = method.getDeclEnd();
+
+ int expectedHeaderLines = Jsni.countNewlines(source, declStart,
+ interval.start);
int expectedBodyLines = Jsni.countNewlines(source, interval.start,
interval.end);
- String newBody = genNonNativeVersionOfJsniMethod(method,
- expectedBodyLines);
+ String newDecl = genNonNativeVersionOfJsniMethod(method,
+ expectedHeaderLines, expectedBodyLines, pretty);
- char[] newSource = newBody.toCharArray();
- int jsniCommentStart = interval.start
- - Jsni.JSNI_BLOCK_START.length();
- changes.add(new Replacement(jsniCommentStart,
- method.getDeclEnd() + 1, newSource));
-
- replaceNativeKeywords(source, changes, method.getDeclStart(),
- jsniCommentStart);
-
+ final char[] newSource = newDecl.toCharArray();
+ changes.add(new Replacement(declStart, declEnd, newSource));
patchedMethods.add(method);
} else {
// report error
diff --git a/dev/core/src/com/google/gwt/dev/util/Jsni.java b/dev/core/src/com/google/gwt/dev/util/Jsni.java
index f6ee187..d3b33c2 100644
--- a/dev/core/src/com/google/gwt/dev/util/Jsni.java
+++ b/dev/core/src/com/google/gwt/dev/util/Jsni.java
@@ -191,7 +191,7 @@
}
JType type = params[i].getType();
- String typeName = type.getQualifiedSourceName();
+ String typeName = type.getErasedType().getQualifiedSourceName();
sb.append(typeName);
sb.append(".class");
}
diff --git a/dev/core/test/com/google/gwt/core/ext/typeinfo/TypeOracleGenericsSupportTest.java b/dev/core/test/com/google/gwt/core/ext/typeinfo/TypeOracleGenericsSupportTest.java
new file mode 100644
index 0000000..d1b4f93
--- /dev/null
+++ b/dev/core/test/com/google/gwt/core/ext/typeinfo/TypeOracleGenericsSupportTest.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo;
+
+import com.google.gwt.core.ext.TreeLogger;
+import com.google.gwt.core.ext.UnableToCompleteException;
+import com.google.gwt.core.ext.typeinfo.test.GenericSubclass;
+import com.google.gwt.dev.cfg.ModuleDef;
+import com.google.gwt.dev.cfg.ModuleDefLoader;
+
+import junit.framework.TestCase;
+
+/**
+ * Test cases for the {@link TypeOracle}'s and TypeOracleBuilder support for
+ * generics.
+ */
+public class TypeOracleGenericsSupportTest extends TestCase {
+ static {
+ ModuleDefLoader.setEnableCachingModules(true);
+ }
+
+ private final TreeLogger logger = TreeLogger.NULL;
+ private ModuleDef moduleDef;
+
+ private final TypeOracle typeOracle;
+
+ public TypeOracleGenericsSupportTest() throws UnableToCompleteException {
+ moduleDef = ModuleDefLoader.loadFromClassPath(logger,
+ "com.google.gwt.core.ext.typeinfo.TypeOracleTest");
+ typeOracle = moduleDef.getTypeOracle(logger);
+ }
+
+ public void test() throws NotFoundException {
+ JClassType type = typeOracle.getType(GenericSubclass.class.getName());
+ }
+}
diff --git a/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericClass.java b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericClass.java
new file mode 100644
index 0000000..085a567
--- /dev/null
+++ b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericClass.java
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo.test;
+
+/**
+ *
+ */
+public class GenericClass<T> {
+ T t;
+
+ public GenericClass(T t) {
+ this.t = t;
+ }
+
+ public T getT() {
+ return t;
+ }
+
+ public void setT(T t) {
+ this.t = t;
+ }
+}
diff --git a/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericSubclass.java b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericSubclass.java
new file mode 100644
index 0000000..056313a
--- /dev/null
+++ b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/GenericSubclass.java
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo.test;
+
+/**
+ *
+ */
+public class GenericSubclass<U> extends GenericClass<U> {
+ // Explore what JDT does when there is a parameterized type
+ GenericClass<Integer> child;
+
+ public GenericSubclass(U t) {
+ super(t);
+ }
+}
diff --git a/dev/core/test/com/google/gwt/core/ext/typeinfo/test/NonGenericSubclass.java b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/NonGenericSubclass.java
new file mode 100644
index 0000000..44413a4
--- /dev/null
+++ b/dev/core/test/com/google/gwt/core/ext/typeinfo/test/NonGenericSubclass.java
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2007 Google Inc.
+ *
+ * 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.
+ */
+package com.google.gwt.core.ext.typeinfo.test;
+
+/**
+ *
+ */
+public class NonGenericSubclass extends GenericClass<Integer> {
+ /**
+ * @param t
+ */
+ public NonGenericSubclass(Integer t) {
+ super(t);
+ // TODO Auto-generated constructor stub
+ }
+}
diff --git a/user/src/com/google/gwt/user/client/rpc/core/java/util/ArrayList_CustomFieldSerializer.java b/user/src/com/google/gwt/user/client/rpc/core/java/util/ArrayList_CustomFieldSerializer.java
index 8727c09..cc9ddd2 100644
--- a/user/src/com/google/gwt/user/client/rpc/core/java/util/ArrayList_CustomFieldSerializer.java
+++ b/user/src/com/google/gwt/user/client/rpc/core/java/util/ArrayList_CustomFieldSerializer.java
@@ -27,7 +27,7 @@
public final class ArrayList_CustomFieldSerializer {
public static void deserialize(SerializationStreamReader streamReader,
- ArrayList<Object> instance) throws SerializationException {
+ ArrayList instance) throws SerializationException {
int size = streamReader.readInt();
for (int i = 0; i < size; ++i) {
Object obj = streamReader.readObject();
@@ -36,11 +36,11 @@
}
public static void serialize(SerializationStreamWriter streamWriter,
- ArrayList<Object> instance) throws SerializationException {
+ ArrayList instance) throws SerializationException {
int size = instance.size();
streamWriter.writeInt(size);
for (Object obj : instance) {
streamWriter.writeObject(obj);
}
}
-}
\ No newline at end of file
+}
diff --git a/user/src/com/google/gwt/user/client/rpc/core/java/util/HashMap_CustomFieldSerializer.java b/user/src/com/google/gwt/user/client/rpc/core/java/util/HashMap_CustomFieldSerializer.java
index 97d4d87..d051792 100644
--- a/user/src/com/google/gwt/user/client/rpc/core/java/util/HashMap_CustomFieldSerializer.java
+++ b/user/src/com/google/gwt/user/client/rpc/core/java/util/HashMap_CustomFieldSerializer.java
@@ -20,6 +20,7 @@
import com.google.gwt.user.client.rpc.SerializationStreamWriter;
import java.util.HashMap;
+import java.util.Set;
import java.util.Map.Entry;
/**
@@ -28,7 +29,7 @@
public final class HashMap_CustomFieldSerializer {
public static void deserialize(SerializationStreamReader streamReader,
- HashMap<Object, Object> instance) throws SerializationException {
+ HashMap instance) throws SerializationException {
int size = streamReader.readInt();
for (int i = 0; i < size; ++i) {
@@ -40,11 +41,11 @@
}
public static void serialize(SerializationStreamWriter streamWriter,
- HashMap<Object, Object> instance) throws SerializationException {
+ HashMap instance) throws SerializationException {
int size = instance.size();
streamWriter.writeInt(size);
- for (Entry<Object, Object> entry : instance.entrySet()) {
+ for (Entry entry : (Set<Entry>)instance.entrySet()) {
streamWriter.writeObject(entry.getKey());
streamWriter.writeObject(entry.getValue());
}
diff --git a/user/src/com/google/gwt/user/client/rpc/core/java/util/HashSet_CustomFieldSerializer.java b/user/src/com/google/gwt/user/client/rpc/core/java/util/HashSet_CustomFieldSerializer.java
index 1eea48c..d732fbe 100644
--- a/user/src/com/google/gwt/user/client/rpc/core/java/util/HashSet_CustomFieldSerializer.java
+++ b/user/src/com/google/gwt/user/client/rpc/core/java/util/HashSet_CustomFieldSerializer.java
@@ -27,7 +27,7 @@
public final class HashSet_CustomFieldSerializer {
public static void deserialize(SerializationStreamReader streamReader,
- HashSet<Object> instance) throws SerializationException {
+ HashSet instance) throws SerializationException {
int size = streamReader.readInt();
for (int i = 0; i < size; ++i) {
instance.add(streamReader.readObject());
@@ -35,7 +35,7 @@
}
public static void serialize(SerializationStreamWriter streamWriter,
- HashSet<Object> instance) throws SerializationException {
+ HashSet instance) throws SerializationException {
streamWriter.writeInt(instance.size());
for (Object obj : instance) {
streamWriter.writeObject(obj);
diff --git a/user/src/com/google/gwt/user/client/rpc/core/java/util/Vector_CustomFieldSerializer.java b/user/src/com/google/gwt/user/client/rpc/core/java/util/Vector_CustomFieldSerializer.java
index 1d008e9..b3a4478 100644
--- a/user/src/com/google/gwt/user/client/rpc/core/java/util/Vector_CustomFieldSerializer.java
+++ b/user/src/com/google/gwt/user/client/rpc/core/java/util/Vector_CustomFieldSerializer.java
@@ -27,7 +27,7 @@
public final class Vector_CustomFieldSerializer {
public static void deserialize(SerializationStreamReader streamReader,
- Vector<Object> instance) throws SerializationException {
+ Vector instance) throws SerializationException {
int size = streamReader.readInt();
for (int i = 0; i < size; ++i) {
Object obj = streamReader.readObject();
@@ -36,7 +36,7 @@
}
public static void serialize(SerializationStreamWriter streamWriter,
- Vector<Object> instance) throws SerializationException {
+ Vector instance) throws SerializationException {
int size = instance.size();
streamWriter.writeInt(size);
for (Object obj : instance) {
diff --git a/user/super/com/google/gwt/emul/java/lang/Enum.java b/user/super/com/google/gwt/emul/java/lang/Enum.java
index 9c00c60..f11649c 100644
--- a/user/super/com/google/gwt/emul/java/lang/Enum.java
+++ b/user/super/com/google/gwt/emul/java/lang/Enum.java
@@ -15,15 +15,12 @@
*/
package java.lang;
-import java.io.Serializable;
-
/**
* The first-class representation of an enumeration.
*
* @param <E>
*/
-public abstract class Enum<E extends Enum<E>> implements Comparable<E>,
- Serializable {
+public abstract class Enum<E extends Enum<E>> implements Comparable<E> {
// public static <T extends Enum<T>> T valueOf(Class<T> enumType, String name)
// {
diff --git a/user/super/com/google/gwt/emul/java/util/Arrays.java b/user/super/com/google/gwt/emul/java/util/Arrays.java
index 0912420..3861bfd 100644
--- a/user/super/com/google/gwt/emul/java/util/Arrays.java
+++ b/user/super/com/google/gwt/emul/java/util/Arrays.java
@@ -19,7 +19,8 @@
import com.google.gwt.core.client.GWT;
/**
- * Utility methods related to native arrays. <a href="http://java.sun.com/j2se/1.5.0/docs/api/java/util/Arrays.html">[Sun
+ * Utility methods related to native arrays. <a
+ * href="http://java.sun.com/j2se/1.5.0/docs/api/java/util/Arrays.html">[Sun
* docs]</a>
*/
public class Arrays {
@@ -34,9 +35,9 @@
/**
* Perform a binary search on a sorted byte array.
- *
+ *
* @param sortedArray byte array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -65,8 +66,8 @@
/**
* Perform a binary search on a sorted char array.
- *
- * @param a char array to search
+ *
+ * @param a char array to search
* @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
@@ -96,9 +97,9 @@
/**
* Perform a binary search on a sorted double array.
- *
+ *
* @param sortedArray double array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -127,14 +128,14 @@
/**
* Perform a binary search on a sorted float array.
- *
+ *
* Note that some underlying JavaScript interpreters do not actually implement
* floats (using double instead), so you may get slightly different behavior
* regarding values that are very close (or equal) since conversion errors
* to/from double may change the values slightly.
- *
+ *
* @param sortedArray float array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -163,9 +164,9 @@
/**
* Perform a binary search on a sorted int array.
- *
+ *
* @param sortedArray int array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -194,15 +195,15 @@
/**
* Perform a binary search on a sorted long array.
- *
+ *
* Note that most underlying JavaScript interpreters do not actually implement
* longs, so the values must be stored in doubles instead. This means that
* certain legal values cannot be represented, and comparison of two unequal
* long values may result in unexpected results if they are not also
* representable as doubles.
- *
+ *
* @param sortedArray long array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -231,15 +232,15 @@
/**
* Perform a binary search on a sorted object array, using natural ordering.
- *
+ *
* @param sortedArray object array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
* the array) minus 1 (to ensure error returns are negative)
* @throws ClassCastException if <code>key</code> is not comparable to
- * <code>sortedArray</code>'s elements.
+ * <code>sortedArray</code>'s elements.
*/
public static int binarySearch(final Object[] sortedArray, final Object key) {
return binarySearch(sortedArray, key, Comparators.natural());
@@ -247,9 +248,9 @@
/**
* Perform a binary search on a sorted short array.
- *
+ *
* @param sortedArray short array to search
- * @param key value to search for
+ * @param key value to search for
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
@@ -279,17 +280,18 @@
/**
* Perform a binary search on a sorted object array, using a user-specified
* comparison function.
- *
+ *
* @param sortedArray object array to search
- * @param key value to search for
- * @param comparator comparision function, <code>null</code> indicates
- * <i>natural ordering</i> should be used.
+ * @param key value to search for
+ * @param comparator comparision function, <code>null</code> indicates
+ * <i>natural ordering</i> should be used.
* @return the index of an element with a matching value, or a negative number
* which is the index of the next larger value (or just past the end
* of the array if the searched value is larger than all elements in
* the array) minus 1 (to ensure error returns are negative)
- * @throws ClassCastException if <code>key</code> and <code>sortedArray</code>'s
- * elements cannot be compared by <code>comparator</code>.
+ * @throws ClassCastException if <code>key</code> and
+ * <code>sortedArray</code>'s elements cannot be compared by
+ * <code>comparator</code>.
*/
public static <T> int binarySearch(final T[] sortedArray, final T key,
Comparator<? super T> comparator) {
@@ -434,30 +436,6 @@
return deepToString(a, new HashSet<Object[]>());
}
- public static boolean equals(Object[] array1, Object[] array2) {
- if (array1 == array2) {
- return true;
- }
-
- if (array1 == null || array2 == null) {
- return false;
- }
-
- if (array1.length != array2.length) {
- return false;
- }
-
- for (int i = 0; i < array1.length; ++i) {
- Object val1 = array1[i];
- Object val2 = array2[i];
- if (!val1.equals(val2)) {
- return false;
- }
- }
-
- return true;
- }
-
public static boolean equals(boolean[] array1, boolean[] array2) {
if (array1 == array2) {
return true;
@@ -524,7 +502,29 @@
return true;
}
- public static boolean equals(short[] array1, short[] array2) {
+ public static boolean equals(double[] array1, double[] array2) {
+ if (array1 == array2) {
+ return true;
+ }
+
+ if (array1 == null || array2 == null) {
+ return false;
+ }
+
+ if (array1.length != array2.length) {
+ return false;
+ }
+
+ for (int i = 0; i < array1.length; ++i) {
+ if (array1[i] != array2[i]) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ public static boolean equals(float[] array1, float[] array2) {
if (array1 == array2) {
return true;
}
@@ -590,7 +590,7 @@
return true;
}
- public static boolean equals(float[] array1, float[] array2) {
+ public static boolean equals(Object[] array1, Object[] array2) {
if (array1 == array2) {
return true;
}
@@ -604,7 +604,9 @@
}
for (int i = 0; i < array1.length; ++i) {
- if (array1[i] != array2[i]) {
+ Object val1 = array1[i];
+ Object val2 = array2[i];
+ if (!val1.equals(val2)) {
return false;
}
}
@@ -612,7 +614,7 @@
return true;
}
- public static boolean equals(double[] array1, double[] array2) {
+ public static boolean equals(short[] array1, short[] array2) {
if (array1 == array2) {
return true;
}
@@ -638,8 +640,7 @@
fill(a, 0, a.length, val);
}
- public static void fill(boolean[] a, int fromIndex, int toIndex,
- boolean val) {
+ public static void fill(boolean[] a, int fromIndex, int toIndex, boolean val) {
for (int i = fromIndex; i < toIndex; ++i) {
a[i] = val;
}
@@ -649,8 +650,7 @@
fill(a, 0, a.length, val);
}
- public static void fill(byte[] a, int fromIndex, int toIndex,
- byte val) {
+ public static void fill(byte[] a, int fromIndex, int toIndex, byte val) {
for (int i = fromIndex; i < toIndex; ++i) {
a[i] = val;
}
@@ -660,52 +660,7 @@
fill(a, 0, a.length, val);
}
- public static void fill(char[] a, int fromIndex, int toIndex,
- char val) {
- for (int i = fromIndex; i < toIndex; ++i) {
- a[i] = val;
- }
- }
-
- public static void fill(short[] a, short val) {
- fill(a, 0, a.length, val);
- }
-
- public static void fill(short[] a, int fromIndex, int toIndex,
- short val) {
- for (int i = fromIndex; i < toIndex; ++i) {
- a[i] = val;
- }
- }
-
- public static void fill(int[] a, int val) {
- fill(a, 0, a.length, val);
- }
-
- public static void fill(int[] a, int fromIndex, int toIndex,
- int val) {
- for (int i = fromIndex; i < toIndex; ++i) {
- a[i] = val;
- }
- }
-
- public static void fill(long[] a, long val) {
- fill(a, 0, a.length, val);
- }
-
- public static void fill(long[] a, int fromIndex, int toIndex,
- long val) {
- for (int i = fromIndex; i < toIndex; ++i) {
- a[i] = val;
- }
- }
-
- public static void fill(float[] a, float val) {
- fill(a, 0, a.length, val);
- }
-
- public static void fill(float[] a, int fromIndex, int toIndex,
- float val) {
+ public static void fill(char[] a, int fromIndex, int toIndex, char val) {
for (int i = fromIndex; i < toIndex; ++i) {
a[i] = val;
}
@@ -715,8 +670,43 @@
fill(a, 0, a.length, val);
}
- public static void fill(double[] a, int fromIndex, int toIndex,
- double val) {
+ public static void fill(double[] a, int fromIndex, int toIndex, double val) {
+ for (int i = fromIndex; i < toIndex; ++i) {
+ a[i] = val;
+ }
+ }
+
+ public static void fill(float[] a, float val) {
+ fill(a, 0, a.length, val);
+ }
+
+ public static void fill(float[] a, int fromIndex, int toIndex, float val) {
+ for (int i = fromIndex; i < toIndex; ++i) {
+ a[i] = val;
+ }
+ }
+
+ public static void fill(int[] a, int val) {
+ fill(a, 0, a.length, val);
+ }
+
+ public static void fill(int[] a, int fromIndex, int toIndex, int val) {
+ for (int i = fromIndex; i < toIndex; ++i) {
+ a[i] = val;
+ }
+ }
+
+ public static void fill(long[] a, int fromIndex, int toIndex, long val) {
+ for (int i = fromIndex; i < toIndex; ++i) {
+ a[i] = val;
+ }
+ }
+
+ public static void fill(long[] a, long val) {
+ fill(a, 0, a.length, val);
+ }
+
+ public static void fill(Object[] a, int fromIndex, int toIndex, Object val) {
for (int i = fromIndex; i < toIndex; ++i) {
a[i] = val;
}
@@ -726,13 +716,16 @@
fill(a, 0, a.length, val);
}
- public static void fill(Object[] a, int fromIndex, int toIndex,
- Object val) {
+ public static void fill(short[] a, int fromIndex, int toIndex, short val) {
for (int i = fromIndex; i < toIndex; ++i) {
a[i] = val;
}
}
+ public static void fill(short[] a, short val) {
+ fill(a, 0, a.length, val);
+ }
+
public static int hashCode(boolean[] a) {
if (a == null) {
return 0;
@@ -769,13 +762,25 @@
return hashCode;
}
- public static int hashCode(short[] a) {
+ public static int hashCode(double[] a) {
if (a == null) {
return 0;
}
int hashCode = 1;
for (int i = 0, n = a.length; i < n; ++i) {
- hashCode = (31 * hashCode + Short.hashCode(a[i])) | 0;
+ hashCode = (31 * hashCode + Double.hashCode(a[i])) | 0;
+ }
+
+ return hashCode;
+ }
+
+ public static int hashCode(float[] a) {
+ if (a == null) {
+ return 0;
+ }
+ int hashCode = 1;
+ for (int i = 0, n = a.length; i < n; ++i) {
+ hashCode = (31 * hashCode + Float.hashCode(a[i])) | 0;
}
return hashCode;
@@ -805,30 +810,6 @@
return hashCode;
}
- public static int hashCode(float[] a) {
- if (a == null) {
- return 0;
- }
- int hashCode = 1;
- for (int i = 0, n = a.length; i < n; ++i) {
- hashCode = (31 * hashCode + Float.hashCode(a[i])) | 0;
- }
-
- return hashCode;
- }
-
- public static int hashCode(double[] a) {
- if (a == null) {
- return 0;
- }
- int hashCode = 1;
- for (int i = 0, n = a.length; i < n; ++i) {
- hashCode = (31 * hashCode + Double.hashCode(a[i])) | 0;
- }
-
- return hashCode;
- }
-
public static int hashCode(Object[] a) {
if (a == null) {
return 0;
@@ -841,6 +822,18 @@
return hashCode;
}
+ public static int hashCode(short[] a) {
+ if (a == null) {
+ return 0;
+ }
+ int hashCode = 1;
+ for (int i = 0, n = a.length; i < n; ++i) {
+ hashCode = (31 * hashCode + Short.hashCode(a[i])) | 0;
+ }
+
+ return hashCode;
+ }
+
public static void sort(byte[] a) {
sort(a, 0, a.length);
}
@@ -859,11 +852,20 @@
nativeSort(a, fromIndex, toIndex);
}
- public static void sort(short[] a) {
+ public static void sort(double[] a) {
sort(a, 0, a.length);
}
- public static void sort(short[] a, int fromIndex, int toIndex) {
+ public static void sort(double[] a, int fromIndex, int toIndex) {
+ verifySortIndices(fromIndex, toIndex);
+ nativeSort(a, fromIndex, toIndex);
+ }
+
+ public static void sort(float[] a) {
+ sort(a, 0, a.length);
+ }
+
+ public static void sort(float[] a, int fromIndex, int toIndex) {
verifySortIndices(fromIndex, toIndex);
nativeSort(a, fromIndex, toIndex);
}
@@ -886,32 +888,32 @@
nativeSort(a, fromIndex, toIndex);
}
- public static void sort(float[] a) {
- sort(a, 0, a.length);
- }
-
- public static void sort(float[] a, int fromIndex, int toIndex) {
- verifySortIndices(fromIndex, toIndex);
- nativeSort(a, fromIndex, toIndex);
- }
-
- public static void sort(double[] a) {
- sort(a, 0, a.length);
- }
-
- public static void sort(double[] a, int fromIndex, int toIndex) {
- verifySortIndices(fromIndex, toIndex);
- nativeSort(a, fromIndex, toIndex);
- }
-
public static void sort(Object[] x) {
nativeSort(x, x.length, Comparators.natural());
}
+ public static void sort(Object[] a, int fromIndex, int toIndex) {
+ // TODO
+ }
+
+ public static void sort(short[] a) {
+ sort(a, 0, a.length);
+ }
+
+ public static void sort(short[] a, int fromIndex, int toIndex) {
+ verifySortIndices(fromIndex, toIndex);
+ nativeSort(a, fromIndex, toIndex);
+ }
+
public static <T> void sort(T[] x, Comparator<? super T> s) {
nativeSort(x, x.length, s != null ? s : Comparators.natural());
}
+ public static <T> void sort(T[] a, int fromIndex, int toIndex,
+ Comparator<? super T> c) {
+ // TODO
+ }
+
public static String toString(boolean[] a) {
if (a == null) {
return "null";
@@ -960,7 +962,23 @@
return b.toString();
}
- public static String toString(short[] a) {
+ public static String toString(double[] a) {
+ if (a == null) {
+ return "null";
+ }
+
+ StringBuffer b = new StringBuffer("[");
+ for (int i = 0; i < a.length; i++) {
+ if (i != 0) {
+ b.append(", ");
+ }
+ b.append(String.valueOf(a[i]));
+ }
+ b.append("]");
+ return b.toString();
+ }
+
+ public static String toString(float[] a) {
if (a == null) {
return "null";
}
@@ -1008,38 +1026,6 @@
return b.toString();
}
- public static String toString(float[] a) {
- if (a == null) {
- return "null";
- }
-
- StringBuffer b = new StringBuffer("[");
- for (int i = 0; i < a.length; i++) {
- if (i != 0) {
- b.append(", ");
- }
- b.append(String.valueOf(a[i]));
- }
- b.append("]");
- return b.toString();
- }
-
- public static String toString(double[] a) {
- if (a == null) {
- return "null";
- }
-
- StringBuffer b = new StringBuffer("[");
- for (int i = 0; i < a.length; i++) {
- if (i != 0) {
- b.append(", ");
- }
- b.append(String.valueOf(a[i]));
- }
- b.append("]");
- return b.toString();
- }
-
public static String toString(Object[] x) {
if (x == null) {
return "null";
@@ -1048,6 +1034,22 @@
return Arrays.asList(x).toString();
}
+ public static String toString(short[] a) {
+ if (a == null) {
+ return "null";
+ }
+
+ StringBuffer b = new StringBuffer("[");
+ for (int i = 0; i < a.length; i++) {
+ if (i != 0) {
+ b.append(", ");
+ }
+ b.append(String.valueOf(a[i]));
+ }
+ b.append("]");
+ return b.toString();
+ }
+
static void unsafeSort(Object[] x, Comparator<?> s) {
nativeSort(x, x.length, s != null ? s : Comparators.natural());
}
@@ -1076,7 +1078,7 @@
if (arraysIveSeen.contains(obj)) {
b.append("[...]");
} else {
- Object[] objArray = (Object[])obj;
+ Object[] objArray = (Object[]) obj;
HashSet<Object[]> tempSet = new HashSet<Object[]>(arraysIveSeen);
b.append(deepToString(objArray, tempSet));
}
@@ -1107,133 +1109,130 @@
return b.toString();
}
- private static native void nativeSort(byte[] array, int fromIndex,
- int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
+ private static native void nativeSort(byte[] array, int fromIndex, int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
- v.sort();
+ v.sort();
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
- private static native void nativeSort(char[] array, int fromIndex,
- int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
+ private static native void nativeSort(char[] array, int fromIndex, int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
- v.sort();
+ v.sort();
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
-
- private static native void nativeSort(short[] array, int fromIndex,
- int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
-
- v.sort();
-
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
-
- private static native void nativeSort(int[] array, int fromIndex, int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
-
- v.sort();
-
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
-
- private static native void nativeSort(long[] array, int fromIndex,
- int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
-
- v.sort();
-
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
-
- private static native void nativeSort(float[] array, int fromIndex,
- int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
-
- v.sort();
-
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
private static native void nativeSort(double[] array, int fromIndex,
int toIndex) /*-{
- var v = new Array();
- for(var i = fromIndex; i < toIndex; ++i){
- v[i - fromIndex] = array[i];
- }
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
- v.sort();
+ v.sort();
- for(var i = fromIndex; i < toIndex; ++i){
- array[i] = v[i - fromIndex];
- }
- }-*/;
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
+
+ private static native void nativeSort(float[] array, int fromIndex,
+ int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
+
+ v.sort();
+
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
+
+ private static native void nativeSort(int[] array, int fromIndex, int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
+
+ v.sort();
+
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
+
+ private static native void nativeSort(long[] array, int fromIndex, int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
+
+ v.sort();
+
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
private static native void nativeSort(Object[] array, int size,
Comparator<?> compare) /*-{
- if (size == 0) {
- return;
- }
+ if (size == 0) {
+ return;
+ }
+
+ var v = new Array();
+ for(var i = 0; i < size; ++i){
+ v[i] = array[i];
+ }
- var v = new Array();
- for(var i = 0; i < size; ++i){
- v[i] = array[i];
- }
-
- if(compare != null) {
- var f = function(a,b) {
- var c = compare.@java.util.Comparator::compare(Ljava/lang/Object;Ljava/lang/Object;)(a,b);
- return c;
- }
- v.sort(f);
- } else {
- v.sort();
- }
+ if(compare != null) {
+ var f = function(a,b) {
+ var c = compare.@java.util.Comparator::compare(Ljava/lang/Object;Ljava/lang/Object;)(a,b);
+ return c;
+ }
+ v.sort(f);
+ } else {
+ v.sort();
+ }
- for(var i = 0; i < size; ++i){
- array[i] = v[i];
- }
- }-*/;
+ for(var i = 0; i < size; ++i){
+ array[i] = v[i];
+ }
+ }-*/;
+
+ private static native void nativeSort(short[] array, int fromIndex,
+ int toIndex) /*-{
+ var v = new Array();
+ for(var i = fromIndex; i < toIndex; ++i){
+ v[i - fromIndex] = array[i];
+ }
+
+ v.sort();
+
+ for(var i = fromIndex; i < toIndex; ++i){
+ array[i] = v[i - fromIndex];
+ }
+ }-*/;
private static void verifySortIndices(int fromIndex, int toIndex) {
if (fromIndex > toIndex) {
- throw new IllegalArgumentException(
- "fromIndex(" + fromIndex + ") > toIndex(" + toIndex + ")");
+ throw new IllegalArgumentException("fromIndex(" + fromIndex
+ + ") > toIndex(" + toIndex + ")");
}
}
}
diff --git a/user/test/com/google/gwt/dev/jjs/test/HostedTest.java b/user/test/com/google/gwt/dev/jjs/test/HostedTest.java
index 1760890..809a91d 100644
--- a/user/test/com/google/gwt/dev/jjs/test/HostedTest.java
+++ b/user/test/com/google/gwt/dev/jjs/test/HostedTest.java
@@ -20,10 +20,15 @@
**********************/
package com.google.gwt.dev.jjs.test;
-import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.core.client.GWT;
+import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.junit.client.GWTTestCase;
+import java.util.AbstractList;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
//CHECKSTYLE_NAMING_OFF
/**
@@ -52,22 +57,44 @@
}
}
+ private static class GenericListTest extends AbstractList<Object> {
+
+ @Override
+ public Object get(int index) {
+ return this;
+ }
+
+ @Override
+ public int size() {
+ return 42;
+ }
+ }
+
+ private static class TestCovariantChild extends TestCovariantSuper {
+ @Override
+ public native String foo(String val) /*-{
+ return val;
+ }-*/;
+ }
+
+ private static class TestCovariantSuper {
+ public native Object foo(String val) /*-{
+ return val;
+ }-*/;
+ }
+
+ private static enum TestEnum {
+ VAL1, VAL2, VAL3
+ }
+
static String sFoo(String s) {
return s + "foo";
}
- private native static boolean getBoxedBooleanAsBool(boolean v) /*-{
- return new Boolean(v);
- }-*/;
-
private native static JavaScriptObject getBoxedBooleanAsObject(boolean v) /*-{
return new Boolean(v);
}-*/;
-
- private native static double getBoxedNumberAsDouble(double v) /*-{
- return new Number(v);
- }-*/;
-
+
private native static JavaScriptObject getBoxedNumberAsObject(double v) /*-{
return new Number(v);
}-*/;
@@ -79,7 +106,7 @@
private native static String getBoxedStringAsString(String v) /*-{
return new String(v);
}-*/;
-
+
private native static double getDouble(double v) /*-{
return -v;
}-*/;
@@ -87,11 +114,11 @@
private static native float getFloat() /*-{
return myFloatValue;
}-*/;
-
+
private static native float getFloatString() /*-{
return Number(myFloatValue.toString());
}-*/;
-
+
private native static int getInt(int v) /*-{
return -v;
}-*/;
@@ -117,15 +144,15 @@
return s + "me";
}-*/;
- private native static int getStringLength(String s) /*-{
- return s.length;
- }-*/;
-
// ok to return JS string from an Object method
private static native Object getStringAsObject() /*-{
return "test";
}-*/;
+ private native static int getStringLength(String s) /*-{
+ return s.length;
+ }-*/;
+
private static native int passThroughInt(int val) /*-{
return val;
}-*/;
@@ -162,6 +189,7 @@
myFloatValue = f;
}-*/;
+ @Override
public String getModuleName() {
return "com.google.gwt.dev.jjs.CompilerSuite";
}
@@ -173,18 +201,15 @@
/*
* Test that returning JavaScript boxed primitives works as expected.
- * Currently only String is automatically unboxed, so Boolean and Number
- * are currently disabled.
+ * Note that Boolean and Number cannot be supported properly in web
+ * mode, so we do not support it in hosted mode and therefore do not
+ * test it here.
*/
public void testAutoBoxing() {
JavaScriptObject bvo = getBoxedBooleanAsObject(true);
assertEquals(getJSOAsString(bvo), "true");
- // boolean bv = getBoxedBooleanAsBool(true);
- // assertEquals(bv, true);
JavaScriptObject nvo = getBoxedNumberAsObject(42);
assertEquals(getJSOAsString(nvo), "42");
- // double nv = getBoxedNumberAsDouble(42);
- // assertEquals(nv, 42, 0);
JavaScriptObject svo = getBoxedStringAsObject("test");
assertEquals(getJSOAsString(svo), "test");
String sv = getBoxedStringAsString("test");
@@ -210,12 +235,31 @@
assertEquals(-125, byteAsInt(b));
}
+ public void testCovariant() {
+ TestCovariantSuper parent = new TestCovariantSuper();
+ TestCovariantChild child = new TestCovariantChild();
+ Object val1 = parent.foo("bar");
+ assertTrue(val1 instanceof String);
+ assertEquals("bar", val1);
+ String val2 = child.foo("bar");
+ assertEquals("bar", val2);
+ }
+
public void testEmbeddedNullsInStrings() {
String s = "Pre\u0000Post";
assertEquals(s.length(), getStringLength(s));
assertEquals(s + "me", getString(s));
}
+ public void testEnum() {
+ TestEnum val = enumSimple(TestEnum.VAL2);
+ assertEquals(TestEnum.VAL2, val);
+ int ord = enumValue(val);
+ assertEquals(TestEnum.VAL2.ordinal(), ord);
+ String name = enumName(val);
+ assertEquals(TestEnum.VAL2.name(), name);
+ }
+
public void testFloat() {
storeFloat(Float.MIN_VALUE);
float f = getFloat();
@@ -228,7 +272,7 @@
f = getFloatString();
assertTrue(f == Float.MAX_VALUE);
}
-
+
public void testFunctionCaching() {
assertEquals("barfoo", sFooCall("bar"));
assertEquals("barfoo", sFooDirect("bar"));
@@ -247,6 +291,28 @@
assertEquals(fooString, fooFuncToString());
}
+ public void testGenerics() {
+ String s = genericSimple("test");
+ assertEquals("test", s);
+ String v = genericGet(s);
+ assertEquals("test", v);
+ List<String> list = new ArrayList<String>();
+ list.add("foo");
+ Object obj = genericWildcard(list);
+ assertTrue(obj instanceof String);
+ assertEquals("foo", obj);
+ obj = genericSubtype("test");
+ List<Object> list2 = genericSubtype(new GenericListTest());
+ assertTrue(list2 instanceof GenericListTest);
+ assertEquals(42, list2.size());
+ assertEquals(list2, list2.get(0));
+ String[] array = new String[] { "foo", "bar" };
+ String[] ret = genericArray(array);
+ assertEquals(2, ret.length);
+ assertEquals("bar", ret[1]);
+ assertTrue(Arrays.deepEquals(array, ret));
+ }
+
/**
* Tests that we are able to use binary and source level names when referencing
* a Java identifier from JSNI.
@@ -279,6 +345,7 @@
*/
public void testJSNIToStringResolution() {
class Foo {
+ @Override
public String toString() {
return "FOO";
}
@@ -309,14 +376,17 @@
assertEquals(f.c(), "blah");
Foo fo = new Foo() {
+ @Override
native String a() /*-{
return "oblah";
}-*/;
+ @Override
native String b() /*-{
return this.@com.google.gwt.dev.jjs.test.HostedTest$2Foo::a()();
}-*/;
+ @Override
native String c() /*-{
return this.@com.google.gwt.dev.jjs.test.HostedTest$1::a()();
}-*/;
@@ -351,6 +421,19 @@
}
}
+ public void testVarargs() {
+ String[] strs = varargsHelper("foo", "bar");
+ assertEquals(2, strs.length);
+ assertEquals("bar", strs[1]);
+ // TODO: not sure if we want to support this or not.
+ // strs = varargsFromJS1();
+ // assertEquals(2, strs.length);
+ // assertEquals("bar", strs[1]);
+ strs = varargsFromJS2(strs);
+ assertEquals(2, strs.length);
+ assertEquals("bar", strs[1]);
+ }
+
String foo(String s) {
return s + "foo";
}
@@ -363,6 +446,18 @@
return obj.toString();
}-*/;
+ private native String enumName(TestEnum val) /*-{
+ return val.@com.google.gwt.dev.jjs.test.HostedTest.TestEnum::name()();
+ }-*/;
+
+ private native TestEnum enumSimple(TestEnum val) /*-{
+ return val;
+ }-*/;
+
+ private native int enumValue(TestEnum val) /*-{
+ return val.@com.google.gwt.dev.jjs.test.HostedTest.TestEnum::ordinal()();
+ }-*/;
+
private native String fooCall(String s) /*-{
var f = this.@com.google.gwt.dev.jjs.test.HostedTest::foo(Ljava/lang/String;);
return f.call(this, s);
@@ -386,6 +481,38 @@
return fooFunc.call(this, s);
}-*/;
+ // Make this a JSNI method calling the Java method when that is implemented.
+ private native <T> T[] genericArray(T[] array) /*-{
+ // return genericPassthrough(array);
+ return this.@com.google.gwt.dev.jjs.test.HostedTest::genericPassthrough([Ljava/lang/Object;)(array);
+ }-*/;
+
+ /*
+ * Since we can't generate a generic instance from within JS, K and V
+ * have to actually be compatible.
+ */
+ private native <K,V> V genericGet(K key) /*-{
+ return key;
+ }-*/;
+
+ @SuppressWarnings("unused") // called by JSNI
+ private <T> T[] genericPassthrough(T[] array) {
+ return array;
+ }
+
+ // generics helper methods
+ private native <T> T genericSimple(T val) /*-{
+ return val;
+ }-*/;
+
+ private native <T,U extends T> T genericSubtype(U val) /*-{
+ return val;
+ }-*/;
+
+ private native Object genericWildcard(List<?> list) /*-{
+ return list.@java.util.List::get(I)(0);
+ }-*/;
+
private native JavaScriptObject getFooFunc() /*-{
return this.@com.google.gwt.dev.jjs.test.HostedTest::foo(Ljava/lang/String;);
}-*/;
@@ -407,11 +534,11 @@
/*-{}-*/;
/**
- * comment
+ * comment.
*/
private native void jsniE()/*-{}-*/;
-
- /** comment */
+
+ /** comment. */
private native void jsniF()/*-{}-*/;
/** comment */private native void jsniG()/*-{}-*/;
@@ -432,8 +559,27 @@
jsniK()
/*-{
}-*/;
-
+
/*-{ try to mess with compiler }-*/
private native void jsniL()/*-{}-*/ ;
+
+ // test that JS can pass a series of arguments to a varargs function
+ private native String[] varargsFromJS1() /*-{
+ return this.@com.google.gwt.dev.jjs.test.HostedTest::varargsPassthrough([Ljava/lang/String;)("foo", "bar");
+ }-*/;
+
+ // test that JS can pass a Java-created array to a varargs function
+ private native String[] varargsFromJS2(String[] arr) /*-{
+ return this.@com.google.gwt.dev.jjs.test.HostedTest::varargsPassthrough([Ljava/lang/String;)(arr);
+ }-*/;
+
+ private native String[] varargsHelper(String... args) /*-{
+ return args;
+ }-*/;
+
+ @SuppressWarnings("unused") // called from JSNI
+ private String[] varargsPassthrough(String... args) {
+ return args;
+ }
}
diff --git a/user/test/com/google/gwt/user/server/rpc/RPCTest.java b/user/test/com/google/gwt/user/server/rpc/RPCTest.java
index fc8e00f..ab9b7ec 100644
--- a/user/test/com/google/gwt/user/server/rpc/RPCTest.java
+++ b/user/test/com/google/gwt/user/server/rpc/RPCTest.java
@@ -159,12 +159,12 @@
// Case 3
RPCRequest request;
request = RPC.decodeRequest(VALID_ENCODED_REQUEST, null);
- assertEquals(A.class.getMethod("method2", null), request.getMethod());
+ assertEquals(A.class.getMethod("method2"), request.getMethod());
assertTrue(request.getParameters().length == 0);
// Case 4
request = RPC.decodeRequest(VALID_ENCODED_REQUEST, A.class);
- assertEquals(A.class.getMethod("method2", null), request.getMethod());
+ assertEquals(A.class.getMethod("method2"), request.getMethod());
assertTrue(request.getParameters().length == 0);
// Case 5
@@ -219,7 +219,7 @@
RPC.encodeResponseForFailure(null, new SerializableException());
Method A_method1 = null;
- A_method1 = A.class.getMethod("method1", null);
+ A_method1 = A.class.getMethod("method1");
// Case 2
try {
@@ -231,7 +231,7 @@
// Case 3
try {
- RPC.encodeResponseForFailure(A.class.getMethod("method1", null),
+ RPC.encodeResponseForFailure(A.class.getMethod("method1"),
new IllegalArgumentException());
fail("Expected UnexpectedException");
} catch (UnexpectedException e) {
@@ -240,7 +240,7 @@
// Case 4
String str = RPC.encodeResponseForFailure(
- A.class.getMethod("method1", null), new SerializableException());
+ A.class.getMethod("method1"), new SerializableException());
assertTrue(str.indexOf("SerializableException") != -1);
}
@@ -263,8 +263,8 @@
SecurityException, NoSuchMethodException {
Method A_method1 = null;
Method A_method2 = null;
- A_method1 = A.class.getMethod("method1", null);
- A_method2 = A.class.getMethod("method2", null);
+ A_method1 = A.class.getMethod("method1");
+ A_method2 = A.class.getMethod("method2");
// Case 1
try {
@@ -316,7 +316,7 @@
// expected to get here
}
- Method A_method1 = A.class.getMethod("method1", null);
+ Method A_method1 = A.class.getMethod("method1");
// Case 2
try {