changeset 13901:45f9dbb93988

modified Kind.format() to avoid calling any user code (JBS:GRAAL-14)
author Doug Simon <doug.simon@oracle.com>
date Thu, 06 Feb 2014 23:14:06 +0100
parents d9aad522d355
children bdeadcd7101d
files graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Kind.java
diffstat 1 files changed, 18 insertions(+), 5 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Kind.java	Thu Feb 06 22:47:41 2014 +0100
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Kind.java	Thu Feb 06 23:14:06 2014 +0100
@@ -255,19 +255,30 @@
 
     /**
      * Marker interface for types that should be {@linkplain Kind#format(Object) formatted} with
-     * their {@link Object#toString()} value.
+     * their {@link Object#toString()} value. Calling {@link Object#toString()} on other objects
+     * poses a security risk because it can potentially call user code.
      */
     public interface FormatWithToString {
     }
 
     /**
+     * Classes for which invoking {@link Object#toString()} does not run user code.
+     */
+    private static boolean isToStringSafe(Class c) {
+        return c == Boolean.class || c == Byte.class || c == Character.class || c == Short.class || c == Integer.class || c == Float.class || c == Long.class || c == Double.class;
+    }
+
+    /**
      * Gets a formatted string for a given value of this kind.
      * 
      * @param value a value of this kind
      * @return a formatted string for {@code value} based on this kind
      */
     public String format(Object value) {
-        if (this == Kind.Object) {
+        if (isPrimitive()) {
+            assert isToStringSafe(value.getClass());
+            return value.toString();
+        } else {
             if (value == null) {
                 return "null";
             } else {
@@ -280,18 +291,20 @@
                     }
                 } else if (value instanceof JavaType) {
                     return "JavaType:" + MetaUtil.toJavaName((JavaType) value);
-                } else if (value instanceof Enum || value instanceof FormatWithToString || value instanceof Number) {
+                } else if (value instanceof Enum) {
+                    return MetaUtil.getSimpleName(value.getClass(), true) + ":" + ((Enum) value).name();
+                } else if (value instanceof FormatWithToString) {
                     return MetaUtil.getSimpleName(value.getClass(), true) + ":" + String.valueOf(value);
                 } else if (value instanceof Class<?>) {
                     return "Class:" + ((Class<?>) value).getName();
+                } else if (isToStringSafe(value.getClass())) {
+                    return value.toString();
                 } else if (value.getClass().isArray()) {
                     return formatArray(value);
                 } else {
                     return MetaUtil.getSimpleName(value.getClass(), true) + "@" + System.identityHashCode(value);
                 }
             }
-        } else {
-            return value.toString();
         }
     }