Merge

Tue, 03 Dec 2013 14:13:15 +0400

author
kizune
date
Tue, 03 Dec 2013 14:13:15 +0400
changeset 702
c1049f63d4f5
parent 701
b9fdc55a6e28
parent 675
b55a011cf8ae
child 703
39a3e5a4d6d4

Merge

     1.1 --- a/.hgtags	Sun Nov 03 07:33:34 2013 +0000
     1.2 +++ b/.hgtags	Tue Dec 03 14:13:15 2013 +0400
     1.3 @@ -224,3 +224,7 @@
     1.4  6a4fdb3bb4e34af4c5bb8db467bb01e13b1a7e31 jdk8-b112
     1.5  676cd7bf5e092356f7ee2116c8cf88cdc12377c7 jdk8-b113
     1.6  79f7b79bf97b71c9b5c9b103dbdef5f269eeb86d jdk8-b114
     1.7 +f0d3ac2474ee755b1180ec71bcdfa190845b17eb jdk8-b115
     1.8 +0fb1a427fbf6e04c77cebbbf99b6631c664ed793 jdk8-b116
     1.9 +1db3d4e4d18913e853d7bebf86816e87fda00a71 jdk8-b117
    1.10 +8d014b039b44c23fa520ce20c2c27f7aa91441e9 jdk8-b118
     2.1 --- a/make/build.xml	Sun Nov 03 07:33:34 2013 +0000
     2.2 +++ b/make/build.xml	Tue Dec 03 14:13:15 2013 +0400
     2.3 @@ -372,6 +372,12 @@
     2.4      
     2.5      <copy file="${file.reference.jfxrt.jar}" todir="dist"/>
     2.6      
     2.7 +    <condition property="jfx.prism.order" value="-Dprism.order=j2d" else=" ">
     2.8 +		<not>
     2.9 +            <os family="mac"/>
    2.10 +        </not>
    2.11 +	</condition>
    2.12 +    
    2.13      <testng outputdir="${build.test.results.dir}" classfilesetref="test.classes"
    2.14         verbose="${testng.verbose}" haltonfailure="true" useDefaultListeners="false" listeners="${testng.listeners}" workingDir="${basedir}">
    2.15        <jvmarg line="${ext.class.path}"/>
    2.16 @@ -380,6 +386,7 @@
    2.17          <propertyref prefix="testjfx-test-sys-prop."/>
    2.18          <mapper from="testjfx-test-sys-prop.*" to="*" type="glob"/>
    2.19        </propertyset>
    2.20 +      <sysproperty key="test.fork.jvm.options" value="${testjfx-test-sys-prop.test.fork.jvm.options} ${jfx.prism.order}"/>
    2.21        <classpath>
    2.22            <pathelement path="${testjfx.run.test.classpath}"/>
    2.23        </classpath>
     3.1 --- a/make/project.properties	Sun Nov 03 07:33:34 2013 +0000
     3.2 +++ b/make/project.properties	Tue Dec 03 14:13:15 2013 +0400
     3.3 @@ -230,7 +230,7 @@
     3.4      ${file.reference.jemmyawtinput.jar}${path.separator}\
     3.5      ${file.reference.testng.jar}${path.separator}\
     3.6      ${nashorn.internal.tests.jar}${path.separator}\
     3.7 -    ${nashorn.api.tests.jar}    
     3.8 +    ${nashorn.api.tests.jar}
     3.9  
    3.10  # testjfx VM options for script tests with @fork option
    3.11  testjfx-test-sys-prop.test.fork.jvm.options=${run.test.jvmargs.main} -Xmx${run.test.xmx} -cp ${testjfx.run.test.classpath}
     4.1 --- a/src/jdk/nashorn/api/scripting/ScriptObjectMirror.java	Sun Nov 03 07:33:34 2013 +0000
     4.2 +++ b/src/jdk/nashorn/api/scripting/ScriptObjectMirror.java	Tue Dec 03 14:13:15 2013 +0400
     4.3 @@ -41,6 +41,7 @@
     4.4  import java.util.Set;
     4.5  import java.util.concurrent.Callable;
     4.6  import javax.script.Bindings;
     4.7 +import jdk.nashorn.internal.runtime.ConsString;
     4.8  import jdk.nashorn.internal.runtime.Context;
     4.9  import jdk.nashorn.internal.runtime.GlobalObject;
    4.10  import jdk.nashorn.internal.runtime.JSType;
    4.11 @@ -594,14 +595,35 @@
    4.12      }
    4.13  
    4.14      /**
    4.15 -     * Make a script object mirror on given object if needed.
    4.16 +     * Utilitity to convert this script object to the given type.
    4.17       *
    4.18 -     * @param obj object to be wrapped
    4.19 -     * @param homeGlobal global to which this object belongs
    4.20 -     * @return wrapped object
    4.21 +     * @param type destination type to convert to
    4.22 +     * @return converted object
    4.23       */
    4.24 -    public static Object wrap(final Object obj, final ScriptObject homeGlobal) {
    4.25 -        return (obj instanceof ScriptObject && homeGlobal != null) ? new ScriptObjectMirror((ScriptObject)obj, homeGlobal) : obj;
    4.26 +    public <T> T to(final Class<T> type) {
    4.27 +        return inGlobal(new Callable<T>() {
    4.28 +            @Override
    4.29 +            public T call() {
    4.30 +                return type.cast(ScriptUtils.convert(sobj, type));
    4.31 +            }
    4.32 +        });
    4.33 +    }
    4.34 +
    4.35 +    /**
    4.36 +     * Make a script object mirror on given object if needed. Also converts ConsString instances to Strings.
    4.37 +     *
    4.38 +     * @param obj object to be wrapped/converted
    4.39 +     * @param homeGlobal global to which this object belongs. Not used for ConsStrings.
    4.40 +     * @return wrapped/converted object
    4.41 +     */
    4.42 +    public static Object wrap(final Object obj, final Object homeGlobal) {
    4.43 +        if(obj instanceof ScriptObject) {
    4.44 +            return homeGlobal instanceof ScriptObject ? new ScriptObjectMirror((ScriptObject)obj, (ScriptObject)homeGlobal) : obj;
    4.45 +        }
    4.46 +        if(obj instanceof ConsString) {
    4.47 +            return obj.toString();
    4.48 +        }
    4.49 +        return obj;
    4.50      }
    4.51  
    4.52      /**
    4.53 @@ -611,7 +633,7 @@
    4.54       * @param homeGlobal global to which this object belongs
    4.55       * @return unwrapped object
    4.56       */
    4.57 -    public static Object unwrap(final Object obj, final ScriptObject homeGlobal) {
    4.58 +    public static Object unwrap(final Object obj, final Object homeGlobal) {
    4.59          if (obj instanceof ScriptObjectMirror) {
    4.60              final ScriptObjectMirror mirror = (ScriptObjectMirror)obj;
    4.61              return (mirror.global == homeGlobal)? mirror.sobj : obj;
    4.62 @@ -627,7 +649,7 @@
    4.63       * @param homeGlobal global to which this object belongs
    4.64       * @return wrapped array
    4.65       */
    4.66 -    public static Object[] wrapArray(final Object[] args, final ScriptObject homeGlobal) {
    4.67 +    public static Object[] wrapArray(final Object[] args, final Object homeGlobal) {
    4.68          if (args == null || args.length == 0) {
    4.69              return args;
    4.70          }
    4.71 @@ -648,7 +670,7 @@
    4.72       * @param homeGlobal global to which this object belongs
    4.73       * @return unwrapped array
    4.74       */
    4.75 -    public static Object[] unwrapArray(final Object[] args, final ScriptObject homeGlobal) {
    4.76 +    public static Object[] unwrapArray(final Object[] args, final Object homeGlobal) {
    4.77          if (args == null || args.length == 0) {
    4.78              return args;
    4.79          }
     5.1 --- a/src/jdk/nashorn/api/scripting/ScriptUtils.java	Sun Nov 03 07:33:34 2013 +0000
     5.2 +++ b/src/jdk/nashorn/api/scripting/ScriptUtils.java	Tue Dec 03 14:13:15 2013 +0400
     5.3 @@ -25,11 +25,17 @@
     5.4  
     5.5  package jdk.nashorn.api.scripting;
     5.6  
     5.7 +import java.lang.invoke.MethodHandle;
     5.8 +import jdk.internal.dynalink.beans.StaticClass;
     5.9 +import jdk.internal.dynalink.linker.LinkerServices;
    5.10 +import jdk.nashorn.internal.runtime.linker.Bootstrap;
    5.11 +import jdk.nashorn.internal.runtime.Context;
    5.12  import jdk.nashorn.internal.runtime.ScriptFunction;
    5.13 +import jdk.nashorn.internal.runtime.ScriptObject;
    5.14  import jdk.nashorn.internal.runtime.ScriptRuntime;
    5.15  
    5.16  /**
    5.17 - * Utilities that are to be called from script code
    5.18 + * Utilities that are to be called from script code.
    5.19   */
    5.20  public final class ScriptUtils {
    5.21      private ScriptUtils() {}
    5.22 @@ -71,4 +77,96 @@
    5.23          return func.makeSynchronizedFunction(sync);
    5.24      }
    5.25  
    5.26 +    /**
    5.27 +     * Make a script object mirror on given object if needed.
    5.28 +     *
    5.29 +     * @param obj object to be wrapped
    5.30 +     * @return wrapped object
    5.31 +     */
    5.32 +    public static Object wrap(final Object obj) {
    5.33 +        if (obj instanceof ScriptObject) {
    5.34 +            return ScriptObjectMirror.wrap(obj, Context.getGlobal());
    5.35 +        }
    5.36 +
    5.37 +        return obj;
    5.38 +    }
    5.39 +
    5.40 +    /**
    5.41 +     * Unwrap a script object mirror if needed.
    5.42 +     *
    5.43 +     * @param obj object to be unwrapped
    5.44 +     * @return unwrapped object
    5.45 +     */
    5.46 +    public static Object unwrap(final Object obj) {
    5.47 +        if (obj instanceof ScriptObjectMirror) {
    5.48 +            return ScriptObjectMirror.unwrap(obj, Context.getGlobal());
    5.49 +        }
    5.50 +
    5.51 +        return obj;
    5.52 +    }
    5.53 +
    5.54 +    /**
    5.55 +     * Wrap an array of object to script object mirrors if needed.
    5.56 +     *
    5.57 +     * @param args array to be unwrapped
    5.58 +     * @return wrapped array
    5.59 +     */
    5.60 +    public static Object[] wrapArray(final Object[] args) {
    5.61 +        if (args == null || args.length == 0) {
    5.62 +            return args;
    5.63 +        }
    5.64 +
    5.65 +        return ScriptObjectMirror.wrapArray(args, Context.getGlobal());
    5.66 +    }
    5.67 +
    5.68 +    /**
    5.69 +     * Unwrap an array of script object mirrors if needed.
    5.70 +     *
    5.71 +     * @param args array to be unwrapped
    5.72 +     * @return unwrapped array
    5.73 +     */
    5.74 +    public static Object[] unwrapArray(final Object[] args) {
    5.75 +        if (args == null || args.length == 0) {
    5.76 +            return args;
    5.77 +        }
    5.78 +
    5.79 +        return ScriptObjectMirror.unwrapArray(args, Context.getGlobal());
    5.80 +    }
    5.81 +
    5.82 +    /**
    5.83 +     * Convert the given object to the given type.
    5.84 +     *
    5.85 +     * @param obj object to be converted
    5.86 +     * @param type destination type to convert to
    5.87 +     * @return converted object
    5.88 +     */
    5.89 +    public static Object convert(final Object obj, final Object type) {
    5.90 +        if (obj == null) {
    5.91 +            return null;
    5.92 +        }
    5.93 +
    5.94 +        final Class<?> clazz;
    5.95 +        if (type instanceof Class) {
    5.96 +            clazz = (Class<?>)type;
    5.97 +        } else if (type instanceof StaticClass) {
    5.98 +            clazz = ((StaticClass)type).getRepresentedClass();
    5.99 +        } else {
   5.100 +            throw new IllegalArgumentException("type expected");
   5.101 +        }
   5.102 +
   5.103 +        final LinkerServices linker = Bootstrap.getLinkerServices();
   5.104 +        final MethodHandle converter = linker.getTypeConverter(obj.getClass(),  clazz);
   5.105 +        if (converter == null) {
   5.106 +            // no supported conversion!
   5.107 +            throw new UnsupportedOperationException("conversion not supported");
   5.108 +        }
   5.109 +
   5.110 +        try {
   5.111 +            return converter.invoke(obj);
   5.112 +        } catch (final RuntimeException | Error e) {
   5.113 +            throw e;
   5.114 +        } catch (final Throwable t) {
   5.115 +            throw new RuntimeException(t);
   5.116 +        }
   5.117 +    }
   5.118  }
     6.1 --- a/src/jdk/nashorn/internal/codegen/Attr.java	Sun Nov 03 07:33:34 2013 +0000
     6.2 +++ b/src/jdk/nashorn/internal/codegen/Attr.java	Tue Dec 03 14:13:15 2013 +0400
     6.3 @@ -271,6 +271,7 @@
     6.4                      functionNode.addDeclaredSymbol(symbol);
     6.5                      if (varNode.isFunctionDeclaration()) {
     6.6                          newType(symbol, FunctionNode.FUNCTION_TYPE);
     6.7 +                        symbol.setIsFunctionDeclaration();
     6.8                      }
     6.9                      return varNode.setName((IdentNode)ident.setSymbol(lc, symbol));
    6.10                  }
    6.11 @@ -1264,12 +1265,17 @@
    6.12  
    6.13      @Override
    6.14      public Node leaveCOMMARIGHT(final BinaryNode binaryNode) {
    6.15 -        return end(ensureSymbol(binaryNode.rhs().getType(), binaryNode));
    6.16 +        return leaveComma(binaryNode, binaryNode.rhs());
    6.17      }
    6.18  
    6.19      @Override
    6.20      public Node leaveCOMMALEFT(final BinaryNode binaryNode) {
    6.21 -        return end(ensureSymbol(binaryNode.lhs().getType(), binaryNode));
    6.22 +        return leaveComma(binaryNode, binaryNode.lhs());
    6.23 +    }
    6.24 +
    6.25 +    private Node leaveComma(final BinaryNode commaNode, final Expression effectiveExpr) {
    6.26 +        ensureTypeNotUnknown(effectiveExpr);
    6.27 +        return end(ensureSymbol(effectiveExpr.getType(), commaNode));
    6.28      }
    6.29  
    6.30      @Override
     7.1 --- a/src/jdk/nashorn/internal/codegen/CodeGenerator.java	Sun Nov 03 07:33:34 2013 +0000
     7.2 +++ b/src/jdk/nashorn/internal/codegen/CodeGenerator.java	Tue Dec 03 14:13:15 2013 +0400
     7.3 @@ -359,8 +359,11 @@
     7.4          return load(node, node.hasType() ? node.getType() : null, false);
     7.5      }
     7.6  
     7.7 -    private static boolean safeLiteral(final Expression rhs) {
     7.8 -        return rhs instanceof LiteralNode && !(rhs instanceof ArrayLiteralNode);
     7.9 +    // Test whether conversion from source to target involves a call of ES 9.1 ToPrimitive
    7.10 +    // with possible side effects from calling an object's toString or valueOf methods.
    7.11 +    private boolean noToPrimitiveConversion(final Type source, final Type target) {
    7.12 +        // Object to boolean conversion does not cause ToPrimitive call
    7.13 +        return source.isJSPrimitive() || !target.isJSPrimitive() || target.isBoolean();
    7.14      }
    7.15  
    7.16      MethodEmitter loadBinaryOperands(final Expression lhs, final Expression rhs, final Type type) {
    7.17 @@ -374,25 +377,19 @@
    7.18          // can combine a LOAD with a CONVERT operation (e.g. use a dynamic getter with the conversion target type as its
    7.19          // return value). What we do here is reorder LOAD RIGHT and CONVERT LEFT when possible; it is possible only when
    7.20          // we can prove that executing CONVERT LEFT can't have a side effect that changes the value of LOAD RIGHT.
    7.21 -        // Basically, if we know that either LEFT is not an object, or RIGHT is a constant literal, then we can do the
    7.22 +        // Basically, if we know that either LEFT already is a primitive value, or does not have to be converted to
    7.23 +        // a primitive value, or RIGHT is an expression that loads without side effects, then we can do the
    7.24          // reordering and collapse LOAD/CONVERT into a single operation; otherwise we need to do the more costly
    7.25          // separate operations to preserve specification semantics.
    7.26 -        final Type lhsType = lhs.getType();
    7.27 -        if (lhsType.isObject() && !safeLiteral(rhs)) {
    7.28 -            // Can't reorder. Load and convert separately.
    7.29 -            load(lhs, lhsType, baseAlreadyOnStack);
    7.30 -            load(rhs, rhs.getType(), false);
    7.31 -            // Avoid empty SWAP, SWAP bytecode sequence if CONVERT LEFT is a no-op
    7.32 -            if (!lhsType.isEquivalentTo(type)) {
    7.33 -                method.swap();
    7.34 -                method.convert(type);
    7.35 -                method.swap();
    7.36 -            }
    7.37 -            method.convert(type);
    7.38 -        } else {
    7.39 +        if (noToPrimitiveConversion(lhs.getType(), type) || rhs.isLocal()) {
    7.40              // Can reorder. Combine load and convert into single operations.
    7.41              load(lhs, type, baseAlreadyOnStack);
    7.42              load(rhs, type, false);
    7.43 +        } else {
    7.44 +            // Can't reorder. Load and convert separately.
    7.45 +            load(lhs, lhs.getType(), baseAlreadyOnStack);
    7.46 +            load(rhs, rhs.getType(), false);
    7.47 +            method.swap().convert(type).swap().convert(type);
    7.48          }
    7.49  
    7.50          return method;
    7.51 @@ -415,6 +412,8 @@
    7.52              return method;
    7.53          }
    7.54  
    7.55 +        assert !type.isUnknown();
    7.56 +
    7.57          /*
    7.58           * The load may be of type IdentNode, e.g. "x", AccessNode, e.g. "x.y"
    7.59           * or IndexNode e.g. "x[y]". Both AccessNodes and IndexNodes are
    7.60 @@ -709,6 +708,12 @@
    7.61                  final CallNode.EvalArgs evalArgs = callNode.getEvalArgs();
    7.62                  // load evaluated code
    7.63                  load(evalArgs.getCode(), Type.OBJECT);
    7.64 +                // load second and subsequent args for side-effect
    7.65 +                final List<Expression> args = callNode.getArgs();
    7.66 +                final int numArgs = args.size();
    7.67 +                for (int i = 1; i < numArgs; i++) {
    7.68 +                    load(args.get(i)).pop();
    7.69 +                }
    7.70                  // special/extra 'eval' arguments
    7.71                  load(evalArgs.getThis());
    7.72                  method.load(evalArgs.getLocation());
     8.1 --- a/src/jdk/nashorn/internal/codegen/MapCreator.java	Sun Nov 03 07:33:34 2013 +0000
     8.2 +++ b/src/jdk/nashorn/internal/codegen/MapCreator.java	Tue Dec 03 14:13:15 2013 +0400
     8.3 @@ -134,6 +134,10 @@
     8.4              flags |= Property.CAN_BE_UNDEFINED;
     8.5          }
     8.6  
     8.7 +        if (symbol.isFunctionDeclaration()) {
     8.8 +            flags |= Property.IS_FUNCTION_DECLARATION;
     8.9 +        }
    8.10 +
    8.11          return flags;
    8.12      }
    8.13  
     9.1 --- a/src/jdk/nashorn/internal/codegen/types/Type.java	Sun Nov 03 07:33:34 2013 +0000
     9.2 +++ b/src/jdk/nashorn/internal/codegen/types/Type.java	Tue Dec 03 14:13:15 2013 +0400
     9.3 @@ -292,6 +292,16 @@
     9.4      }
     9.5  
     9.6      /**
     9.7 +     * Determines whether this type represents an primitive type according to the ECMAScript specification,
     9.8 +     * which includes Boolean, Number, and String.
     9.9 +     *
    9.10 +     * @return true if a JavaScript primitive type, false otherwise.
    9.11 +     */
    9.12 +    public boolean isJSPrimitive() {
    9.13 +        return !isObject() || isString();
    9.14 +    }
    9.15 +
    9.16 +    /**
    9.17       * Determines whether a type is the BOOLEAN type
    9.18       * @return true if BOOLEAN, false otherwise
    9.19       */
    9.20 @@ -443,7 +453,7 @@
    9.21          } else if (type0.isArray() != type1.isArray()) {
    9.22              //array and non array is always object, widest(Object[], int) NEVER returns Object[], which has most weight. that does not make sense
    9.23              return Type.OBJECT;
    9.24 -        } else if (type0.isObject() && type1.isObject() && ((ObjectType)type0).getTypeClass() != ((ObjectType)type1).getTypeClass()) {
    9.25 +        } else if (type0.isObject() && type1.isObject() && type0.getTypeClass() != type1.getTypeClass()) {
    9.26              // Object<type=String> and Object<type=ScriptFunction> will produce Object
    9.27              // TODO: maybe find most specific common superclass?
    9.28              return Type.OBJECT;
    10.1 --- a/src/jdk/nashorn/internal/ir/BinaryNode.java	Sun Nov 03 07:33:34 2013 +0000
    10.2 +++ b/src/jdk/nashorn/internal/ir/BinaryNode.java	Tue Dec 03 14:13:15 2013 +0400
    10.3 @@ -90,6 +90,9 @@
    10.4              return Type.LONG;
    10.5          case ASSIGN_SAR:
    10.6          case ASSIGN_SHL:
    10.7 +        case BIT_AND:
    10.8 +        case BIT_OR:
    10.9 +        case BIT_XOR:
   10.10          case ASSIGN_BIT_AND:
   10.11          case ASSIGN_BIT_OR:
   10.12          case ASSIGN_BIT_XOR:
   10.13 @@ -170,6 +173,42 @@
   10.14      }
   10.15  
   10.16      @Override
   10.17 +    public boolean isLocal() {
   10.18 +        switch (tokenType()) {
   10.19 +        case SAR:
   10.20 +        case SHL:
   10.21 +        case SHR:
   10.22 +        case BIT_AND:
   10.23 +        case BIT_OR:
   10.24 +        case BIT_XOR:
   10.25 +        case ADD:
   10.26 +        case DIV:
   10.27 +        case MOD:
   10.28 +        case MUL:
   10.29 +        case SUB:
   10.30 +            return lhs.isLocal() && lhs.getType().isJSPrimitive()
   10.31 +                && rhs.isLocal() && rhs.getType().isJSPrimitive();
   10.32 +        case ASSIGN_ADD:
   10.33 +        case ASSIGN_BIT_AND:
   10.34 +        case ASSIGN_BIT_OR:
   10.35 +        case ASSIGN_BIT_XOR:
   10.36 +        case ASSIGN_DIV:
   10.37 +        case ASSIGN_MOD:
   10.38 +        case ASSIGN_MUL:
   10.39 +        case ASSIGN_SAR:
   10.40 +        case ASSIGN_SHL:
   10.41 +        case ASSIGN_SHR:
   10.42 +        case ASSIGN_SUB:
   10.43 +            return lhs instanceof IdentNode && lhs.isLocal() && lhs.getType().isJSPrimitive()
   10.44 +                    && rhs.isLocal() && rhs.getType().isJSPrimitive();
   10.45 +        case ASSIGN:
   10.46 +            return lhs instanceof IdentNode && lhs.isLocal() && rhs.isLocal();
   10.47 +        default:
   10.48 +            return false;
   10.49 +        }
   10.50 +    }
   10.51 +
   10.52 +    @Override
   10.53      public void toString(final StringBuilder sb) {
   10.54          final TokenType type = tokenType();
   10.55  
    11.1 --- a/src/jdk/nashorn/internal/ir/Expression.java	Sun Nov 03 07:33:34 2013 +0000
    11.2 +++ b/src/jdk/nashorn/internal/ir/Expression.java	Tue Dec 03 14:13:15 2013 +0400
    11.3 @@ -96,4 +96,16 @@
    11.4          assert hasType() : this + " has no type";
    11.5          return symbol.getSymbolType();
    11.6      }
    11.7 +
    11.8 +    /**
    11.9 +     * Returns {@code true} if this expression depends exclusively on state that is constant
   11.10 +     * or local to the currently running function and thus inaccessible to other functions.
   11.11 +     * This implies that a local expression must not call any other functions (neither directly
   11.12 +     * nor implicitly through a getter, setter, or object-to-primitive type conversion).
   11.13 +     *
   11.14 +     * @return true if this expression does not depend on state shared with other functions.
   11.15 +     */
   11.16 +    public boolean isLocal() {
   11.17 +        return false;
   11.18 +    }
   11.19  }
    12.1 --- a/src/jdk/nashorn/internal/ir/IdentNode.java	Sun Nov 03 07:33:34 2013 +0000
    12.2 +++ b/src/jdk/nashorn/internal/ir/IdentNode.java	Tue Dec 03 14:13:15 2013 +0400
    12.3 @@ -138,6 +138,11 @@
    12.4          return getName();
    12.5      }
    12.6  
    12.7 +    @Override
    12.8 +    public boolean isLocal() {
    12.9 +        return !getSymbol().isScope();
   12.10 +    }
   12.11 +
   12.12      /**
   12.13       * Check if this IdentNode is a property name
   12.14       * @return true if this is a property name
    13.1 --- a/src/jdk/nashorn/internal/ir/LiteralNode.java	Sun Nov 03 07:33:34 2013 +0000
    13.2 +++ b/src/jdk/nashorn/internal/ir/LiteralNode.java	Tue Dec 03 14:13:15 2013 +0400
    13.3 @@ -275,6 +275,11 @@
    13.4          public boolean isTrue() {
    13.5              return JSType.toBoolean(value);
    13.6          }
    13.7 +
    13.8 +        @Override
    13.9 +        public boolean isLocal() {
   13.10 +            return true;
   13.11 +        }
   13.12      }
   13.13  
   13.14      @Immutable
    14.1 --- a/src/jdk/nashorn/internal/ir/Symbol.java	Sun Nov 03 07:33:34 2013 +0000
    14.2 +++ b/src/jdk/nashorn/internal/ir/Symbol.java	Tue Dec 03 14:13:15 2013 +0400
    14.3 @@ -75,6 +75,8 @@
    14.4      public static final int IS_SPECIALIZED_PARAM = 1 << 13;
    14.5      /** Is this symbol a shared temporary? */
    14.6      public static final int IS_SHARED            = 1 << 14;
    14.7 +    /** Is this a function declaration? */
    14.8 +    public static final int IS_FUNCTION_DECLARATION = 1 << 15;
    14.9  
   14.10      /** Null or name identifying symbol. */
   14.11      private final String name;
   14.12 @@ -360,6 +362,14 @@
   14.13      }
   14.14  
   14.15      /**
   14.16 +     * Check if this symbol is a function declaration
   14.17 +     * @return true if a function declaration
   14.18 +     */
   14.19 +    public boolean isFunctionDeclaration() {
   14.20 +        return (flags & IS_FUNCTION_DECLARATION) == IS_FUNCTION_DECLARATION;
   14.21 +    }
   14.22 +
   14.23 +    /**
   14.24       * Creates an unshared copy of a symbol. The symbol must be currently shared.
   14.25       * @param newName the name for the new symbol.
   14.26       * @return a new, unshared symbol.
   14.27 @@ -396,6 +406,16 @@
   14.28  
   14.29  
   14.30      /**
   14.31 +     * Mark this symbol as a function declaration.
   14.32 +     */
   14.33 +    public void setIsFunctionDeclaration() {
   14.34 +        if (!isFunctionDeclaration()) {
   14.35 +            trace("SET IS FUNCTION DECLARATION");
   14.36 +            flags |= IS_FUNCTION_DECLARATION;
   14.37 +        }
   14.38 +    }
   14.39 +
   14.40 +    /**
   14.41       * Check if this symbol is a variable
   14.42       * @return true if variable
   14.43       */
    15.1 --- a/src/jdk/nashorn/internal/ir/TernaryNode.java	Sun Nov 03 07:33:34 2013 +0000
    15.2 +++ b/src/jdk/nashorn/internal/ir/TernaryNode.java	Tue Dec 03 14:13:15 2013 +0400
    15.3 @@ -109,6 +109,13 @@
    15.4          }
    15.5      }
    15.6  
    15.7 +    @Override
    15.8 +    public boolean isLocal() {
    15.9 +        return getTest().isLocal()
   15.10 +                && getTrueExpression().isLocal()
   15.11 +                && getFalseExpression().isLocal();
   15.12 +    }
   15.13 +
   15.14      /**
   15.15       * Get the test expression for this ternary expression, i.e. "x" in x ? y : z
   15.16       * @return the test expression
    16.1 --- a/src/jdk/nashorn/internal/ir/UnaryNode.java	Sun Nov 03 07:33:34 2013 +0000
    16.2 +++ b/src/jdk/nashorn/internal/ir/UnaryNode.java	Tue Dec 03 14:13:15 2013 +0400
    16.3 @@ -129,6 +129,26 @@
    16.4      }
    16.5  
    16.6      @Override
    16.7 +    public boolean isLocal() {
    16.8 +        switch (tokenType()) {
    16.9 +            case NEW:
   16.10 +                return false;
   16.11 +            case ADD:
   16.12 +            case SUB:
   16.13 +            case NOT:
   16.14 +            case BIT_NOT:
   16.15 +                return rhs.isLocal() && rhs.getType().isJSPrimitive();
   16.16 +            case DECPOSTFIX:
   16.17 +            case DECPREFIX:
   16.18 +            case INCPOSTFIX:
   16.19 +            case INCPREFIX:
   16.20 +                return rhs instanceof IdentNode && rhs.isLocal() && rhs.getType().isJSPrimitive();
   16.21 +            default:
   16.22 +                return rhs.isLocal();
   16.23 +        }
   16.24 +    }
   16.25 +
   16.26 +    @Override
   16.27      public void toString(final StringBuilder sb) {
   16.28          toString(sb, new Runnable() {
   16.29              @Override
    17.1 --- a/src/jdk/nashorn/internal/ir/debug/ObjectSizeCalculator.java	Sun Nov 03 07:33:34 2013 +0000
    17.2 +++ b/src/jdk/nashorn/internal/ir/debug/ObjectSizeCalculator.java	Tue Dec 03 14:13:15 2013 +0400
    17.3 @@ -25,10 +25,10 @@
    17.4  
    17.5  package jdk.nashorn.internal.ir.debug;
    17.6  
    17.7 -import java.lang.management.ManagementFactory;
    17.8 -import java.lang.management.MemoryPoolMXBean;
    17.9  import java.lang.reflect.Array;
   17.10  import java.lang.reflect.Field;
   17.11 +import java.lang.reflect.InvocationTargetException;
   17.12 +import java.lang.reflect.Method;
   17.13  import java.lang.reflect.Modifier;
   17.14  import java.util.ArrayDeque;
   17.15  import java.util.ArrayList;
   17.16 @@ -51,9 +51,9 @@
   17.17   * switch, it can not detect
   17.18   * this fact and will report incorrect sizes, as it will presume the default JVM
   17.19   * behavior.
   17.20 - *
   17.21 - * @author Attila Szegedi
   17.22   */
   17.23 +
   17.24 +@SuppressWarnings("StaticNonFinalUsedInInitialization")
   17.25  public class ObjectSizeCalculator {
   17.26  
   17.27      /**
   17.28 @@ -368,6 +368,29 @@
   17.29                  type.getName());
   17.30      }
   17.31  
   17.32 +    // ALERT: java.lang.management is not available in compact 1.  We need
   17.33 +    // to use reflection to soft link test memory statistics.
   17.34 +
   17.35 +    static Class<?>  managementFactory    = null;
   17.36 +    static Class<?>  memoryPoolMXBean     = null;
   17.37 +    static Class<?>  memoryUsage          = null;
   17.38 +    static Method    getMemoryPoolMXBeans = null;
   17.39 +    static Method    getUsage             = null;
   17.40 +    static Method    getMax               = null;
   17.41 +    static {
   17.42 +        try {
   17.43 +            managementFactory    = Class.forName("java.lang.management.ManagementFactory");
   17.44 +            memoryPoolMXBean     = Class.forName("java.lang.management.MemoryPoolMXBean");
   17.45 +            memoryUsage          = Class.forName("java.lang.management.MemoryUsage");
   17.46 +
   17.47 +            getMemoryPoolMXBeans = managementFactory.getMethod("getMemoryPoolMXBeans");
   17.48 +            getUsage             = memoryPoolMXBean.getMethod("getUsage");
   17.49 +            getMax               = memoryUsage.getMethod("getMax");
   17.50 +        } catch (ClassNotFoundException | NoSuchMethodException | SecurityException ex) {
   17.51 +            // Pass thru, asserts when attempting to use.
   17.52 +        }
   17.53 +    }
   17.54 +
   17.55      /**
   17.56       * Return the current memory usage
   17.57       * @return current memory usage derived from system configuration
   17.58 @@ -409,9 +432,33 @@
   17.59                  strVmVersion.indexOf('.')));
   17.60          if (vmVersion >= 17) {
   17.61              long maxMemory = 0;
   17.62 -            for (MemoryPoolMXBean mp : ManagementFactory.getMemoryPoolMXBeans()) {
   17.63 -                maxMemory += mp.getUsage().getMax();
   17.64 +
   17.65 +            /*
   17.66 +               See ALERT above.  The reflection code below duplicates the following
   17.67 +               sequence, and avoids hard coding of java.lang.management.
   17.68 +
   17.69 +               for (MemoryPoolMXBean mp : ManagementFactory.getMemoryPoolMXBeans()) {
   17.70 +                   maxMemory += mp.getUsage().getMax();
   17.71 +               }
   17.72 +            */
   17.73 +
   17.74 +            if (getMemoryPoolMXBeans == null) {
   17.75 +                throw new AssertionError("java.lang.management not available in compact 1");
   17.76              }
   17.77 +
   17.78 +            try {
   17.79 +                final List<?> memoryPoolMXBeans = (List<?>)getMemoryPoolMXBeans.invoke(managementFactory);
   17.80 +                for (final Object mp : memoryPoolMXBeans) {
   17.81 +                    final Object usage = getUsage.invoke(mp);
   17.82 +                    final Object max = getMax.invoke(usage);
   17.83 +                    maxMemory += ((Long)max).longValue();
   17.84 +                }
   17.85 +            } catch (IllegalAccessException |
   17.86 +                     IllegalArgumentException |
   17.87 +                     InvocationTargetException ex) {
   17.88 +                throw new AssertionError("java.lang.management not available in compact 1");
   17.89 +            }
   17.90 +
   17.91              if (maxMemory < 30L * 1024 * 1024 * 1024) {
   17.92                  // HotSpot 17.0 and above use compressed OOPs below 30GB of RAM total
   17.93                  // for all memory pools (yes, including code cache).
    18.1 --- a/src/jdk/nashorn/internal/objects/Global.java	Sun Nov 03 07:33:34 2013 +0000
    18.2 +++ b/src/jdk/nashorn/internal/objects/Global.java	Tue Dec 03 14:13:15 2013 +0400
    18.3 @@ -53,19 +53,19 @@
    18.4  import jdk.nashorn.internal.runtime.GlobalObject;
    18.5  import jdk.nashorn.internal.runtime.JSType;
    18.6  import jdk.nashorn.internal.runtime.NativeJavaPackage;
    18.7 +import jdk.nashorn.internal.runtime.PropertyDescriptor;
    18.8  import jdk.nashorn.internal.runtime.PropertyMap;
    18.9 +import jdk.nashorn.internal.runtime.Scope;
   18.10  import jdk.nashorn.internal.runtime.ScriptEnvironment;
   18.11 -import jdk.nashorn.internal.runtime.PropertyDescriptor;
   18.12 -import jdk.nashorn.internal.runtime.arrays.ArrayData;
   18.13 -import jdk.nashorn.internal.runtime.regexp.RegExpResult;
   18.14 -import jdk.nashorn.internal.runtime.Scope;
   18.15  import jdk.nashorn.internal.runtime.ScriptFunction;
   18.16  import jdk.nashorn.internal.runtime.ScriptObject;
   18.17  import jdk.nashorn.internal.runtime.ScriptRuntime;
   18.18  import jdk.nashorn.internal.runtime.ScriptingFunctions;
   18.19  import jdk.nashorn.internal.runtime.Source;
   18.20 +import jdk.nashorn.internal.runtime.arrays.ArrayData;
   18.21  import jdk.nashorn.internal.runtime.linker.Bootstrap;
   18.22  import jdk.nashorn.internal.runtime.linker.InvokeByName;
   18.23 +import jdk.nashorn.internal.runtime.regexp.RegExpResult;
   18.24  import jdk.nashorn.internal.scripts.JO;
   18.25  
   18.26  /**
    19.1 --- a/src/jdk/nashorn/internal/objects/NativeObject.java	Sun Nov 03 07:33:34 2013 +0000
    19.2 +++ b/src/jdk/nashorn/internal/objects/NativeObject.java	Tue Dec 03 14:13:15 2013 +0400
    19.3 @@ -60,6 +60,7 @@
    19.4  import jdk.nashorn.internal.runtime.ScriptRuntime;
    19.5  import jdk.nashorn.internal.runtime.linker.Bootstrap;
    19.6  import jdk.nashorn.internal.runtime.linker.InvokeByName;
    19.7 +import jdk.nashorn.internal.runtime.linker.NashornBeansLinker;
    19.8  
    19.9  /**
   19.10   * ECMA 15.2 Object objects
   19.11 @@ -729,8 +730,7 @@
   19.12              final MethodType methodType, final Object source) {
   19.13          final GuardedInvocation inv;
   19.14          try {
   19.15 -            inv = linker.getGuardedInvocation(createLinkRequest(operation, methodType, source),
   19.16 -                Bootstrap.getLinkerServices());
   19.17 +            inv = NashornBeansLinker.getGuardedInvocation(linker, createLinkRequest(operation, methodType, source), Bootstrap.getLinkerServices());
   19.18              assert passesGuard(source, inv.getGuard());
   19.19          } catch(RuntimeException|Error e) {
   19.20              throw e;
    20.1 --- a/src/jdk/nashorn/internal/runtime/CompiledFunctions.java	Sun Nov 03 07:33:34 2013 +0000
    20.2 +++ b/src/jdk/nashorn/internal/runtime/CompiledFunctions.java	Tue Dec 03 14:13:15 2013 +0400
    20.3 @@ -24,6 +24,7 @@
    20.4   */
    20.5  package jdk.nashorn.internal.runtime;
    20.6  
    20.7 +import java.lang.invoke.MethodHandle;
    20.8  import java.lang.invoke.MethodType;
    20.9  import java.util.Iterator;
   20.10  import java.util.TreeSet;
   20.11 @@ -35,6 +36,8 @@
   20.12  @SuppressWarnings("serial")
   20.13  final class CompiledFunctions extends TreeSet<CompiledFunction> {
   20.14  
   20.15 +    private CompiledFunction generic;
   20.16 +
   20.17      CompiledFunction best(final MethodType type) {
   20.18          final Iterator<CompiledFunction> iter = iterator();
   20.19          while (iter.hasNext()) {
   20.20 @@ -43,13 +46,10 @@
   20.21                  return next;
   20.22              }
   20.23          }
   20.24 -        return mostGeneric();
   20.25 +        return generic();
   20.26      }
   20.27  
   20.28      boolean needsCallee() {
   20.29 -        for (final CompiledFunction inv : this) {
   20.30 -            assert ScriptFunctionData.needsCallee(inv.getInvoker()) == ScriptFunctionData.needsCallee(mostGeneric().getInvoker());
   20.31 -        }
   20.32          return ScriptFunctionData.needsCallee(mostGeneric().getInvoker());
   20.33      }
   20.34  
   20.35 @@ -57,6 +57,48 @@
   20.36          return last();
   20.37      }
   20.38  
   20.39 +    CompiledFunction generic() {
   20.40 +        CompiledFunction gen = this.generic;
   20.41 +        if (gen == null) {
   20.42 +            gen = this.generic = makeGeneric(mostGeneric());
   20.43 +        }
   20.44 +        return gen;
   20.45 +    }
   20.46 +
   20.47 +    private static CompiledFunction makeGeneric(final CompiledFunction func) {
   20.48 +        final MethodHandle invoker = composeGenericMethod(func.getInvoker());
   20.49 +        final MethodHandle constructor = func.hasConstructor() ? composeGenericMethod(func.getConstructor()) : null;
   20.50 +        return new CompiledFunction(invoker.type(), invoker, constructor);
   20.51 +    }
   20.52 +
   20.53 +    /**
   20.54 +     * Takes a method handle, and returns a potentially different method handle that can be used in
   20.55 +     * {@code ScriptFunction#invoke(Object, Object...)} or {code ScriptFunction#construct(Object, Object...)}.
   20.56 +     * The returned method handle will be sure to return {@code Object}, and will have all its parameters turned into
   20.57 +     * {@code Object} as well, except for the following ones:
   20.58 +     * <ul>
   20.59 +     *   <li>a last parameter of type {@code Object[]} which is used for vararg functions,</li>
   20.60 +     *   <li>the first argument, which is forced to be {@link ScriptFunction}, in case the function receives itself
   20.61 +     *   (callee) as an argument.</li>
   20.62 +     * </ul>
   20.63 +     *
   20.64 +     * @param mh the original method handle
   20.65 +     *
   20.66 +     * @return the new handle, conforming to the rules above.
   20.67 +     */
   20.68 +    private static MethodHandle composeGenericMethod(final MethodHandle mh) {
   20.69 +        final MethodType type = mh.type();
   20.70 +        final boolean isVarArg = ScriptFunctionData.isVarArg(mh);
   20.71 +        final int paramCount = isVarArg ? type.parameterCount() - 1 : type.parameterCount();
   20.72 +
   20.73 +        MethodType newType = MethodType.genericMethodType(paramCount, isVarArg);
   20.74 +
   20.75 +        if (ScriptFunctionData.needsCallee(mh)) {
   20.76 +            newType = newType.changeParameterType(0, ScriptFunction.class);
   20.77 +        }
   20.78 +        return type.equals(newType) ? mh : mh.asType(newType);
   20.79 +    }
   20.80 +
   20.81      /**
   20.82       * Is the given type even more specific than this entire list? That means
   20.83       * we have an opportunity for more specific versions of the method
    21.1 --- a/src/jdk/nashorn/internal/runtime/ConsString.java	Sun Nov 03 07:33:34 2013 +0000
    21.2 +++ b/src/jdk/nashorn/internal/runtime/ConsString.java	Tue Dec 03 14:13:15 2013 +0400
    21.3 @@ -57,10 +57,7 @@
    21.4  
    21.5      @Override
    21.6      public String toString() {
    21.7 -        if (!flat) {
    21.8 -            flatten();
    21.9 -        }
   21.10 -        return (String) left;
   21.11 +        return (String) flattened();
   21.12      }
   21.13  
   21.14      @Override
   21.15 @@ -70,18 +67,19 @@
   21.16  
   21.17      @Override
   21.18      public char charAt(final int index) {
   21.19 -        if (!flat) {
   21.20 -            flatten();
   21.21 -        }
   21.22 -        return left.charAt(index);
   21.23 +        return flattened().charAt(index);
   21.24      }
   21.25  
   21.26      @Override
   21.27      public CharSequence subSequence(final int start, final int end) {
   21.28 +        return flattened().subSequence(start, end);
   21.29 +    }
   21.30 +
   21.31 +    private CharSequence flattened() {
   21.32          if (!flat) {
   21.33              flatten();
   21.34          }
   21.35 -        return left.subSequence(start, end);
   21.36 +        return left;
   21.37      }
   21.38  
   21.39      private void flatten() {
    22.1 --- a/src/jdk/nashorn/internal/runtime/FinalScriptFunctionData.java	Sun Nov 03 07:33:34 2013 +0000
    22.2 +++ b/src/jdk/nashorn/internal/runtime/FinalScriptFunctionData.java	Tue Dec 03 14:13:15 2013 +0400
    22.3 @@ -40,7 +40,7 @@
    22.4       *
    22.5       * @param name          name
    22.6       * @param arity         arity
    22.7 -     * @param list          precompiled code
    22.8 +     * @param functions     precompiled code
    22.9       * @param isStrict      strict
   22.10       * @param isBuiltin     builtin
   22.11       * @param isConstructor constructor
   22.12 @@ -73,12 +73,13 @@
   22.13      }
   22.14  
   22.15      private void addInvoker(final MethodHandle mh) {
   22.16 -        boolean needsCallee = needsCallee(mh);
   22.17          if (isConstructor(mh)) {
   22.18 -            //only nasgen constructors: (boolean, self, args) are subject to binding a boolean newObj. isConstructor
   22.19 -            //is too conservative a check. However, isConstructor(mh) always implies isConstructor param
   22.20 +            // only nasgen constructors: (boolean, self, args) are subject to binding a boolean newObj. isConstructor
   22.21 +            // is too conservative a check. However, isConstructor(mh) always implies isConstructor param
   22.22              assert isConstructor();
   22.23 -            code.add(new CompiledFunction(mh.type(), MH.insertArguments(mh, 0, false), composeConstructor(MH.insertArguments(mh, 0, true), needsCallee))); //make sure callee state can be determined when we reach constructor
   22.24 +            final MethodHandle invoker = MH.insertArguments(mh, 0, false);
   22.25 +            final MethodHandle constructor = composeConstructor(MH.insertArguments(mh, 0, true));
   22.26 +            code.add(new CompiledFunction(mh.type(), invoker, constructor));
   22.27          } else {
   22.28              code.add(new CompiledFunction(mh.type(), mh));
   22.29          }
    23.1 --- a/src/jdk/nashorn/internal/runtime/JSType.java	Sun Nov 03 07:33:34 2013 +0000
    23.2 +++ b/src/jdk/nashorn/internal/runtime/JSType.java	Tue Dec 03 14:13:15 2013 +0400
    23.3 @@ -88,6 +88,9 @@
    23.4      /** JavaScript compliant conversion function from Object to number */
    23.5      public static final Call TO_NUMBER = staticCall(myLookup, JSType.class, "toNumber", double.class, Object.class);
    23.6  
    23.7 +    /** JavaScript compliant conversion function from Object to String */
    23.8 +    public static final Call TO_STRING = staticCall(myLookup, JSType.class, "toString", String.class, Object.class);
    23.9 +
   23.10      /** JavaScript compliant conversion function from Object to int32 */
   23.11      public static final Call TO_INT32 = staticCall(myLookup, JSType.class, "toInt32", int.class, Object.class);
   23.12  
   23.13 @@ -883,7 +886,7 @@
   23.14       */
   23.15      public static Object toJavaArray(final Object obj, final Class<?> componentType) {
   23.16          if (obj instanceof ScriptObject) {
   23.17 -            return convertArray(((ScriptObject)obj).getArray().asObjectArray(), componentType);
   23.18 +            return ((ScriptObject)obj).getArray().asArrayOfType(componentType);
   23.19          } else if (obj instanceof JSObject) {
   23.20              final ArrayLikeIterator<?> itr = ArrayLikeIterator.arrayLikeIterator(obj);
   23.21              final int len = (int) itr.getLength();
   23.22 @@ -908,6 +911,15 @@
   23.23       * @return converted Java array
   23.24       */
   23.25      public static Object convertArray(final Object[] src, final Class<?> componentType) {
   23.26 +        if(componentType == Object.class) {
   23.27 +            for(int i = 0; i < src.length; ++i) {
   23.28 +                final Object e = src[i];
   23.29 +                if(e instanceof ConsString) {
   23.30 +                    src[i] = e.toString();
   23.31 +                }
   23.32 +            }
   23.33 +        }
   23.34 +
   23.35          final int l = src.length;
   23.36          final Object dst = Array.newInstance(componentType, l);
   23.37          final MethodHandle converter = Bootstrap.getLinkerServices().getTypeConverter(Object.class, componentType);
    24.1 --- a/src/jdk/nashorn/internal/runtime/Property.java	Sun Nov 03 07:33:34 2013 +0000
    24.2 +++ b/src/jdk/nashorn/internal/runtime/Property.java	Tue Dec 03 14:13:15 2013 +0400
    24.3 @@ -56,33 +56,36 @@
    24.4      public static final int WRITABLE_ENUMERABLE_CONFIGURABLE = 0b0000_0000_0000;
    24.5  
    24.6      /** ECMA 8.6.1 - Is this property not writable? */
    24.7 -    public static final int NOT_WRITABLE     = 0b0000_0000_0001;
    24.8 +    public static final int NOT_WRITABLE     = 1 << 0;
    24.9  
   24.10      /** ECMA 8.6.1 - Is this property not enumerable? */
   24.11 -    public static final int NOT_ENUMERABLE   = 0b0000_0000_0010;
   24.12 +    public static final int NOT_ENUMERABLE   = 1 << 1;
   24.13  
   24.14      /** ECMA 8.6.1 - Is this property not configurable? */
   24.15 -    public static final int NOT_CONFIGURABLE = 0b0000_0000_0100;
   24.16 +    public static final int NOT_CONFIGURABLE = 1 << 2;
   24.17  
   24.18 -    private static final int MODIFY_MASK     = 0b0000_0000_1111;
   24.19 +    private static final int MODIFY_MASK     = (NOT_WRITABLE | NOT_ENUMERABLE | NOT_CONFIGURABLE);
   24.20  
   24.21      /** Is this a spill property? See {@link AccessorProperty} */
   24.22 -    public static final int IS_SPILL         = 0b0000_0001_0000;
   24.23 +    public static final int IS_SPILL         = 1 << 3;
   24.24  
   24.25      /** Is this a function parameter? */
   24.26 -    public static final int IS_PARAMETER     = 0b0000_0010_0000;
   24.27 +    public static final int IS_PARAMETER     = 1 << 4;
   24.28  
   24.29      /** Is parameter accessed thru arguments? */
   24.30 -    public static final int HAS_ARGUMENTS    = 0b0000_0100_0000;
   24.31 +    public static final int HAS_ARGUMENTS    = 1 << 5;
   24.32  
   24.33      /** Is this property always represented as an Object? See {@link ObjectClassGenerator} and dual fields flag. */
   24.34 -    public static final int IS_ALWAYS_OBJECT = 0b0000_1000_0000;
   24.35 +    public static final int IS_ALWAYS_OBJECT = 1 << 6;
   24.36  
   24.37      /** Can this property be primitive? */
   24.38 -    public static final int CAN_BE_PRIMITIVE = 0b0001_0000_0000;
   24.39 +    public static final int CAN_BE_PRIMITIVE = 1 << 7;
   24.40  
   24.41      /** Can this property be undefined? */
   24.42 -    public static final int CAN_BE_UNDEFINED = 0b0010_0000_0000;
   24.43 +    public static final int CAN_BE_UNDEFINED = 1 << 8;
   24.44 +
   24.45 +    /* Is this a function declaration property ? */
   24.46 +    public static final int IS_FUNCTION_DECLARATION = 1 << 9;
   24.47  
   24.48      /** Property key. */
   24.49      private final String key;
   24.50 @@ -522,4 +525,12 @@
   24.51      public boolean canBeUndefined() {
   24.52          return (flags & CAN_BE_UNDEFINED) == CAN_BE_UNDEFINED;
   24.53      }
   24.54 +
   24.55 +    /**
   24.56 +     * Check whether this property represents a function declaration.
   24.57 +     * @return whether this property is a function declaration or not.
   24.58 +     */
   24.59 +    public boolean isFunctionDeclaration() {
   24.60 +        return (flags & IS_FUNCTION_DECLARATION) == IS_FUNCTION_DECLARATION;
   24.61 +    }
   24.62  }
    25.1 --- a/src/jdk/nashorn/internal/runtime/ScriptFunctionData.java	Sun Nov 03 07:33:34 2013 +0000
    25.2 +++ b/src/jdk/nashorn/internal/runtime/ScriptFunctionData.java	Tue Dec 03 14:13:15 2013 +0400
    25.3 @@ -213,13 +213,13 @@
    25.4       */
    25.5      public final MethodHandle getGenericInvoker() {
    25.6          ensureCodeGenerated();
    25.7 -        return composeGenericMethod(code.mostGeneric().getInvoker());
    25.8 +        return code.generic().getInvoker();
    25.9      }
   25.10  
   25.11      final MethodHandle getGenericConstructor() {
   25.12          ensureCodeGenerated();
   25.13 -        ensureConstructor(code.mostGeneric());
   25.14 -        return composeGenericMethod(code.mostGeneric().getConstructor());
   25.15 +        ensureConstructor(code.generic());
   25.16 +        return code.generic().getConstructor();
   25.17      }
   25.18  
   25.19      private CompiledFunction getBest(final MethodType callSiteType) {
   25.20 @@ -267,18 +267,17 @@
   25.21      }
   25.22  
   25.23      /**
   25.24 -     * Compose a constructor given a primordial constructor handle
   25.25 +     * Compose a constructor given a primordial constructor handle.
   25.26       *
   25.27 -     * @param ctor         primordial constructor handle
   25.28 -     * @param needsCallee  do we need to pass a callee
   25.29 -     *
   25.30 +     * @param ctor primordial constructor handle
   25.31       * @return the composed constructor
   25.32       */
   25.33 -    protected MethodHandle composeConstructor(final MethodHandle ctor, final boolean needsCallee) {
   25.34 +    protected MethodHandle composeConstructor(final MethodHandle ctor) {
   25.35          // If it was (callee, this, args...), permute it to (this, callee, args...). We're doing this because having
   25.36          // "this" in the first argument position is what allows the elegant folded composition of
   25.37          // (newFilter x constructor x allocator) further down below in the code. Also, ensure the composite constructor
   25.38          // always returns Object.
   25.39 +        final boolean needsCallee = needsCallee(ctor);
   25.40          MethodHandle composedCtor = needsCallee ? swapCalleeAndThis(ctor) : ctor;
   25.41  
   25.42          composedCtor = changeReturnTypeToObject(composedCtor);
   25.43 @@ -472,33 +471,6 @@
   25.44      }
   25.45  
   25.46      /**
   25.47 -     * Takes a method handle, and returns a potentially different method handle that can be used in
   25.48 -     * {@code ScriptFunction#invoke(Object, Object...)} or {code ScriptFunction#construct(Object, Object...)}.
   25.49 -     * The returned method handle will be sure to return {@code Object}, and will have all its parameters turned into
   25.50 -     * {@code Object} as well, except for the following ones:
   25.51 -     * <ul>
   25.52 -     *   <li>a last parameter of type {@code Object[]} which is used for vararg functions,</li>
   25.53 -     *   <li>the first argument, which is forced to be {@link ScriptFunction}, in case the function receives itself
   25.54 -     *   (callee) as an argument.</li>
   25.55 -     * </ul>
   25.56 -     *
   25.57 -     * @param mh the original method handle
   25.58 -     *
   25.59 -     * @return the new handle, conforming to the rules above.
   25.60 -     */
   25.61 -    protected MethodHandle composeGenericMethod(final MethodHandle mh) {
   25.62 -        final MethodType type = mh.type();
   25.63 -        MethodType newType = type.generic();
   25.64 -        if (isVarArg(mh)) {
   25.65 -            newType = newType.changeParameterType(type.parameterCount() - 1, Object[].class);
   25.66 -        }
   25.67 -        if (needsCallee(mh)) {
   25.68 -            newType = newType.changeParameterType(0, ScriptFunction.class);
   25.69 -        }
   25.70 -        return type.equals(newType) ? mh : mh.asType(newType);
   25.71 -    }
   25.72 -
   25.73 -    /**
   25.74       * Execute this script function.
   25.75       *
   25.76       * @param self  Target object.
   25.77 @@ -508,10 +480,9 @@
   25.78       * @throws Throwable if there is an exception/error with the invocation or thrown from it
   25.79       */
   25.80      Object invoke(final ScriptFunction fn, final Object self, final Object... arguments) throws Throwable {
   25.81 -        final MethodHandle mh = getGenericInvoker();
   25.82 -
   25.83 -        final Object       selfObj    = convertThisObject(self);
   25.84 -        final Object[]     args       = arguments == null ? ScriptRuntime.EMPTY_ARRAY : arguments;
   25.85 +        final MethodHandle mh  = getGenericInvoker();
   25.86 +        final Object   selfObj = convertThisObject(self);
   25.87 +        final Object[] args    = arguments == null ? ScriptRuntime.EMPTY_ARRAY : arguments;
   25.88  
   25.89          if (isVarArg(mh)) {
   25.90              if (needsCallee(mh)) {
   25.91 @@ -531,6 +502,12 @@
   25.92                  return mh.invokeExact(fn, selfObj, getArg(args, 0), getArg(args, 1));
   25.93              case 5:
   25.94                  return mh.invokeExact(fn, selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2));
   25.95 +            case 6:
   25.96 +                return mh.invokeExact(fn, selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3));
   25.97 +            case 7:
   25.98 +                return mh.invokeExact(fn, selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4));
   25.99 +            case 8:
  25.100 +                return mh.invokeExact(fn, selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4), getArg(args, 5));
  25.101              default:
  25.102                  return mh.invokeWithArguments(withArguments(fn, selfObj, paramCount, args));
  25.103              }
  25.104 @@ -545,15 +522,20 @@
  25.105              return mh.invokeExact(selfObj, getArg(args, 0), getArg(args, 1));
  25.106          case 4:
  25.107              return mh.invokeExact(selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2));
  25.108 +        case 5:
  25.109 +            return mh.invokeExact(selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3));
  25.110 +        case 6:
  25.111 +            return mh.invokeExact(selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4));
  25.112 +        case 7:
  25.113 +            return mh.invokeExact(selfObj, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4), getArg(args, 5));
  25.114          default:
  25.115              return mh.invokeWithArguments(withArguments(null, selfObj, paramCount, args));
  25.116          }
  25.117      }
  25.118  
  25.119      Object construct(final ScriptFunction fn, final Object... arguments) throws Throwable {
  25.120 -        final MethodHandle mh = getGenericConstructor();
  25.121 -
  25.122 -        final Object[]     args       = arguments == null ? ScriptRuntime.EMPTY_ARRAY : arguments;
  25.123 +        final MethodHandle mh   = getGenericConstructor();
  25.124 +        final Object[]     args = arguments == null ? ScriptRuntime.EMPTY_ARRAY : arguments;
  25.125  
  25.126          if (isVarArg(mh)) {
  25.127              if (needsCallee(mh)) {
  25.128 @@ -573,6 +555,12 @@
  25.129                  return mh.invokeExact(fn, getArg(args, 0), getArg(args, 1));
  25.130              case 4:
  25.131                  return mh.invokeExact(fn, getArg(args, 0), getArg(args, 1), getArg(args, 2));
  25.132 +            case 5:
  25.133 +                return mh.invokeExact(fn, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3));
  25.134 +            case 6:
  25.135 +                return mh.invokeExact(fn, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4));
  25.136 +            case 7:
  25.137 +                return mh.invokeExact(fn, getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4), getArg(args, 5));
  25.138              default:
  25.139                  return mh.invokeWithArguments(withArguments(fn, paramCount, args));
  25.140              }
  25.141 @@ -587,6 +575,12 @@
  25.142              return mh.invokeExact(getArg(args, 0), getArg(args, 1));
  25.143          case 3:
  25.144              return mh.invokeExact(getArg(args, 0), getArg(args, 1), getArg(args, 2));
  25.145 +        case 4:
  25.146 +            return mh.invokeExact(getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3));
  25.147 +        case 5:
  25.148 +            return mh.invokeExact(getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4));
  25.149 +        case 6:
  25.150 +            return mh.invokeExact(getArg(args, 0), getArg(args, 1), getArg(args, 2), getArg(args, 3), getArg(args, 4), getArg(args, 5));
  25.151          default:
  25.152              return mh.invokeWithArguments(withArguments(null, paramCount, args));
  25.153          }
  25.154 @@ -664,20 +658,21 @@
  25.155       * @return the adapted handle
  25.156       */
  25.157      private static MethodHandle changeReturnTypeToObject(final MethodHandle mh) {
  25.158 -        return MH.asType(mh, mh.type().changeReturnType(Object.class));
  25.159 +        final MethodType type = mh.type();
  25.160 +        return (type.returnType() == Object.class) ? mh : MH.asType(mh, type.changeReturnType(Object.class));
  25.161      }
  25.162  
  25.163      private void ensureConstructor(final CompiledFunction inv) {
  25.164          if (!inv.hasConstructor()) {
  25.165 -            inv.setConstructor(composeConstructor(inv.getInvoker(), needsCallee(inv.getInvoker())));
  25.166 +            inv.setConstructor(composeConstructor(inv.getInvoker()));
  25.167          }
  25.168      }
  25.169  
  25.170      /**
  25.171 -     * Heuristic to figure out if the method handle has a callee argument. If it's type is either
  25.172 -     * {@code (boolean, ScriptFunction, ...)} or {@code (ScriptFunction, ...)}, then we'll assume it has
  25.173 -     * a callee argument. We need this as the constructor above is not passed this information, and can't just blindly
  25.174 -     * assume it's false (notably, it's being invoked for creation of new scripts, and scripts have scopes, therefore
  25.175 +     * Heuristic to figure out if the method handle has a callee argument. If it's type is
  25.176 +     * {@code (ScriptFunction, ...)}, then we'll assume it has a callee argument. We need this as
  25.177 +     * the constructor above is not passed this information, and can't just blindly assume it's false
  25.178 +     * (notably, it's being invoked for creation of new scripts, and scripts have scopes, therefore
  25.179       * they also always receive a callee).
  25.180       *
  25.181       * @param mh the examined method handle
  25.182 @@ -685,18 +680,8 @@
  25.183       * @return true if the method handle expects a callee, false otherwise
  25.184       */
  25.185      protected static boolean needsCallee(final MethodHandle mh) {
  25.186 -        final MethodType type   = mh.type();
  25.187 -        final int        length = type.parameterCount();
  25.188 -
  25.189 -        if (length == 0) {
  25.190 -            return false;
  25.191 -        }
  25.192 -
  25.193 -        if (type.parameterType(0) == ScriptFunction.class) {
  25.194 -            return true;
  25.195 -        }
  25.196 -
  25.197 -        return length > 1 && type.parameterType(0) == boolean.class && type.parameterType(1) == ScriptFunction.class;
  25.198 +        final MethodType type = mh.type();
  25.199 +        return (type.parameterCount() > 0 && type.parameterType(0) == ScriptFunction.class);
  25.200      }
  25.201  
  25.202      /**
    26.1 --- a/src/jdk/nashorn/internal/runtime/ScriptObject.java	Sun Nov 03 07:33:34 2013 +0000
    26.2 +++ b/src/jdk/nashorn/internal/runtime/ScriptObject.java	Tue Dec 03 14:13:15 2013 +0400
    26.3 @@ -226,14 +226,23 @@
    26.4  
    26.5          for (final Property property : properties) {
    26.6              final String key = property.getKey();
    26.7 -
    26.8 -            if (newMap.findProperty(key) == null) {
    26.9 +            final Property oldProp = newMap.findProperty(key);
   26.10 +            if (oldProp == null) {
   26.11                  if (property instanceof UserAccessorProperty) {
   26.12                      final UserAccessorProperty prop = this.newUserAccessors(key, property.getFlags(), property.getGetterFunction(source), property.getSetterFunction(source));
   26.13                      newMap = newMap.addProperty(prop);
   26.14                  } else {
   26.15                      newMap = newMap.addPropertyBind((AccessorProperty)property, source);
   26.16                  }
   26.17 +            } else {
   26.18 +                // See ECMA section 10.5 Declaration Binding Instantiation
   26.19 +                // step 5 processing each function declaration.
   26.20 +                if (property.isFunctionDeclaration() && !oldProp.isConfigurable()) {
   26.21 +                     if (oldProp instanceof UserAccessorProperty ||
   26.22 +                         !(oldProp.isWritable() && oldProp.isEnumerable())) {
   26.23 +                         throw typeError("cant.redefine.property", key, ScriptRuntime.safeToString(this));
   26.24 +                     }
   26.25 +                }
   26.26              }
   26.27          }
   26.28  
    27.1 --- a/src/jdk/nashorn/internal/runtime/ScriptingFunctions.java	Sun Nov 03 07:33:34 2013 +0000
    27.2 +++ b/src/jdk/nashorn/internal/runtime/ScriptingFunctions.java	Tue Dec 03 14:13:15 2013 +0400
    27.3 @@ -190,7 +190,7 @@
    27.4                  char buffer[] = new char[1024];
    27.5                  try (final InputStreamReader inputStream = new InputStreamReader(process.getErrorStream())) {
    27.6                      for (int length; (length = inputStream.read(buffer, 0, buffer.length)) != -1; ) {
    27.7 -                        outBuffer.append(buffer, 0, length);
    27.8 +                        errBuffer.append(buffer, 0, length);
    27.9                      }
   27.10                  } catch (IOException ex) {
   27.11                      exception[1] = ex;
    28.1 --- a/src/jdk/nashorn/internal/runtime/linker/Bootstrap.java	Sun Nov 03 07:33:34 2013 +0000
    28.2 +++ b/src/jdk/nashorn/internal/runtime/linker/Bootstrap.java	Tue Dec 03 14:13:15 2013 +0400
    28.3 @@ -63,7 +63,7 @@
    28.4          final DynamicLinkerFactory factory = new DynamicLinkerFactory();
    28.5          factory.setPrioritizedLinkers(new NashornLinker(), new NashornPrimitiveLinker(), new NashornStaticClassLinker(),
    28.6                  new BoundDynamicMethodLinker(), new JavaSuperAdapterLinker(), new JSObjectLinker(), new ReflectionCheckLinker());
    28.7 -        factory.setFallbackLinkers(new BeansLinker(), new NashornBottomLinker());
    28.8 +        factory.setFallbackLinkers(new NashornBeansLinker(), new NashornBottomLinker());
    28.9          factory.setSyncOnRelink(true);
   28.10          final int relinkThreshold = Options.getIntProperty("nashorn.unstable.relink.threshold", -1);
   28.11          if (relinkThreshold > -1) {
    29.1 --- a/src/jdk/nashorn/internal/runtime/linker/BoundDynamicMethodLinker.java	Sun Nov 03 07:33:34 2013 +0000
    29.2 +++ b/src/jdk/nashorn/internal/runtime/linker/BoundDynamicMethodLinker.java	Tue Dec 03 14:13:15 2013 +0400
    29.3 @@ -72,7 +72,7 @@
    29.4                  type.changeParameterType(0, dynamicMethodClass).changeParameterType(1, boundThis.getClass()));
    29.5  
    29.6          // Delegate to BeansLinker
    29.7 -        final GuardedInvocation inv = BeansLinker.getLinkerForClass(dynamicMethodClass).getGuardedInvocation(
    29.8 +        final GuardedInvocation inv = NashornBeansLinker.getGuardedInvocation(BeansLinker.getLinkerForClass(dynamicMethodClass),
    29.9                  linkRequest.replaceArguments(newDescriptor, args), linkerServices);
   29.10          if(inv == null) {
   29.11              return null;
    30.1 --- a/src/jdk/nashorn/internal/runtime/linker/JavaSuperAdapterLinker.java	Sun Nov 03 07:33:34 2013 +0000
    30.2 +++ b/src/jdk/nashorn/internal/runtime/linker/JavaSuperAdapterLinker.java	Tue Dec 03 14:13:15 2013 +0400
    30.3 @@ -100,8 +100,9 @@
    30.4                  type.changeParameterType(0, adapterClass), 0);
    30.5  
    30.6          // Delegate to BeansLinker
    30.7 -        final GuardedInvocation guardedInv = BeansLinker.getLinkerForClass(adapterClass).getGuardedInvocation(
    30.8 -                linkRequest.replaceArguments(newDescriptor, args), linkerServices);
    30.9 +        final GuardedInvocation guardedInv = NashornBeansLinker.getGuardedInvocation(
   30.10 +                BeansLinker.getLinkerForClass(adapterClass), linkRequest.replaceArguments(newDescriptor, args),
   30.11 +                linkerServices);
   30.12  
   30.13          final MethodHandle guard = IS_ADAPTER_OF_CLASS.bindTo(adapterClass);
   30.14          if(guardedInv == null) {
    31.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    31.2 +++ b/src/jdk/nashorn/internal/runtime/linker/NashornBeansLinker.java	Tue Dec 03 14:13:15 2013 +0400
    31.3 @@ -0,0 +1,127 @@
    31.4 +/*
    31.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    31.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    31.7 + *
    31.8 + * This code is free software; you can redistribute it and/or modify it
    31.9 + * under the terms of the GNU General Public License version 2 only, as
   31.10 + * published by the Free Software Foundation.  Oracle designates this
   31.11 + * particular file as subject to the "Classpath" exception as provided
   31.12 + * by Oracle in the LICENSE file that accompanied this code.
   31.13 + *
   31.14 + * This code is distributed in the hope that it will be useful, but WITHOUT
   31.15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   31.16 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   31.17 + * version 2 for more details (a copy is included in the LICENSE file that
   31.18 + * accompanied this code).
   31.19 + *
   31.20 + * You should have received a copy of the GNU General Public License version
   31.21 + * 2 along with this work; if not, write to the Free Software Foundation,
   31.22 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   31.23 + *
   31.24 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   31.25 + * or visit www.oracle.com if you need additional information or have any
   31.26 + * questions.
   31.27 + */
   31.28 +
   31.29 +package jdk.nashorn.internal.runtime.linker;
   31.30 +
   31.31 +import java.lang.invoke.MethodHandle;
   31.32 +import java.lang.invoke.MethodHandles;
   31.33 +import java.lang.invoke.MethodType;
   31.34 +import jdk.internal.dynalink.beans.BeansLinker;
   31.35 +import jdk.internal.dynalink.linker.ConversionComparator.Comparison;
   31.36 +import jdk.internal.dynalink.linker.GuardedInvocation;
   31.37 +import jdk.internal.dynalink.linker.GuardingDynamicLinker;
   31.38 +import jdk.internal.dynalink.linker.LinkRequest;
   31.39 +import jdk.internal.dynalink.linker.LinkerServices;
   31.40 +import jdk.internal.dynalink.support.Lookup;
   31.41 +import jdk.nashorn.internal.runtime.ConsString;
   31.42 +
   31.43 +/**
   31.44 + * This linker delegates to a {@code BeansLinker} but passes it a special linker services object that has a modified
   31.45 + * {@code asType} method that will ensure that we never pass internal engine objects that should not be externally
   31.46 + * observable (currently only ConsString) to Java APIs, but rather that we flatten it into a String. We can't just add
   31.47 + * this functionality as custom converters via {@code GuaardingTypeConverterFactory}, since they are not consulted when
   31.48 + * the target method handle parameter signature is {@code Object}.
   31.49 + */
   31.50 +public class NashornBeansLinker implements GuardingDynamicLinker {
   31.51 +    private static final MethodHandle EXPORT_ARGUMENT = new Lookup(MethodHandles.lookup()).findOwnStatic("exportArgument", Object.class, Object.class);
   31.52 +
   31.53 +    private final BeansLinker beansLinker = new BeansLinker();
   31.54 +
   31.55 +    @Override
   31.56 +    public GuardedInvocation getGuardedInvocation(final LinkRequest linkRequest, final LinkerServices linkerServices) throws Exception {
   31.57 +        return getGuardedInvocation(beansLinker, linkRequest, linkerServices);
   31.58 +    }
   31.59 +
   31.60 +    /**
   31.61 +     * Delegates to the specified linker but injects its linker services wrapper so that it will apply all special
   31.62 +     * conversions that this class does.
   31.63 +     * @param delegateLinker the linker to which the actual work is delegated to.
   31.64 +     * @param linkRequest the delegated link request
   31.65 +     * @param linkerServices the original link services that will be augmented with special conversions
   31.66 +     * @return the guarded invocation from the delegate, possibly augmented with special conversions
   31.67 +     * @throws Exception if the delegate throws an exception
   31.68 +     */
   31.69 +    public static GuardedInvocation getGuardedInvocation(final GuardingDynamicLinker delegateLinker, final LinkRequest linkRequest, final LinkerServices linkerServices) throws Exception {
   31.70 +        return delegateLinker.getGuardedInvocation(linkRequest, new NashornBeansLinkerServices(linkerServices));
   31.71 +    }
   31.72 +
   31.73 +    @SuppressWarnings("unused")
   31.74 +    private static Object exportArgument(final Object arg) {
   31.75 +        return arg instanceof ConsString ? arg.toString() : arg;
   31.76 +    }
   31.77 +
   31.78 +    private static class NashornBeansLinkerServices implements LinkerServices {
   31.79 +        private final LinkerServices linkerServices;
   31.80 +
   31.81 +        NashornBeansLinkerServices(final LinkerServices linkerServices) {
   31.82 +            this.linkerServices = linkerServices;
   31.83 +        }
   31.84 +
   31.85 +        @Override
   31.86 +        public MethodHandle asType(final MethodHandle handle, final MethodType fromType) {
   31.87 +            final MethodHandle typed = linkerServices.asType(handle, fromType);
   31.88 +
   31.89 +            final MethodType handleType = handle.type();
   31.90 +            final int paramCount = handleType.parameterCount();
   31.91 +            assert fromType.parameterCount() == handleType.parameterCount();
   31.92 +
   31.93 +            MethodHandle[] filters = null;
   31.94 +            for(int i = 0; i < paramCount; ++i) {
   31.95 +                if(shouldConvert(handleType.parameterType(i), fromType.parameterType(i))) {
   31.96 +                    if(filters == null) {
   31.97 +                        filters = new MethodHandle[paramCount];
   31.98 +                    }
   31.99 +                    filters[i] = EXPORT_ARGUMENT;
  31.100 +                }
  31.101 +            }
  31.102 +
  31.103 +            return filters != null ? MethodHandles.filterArguments(typed, 0, filters) : typed;
  31.104 +        }
  31.105 +
  31.106 +        private static boolean shouldConvert(final Class<?> handleType, final Class<?> fromType) {
  31.107 +            return handleType == Object.class && fromType == Object.class;
  31.108 +        }
  31.109 +
  31.110 +        @Override
  31.111 +        public MethodHandle getTypeConverter(final Class<?> sourceType, final Class<?> targetType) {
  31.112 +            return linkerServices.getTypeConverter(sourceType, targetType);
  31.113 +        }
  31.114 +
  31.115 +        @Override
  31.116 +        public boolean canConvert(final Class<?> from, final Class<?> to) {
  31.117 +            return linkerServices.canConvert(from, to);
  31.118 +        }
  31.119 +
  31.120 +        @Override
  31.121 +        public GuardedInvocation getGuardedInvocation(final LinkRequest linkRequest) throws Exception {
  31.122 +            return linkerServices.getGuardedInvocation(linkRequest);
  31.123 +        }
  31.124 +
  31.125 +        @Override
  31.126 +        public Comparison compareConversion(final Class<?> sourceType, final Class<?> targetType1, final Class<?> targetType2) {
  31.127 +            return linkerServices.compareConversion(sourceType, targetType1, targetType2);
  31.128 +        }
  31.129 +    }
  31.130 +}
    32.1 --- a/src/jdk/nashorn/internal/runtime/linker/NashornBottomLinker.java	Sun Nov 03 07:33:34 2013 +0000
    32.2 +++ b/src/jdk/nashorn/internal/runtime/linker/NashornBottomLinker.java	Tue Dec 03 14:13:15 2013 +0400
    32.3 @@ -33,14 +33,18 @@
    32.4  import java.lang.invoke.MethodType;
    32.5  import java.lang.reflect.Method;
    32.6  import java.lang.reflect.Modifier;
    32.7 +import java.util.Map;
    32.8 +import java.util.HashMap;
    32.9  import jdk.internal.dynalink.CallSiteDescriptor;
   32.10  import jdk.internal.dynalink.beans.BeansLinker;
   32.11  import jdk.internal.dynalink.linker.GuardedInvocation;
   32.12  import jdk.internal.dynalink.linker.GuardingDynamicLinker;
   32.13 +import jdk.internal.dynalink.linker.GuardingTypeConverterFactory;
   32.14  import jdk.internal.dynalink.linker.LinkRequest;
   32.15  import jdk.internal.dynalink.linker.LinkerServices;
   32.16  import jdk.internal.dynalink.support.Guards;
   32.17  import jdk.nashorn.internal.runtime.Context;
   32.18 +import jdk.nashorn.internal.runtime.JSType;
   32.19  import jdk.nashorn.internal.runtime.ScriptRuntime;
   32.20  
   32.21  /**
   32.22 @@ -50,7 +54,7 @@
   32.23   * setters for Java objects that couldn't be linked by any other linker, and throw appropriate ECMAScript errors for
   32.24   * attempts to invoke arbitrary Java objects as functions or constructors.
   32.25   */
   32.26 -final class NashornBottomLinker implements GuardingDynamicLinker {
   32.27 +final class NashornBottomLinker implements GuardingDynamicLinker, GuardingTypeConverterFactory {
   32.28  
   32.29      @Override
   32.30      public GuardedInvocation getGuardedInvocation(final LinkRequest linkRequest, final LinkerServices linkerServices)
   32.31 @@ -129,6 +133,29 @@
   32.32          throw new AssertionError("unknown call type " + desc);
   32.33      }
   32.34  
   32.35 +    @Override
   32.36 +    public GuardedInvocation convertToType(final Class<?> sourceType, final Class<?> targetType) throws Exception {
   32.37 +        final GuardedInvocation gi = convertToTypeNoCast(sourceType, targetType);
   32.38 +        return gi == null ? null : gi.asType(MH.type(targetType, sourceType));
   32.39 +    }
   32.40 +
   32.41 +    /**
   32.42 +     * Main part of the implementation of {@link GuardingTypeConverterFactory#convertToType(Class, Class)} that doesn't
   32.43 +     * care about adapting the method signature; that's done by the invoking method. Returns conversion from Object to String/number/boolean (JS primitive types).
   32.44 +     * @param sourceType the source type
   32.45 +     * @param targetType the target type
   32.46 +     * @return a guarded invocation that converts from the source type to the target type.
   32.47 +     * @throws Exception if something goes wrong
   32.48 +     */
   32.49 +    private static GuardedInvocation convertToTypeNoCast(final Class<?> sourceType, final Class<?> targetType) throws Exception {
   32.50 +        final MethodHandle mh = CONVERTERS.get(targetType);
   32.51 +        if (mh != null) {
   32.52 +            return new GuardedInvocation(mh, null);
   32.53 +        }
   32.54 +
   32.55 +        return null;
   32.56 +    }
   32.57 +
   32.58      private static GuardedInvocation getInvocation(final MethodHandle handle, final Object self, final LinkerServices linkerServices, final CallSiteDescriptor desc) {
   32.59          return Bootstrap.asType(new GuardedInvocation(handle, Guards.getClassGuard(self.getClass())), linkerServices, desc);
   32.60      }
   32.61 @@ -161,6 +188,15 @@
   32.62          throw new AssertionError("unknown call type " + desc);
   32.63      }
   32.64  
   32.65 +    private static final Map<Class<?>, MethodHandle> CONVERTERS = new HashMap<>();
   32.66 +    static {
   32.67 +        CONVERTERS.put(boolean.class, JSType.TO_BOOLEAN.methodHandle());
   32.68 +        CONVERTERS.put(double.class, JSType.TO_NUMBER.methodHandle());
   32.69 +        CONVERTERS.put(int.class, JSType.TO_INTEGER.methodHandle());
   32.70 +        CONVERTERS.put(long.class, JSType.TO_LONG.methodHandle());
   32.71 +        CONVERTERS.put(String.class, JSType.TO_STRING.methodHandle());
   32.72 +    }
   32.73 +
   32.74      private static String getArgument(final LinkRequest linkRequest) {
   32.75          final CallSiteDescriptor desc = linkRequest.getCallSiteDescriptor();
   32.76          if (desc.getNameTokenCount() > 2) {
    33.1 --- a/src/jdk/nashorn/internal/runtime/linker/NashornLinker.java	Sun Nov 03 07:33:34 2013 +0000
    33.2 +++ b/src/jdk/nashorn/internal/runtime/linker/NashornLinker.java	Tue Dec 03 14:13:15 2013 +0400
    33.3 @@ -32,6 +32,8 @@
    33.4  import java.lang.reflect.Modifier;
    33.5  import java.util.Deque;
    33.6  import java.util.List;
    33.7 +import java.util.Map;
    33.8 +import javax.script.Bindings;
    33.9  import jdk.internal.dynalink.CallSiteDescriptor;
   33.10  import jdk.internal.dynalink.linker.ConversionComparator;
   33.11  import jdk.internal.dynalink.linker.GuardedInvocation;
   33.12 @@ -40,7 +42,11 @@
   33.13  import jdk.internal.dynalink.linker.LinkerServices;
   33.14  import jdk.internal.dynalink.linker.TypeBasedGuardingDynamicLinker;
   33.15  import jdk.internal.dynalink.support.Guards;
   33.16 +import jdk.nashorn.api.scripting.JSObject;
   33.17 +import jdk.nashorn.api.scripting.ScriptObjectMirror;
   33.18 +import jdk.nashorn.api.scripting.ScriptUtils;
   33.19  import jdk.nashorn.internal.objects.NativeArray;
   33.20 +import jdk.nashorn.internal.runtime.Context;
   33.21  import jdk.nashorn.internal.runtime.JSType;
   33.22  import jdk.nashorn.internal.runtime.ScriptFunction;
   33.23  import jdk.nashorn.internal.runtime.ScriptObject;
   33.24 @@ -115,9 +121,14 @@
   33.25              return new GuardedInvocation(mh, canLinkTypeStatic(sourceType) ? null : IS_NASHORN_OR_UNDEFINED_TYPE);
   33.26          }
   33.27  
   33.28 -        GuardedInvocation inv = getArrayConverter(sourceType, targetType);
   33.29 -        if(inv != null) {
   33.30 -            return inv;
   33.31 +        final GuardedInvocation arrayConverter = getArrayConverter(sourceType, targetType);
   33.32 +        if(arrayConverter != null) {
   33.33 +            return arrayConverter;
   33.34 +        }
   33.35 +
   33.36 +        final GuardedInvocation mirrorConverter = getMirrorConverter(sourceType, targetType);
   33.37 +        if(mirrorConverter != null) {
   33.38 +            return mirrorConverter;
   33.39          }
   33.40  
   33.41          return getSamTypeConverter(sourceType, targetType);
   33.42 @@ -181,6 +192,18 @@
   33.43          return MH.asType(converter, converter.type().changeReturnType(type));
   33.44      }
   33.45  
   33.46 +    private static GuardedInvocation getMirrorConverter(Class<?> sourceType, Class<?> targetType) {
   33.47 +        // Could've also used (targetType.isAssignableFrom(ScriptObjectMirror.class) && targetType != Object.class) but
   33.48 +        // it's probably better to explicitly spell out the supported target types
   33.49 +        if (targetType == Map.class || targetType == Bindings.class || targetType == JSObject.class || targetType == ScriptObjectMirror.class) {
   33.50 +            if(ScriptObject.class.isAssignableFrom(sourceType)) {
   33.51 +                return new GuardedInvocation(CREATE_MIRROR, null);
   33.52 +            }
   33.53 +            return new GuardedInvocation(CREATE_MIRROR, IS_SCRIPT_OBJECT);
   33.54 +        }
   33.55 +        return null;
   33.56 +    }
   33.57 +
   33.58      private static boolean isAutoConvertibleFromFunction(final Class<?> clazz) {
   33.59          return isAbstractClass(clazz) && !ScriptObject.class.isAssignableFrom(clazz) &&
   33.60                  JavaAdapterFactory.isAutoConvertibleFromFunction(clazz);
   33.61 @@ -235,17 +258,23 @@
   33.62          return clazz == List.class || clazz == Deque.class;
   33.63      }
   33.64  
   33.65 +    private static final MethodHandle IS_SCRIPT_OBJECT = Guards.isInstance(ScriptObject.class, MH.type(Boolean.TYPE, Object.class));
   33.66      private static final MethodHandle IS_SCRIPT_FUNCTION = Guards.isInstance(ScriptFunction.class, MH.type(Boolean.TYPE, Object.class));
   33.67      private static final MethodHandle IS_NATIVE_ARRAY = Guards.isOfClass(NativeArray.class, MH.type(Boolean.TYPE, Object.class));
   33.68  
   33.69 -    private static final MethodHandle IS_NASHORN_OR_UNDEFINED_TYPE = findOwnMH("isNashornTypeOrUndefined",
   33.70 -            Boolean.TYPE, Object.class);
   33.71 +    private static final MethodHandle IS_NASHORN_OR_UNDEFINED_TYPE = findOwnMH("isNashornTypeOrUndefined", Boolean.TYPE, Object.class);
   33.72 +    private static final MethodHandle CREATE_MIRROR = findOwnMH("createMirror", Object.class, Object.class);
   33.73  
   33.74      @SuppressWarnings("unused")
   33.75      private static boolean isNashornTypeOrUndefined(final Object obj) {
   33.76          return obj instanceof ScriptObject || obj instanceof Undefined;
   33.77      }
   33.78  
   33.79 +    @SuppressWarnings("unused")
   33.80 +    private static Object createMirror(final Object obj) {
   33.81 +        return ScriptUtils.wrap(obj);
   33.82 +    }
   33.83 +
   33.84      private static MethodHandle findOwnMH(final String name, final Class<?> rtype, final Class<?>... types) {
   33.85          return MH.findStatic(MethodHandles.lookup(), NashornLinker.class, name, MH.type(rtype, types));
   33.86      }
    34.1 --- a/src/jdk/nashorn/internal/runtime/linker/NashornStaticClassLinker.java	Sun Nov 03 07:33:34 2013 +0000
    34.2 +++ b/src/jdk/nashorn/internal/runtime/linker/NashornStaticClassLinker.java	Tue Dec 03 14:13:15 2013 +0400
    34.3 @@ -93,7 +93,7 @@
    34.4      }
    34.5  
    34.6      private static GuardedInvocation delegate(LinkerServices linkerServices, final LinkRequest request) throws Exception {
    34.7 -        return staticClassLinker.getGuardedInvocation(request, linkerServices);
    34.8 +        return NashornBeansLinker.getGuardedInvocation(staticClassLinker, request, linkerServices);
    34.9      }
   34.10  
   34.11      private static GuardedInvocation checkNullConstructor(final GuardedInvocation ctorInvocation, final Class<?> receiverClass) {
    35.1 --- a/test/script/basic/JDK-8015355.js	Sun Nov 03 07:33:34 2013 +0000
    35.2 +++ b/test/script/basic/JDK-8015355.js	Tue Dec 03 14:13:15 2013 +0400
    35.3 @@ -28,10 +28,6 @@
    35.4   * @run
    35.5   */
    35.6  
    35.7 -function fail(msg) {
    35.8 -    print(msg);
    35.9 -}
   35.10 -
   35.11  function check(callback) {
   35.12      try {
   35.13          callback();
    36.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    36.2 +++ b/test/script/basic/JDK-8027042.js	Tue Dec 03 14:13:15 2013 +0400
    36.3 @@ -0,0 +1,58 @@
    36.4 +/*
    36.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    36.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    36.7 + * 
    36.8 + * This code is free software; you can redistribute it and/or modify it
    36.9 + * under the terms of the GNU General Public License version 2 only, as
   36.10 + * published by the Free Software Foundation.
   36.11 + * 
   36.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   36.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   36.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   36.15 + * version 2 for more details (a copy is included in the LICENSE file that
   36.16 + * accompanied this code).
   36.17 + * 
   36.18 + * You should have received a copy of the GNU General Public License version
   36.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   36.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   36.21 + * 
   36.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   36.23 + * or visit www.oracle.com if you need additional information or have any
   36.24 + * questions.
   36.25 + */
   36.26 +
   36.27 +/**
   36.28 + * JDK-8027042: Evaluation order for binary operators can be improved
   36.29 + *
   36.30 + * @test
   36.31 + * @run
   36.32 + */
   36.33 +
   36.34 +// var with getter side effect
   36.35 +Object.defineProperty(this, "a", { get: function() {print("get a"); return 1; }});
   36.36 +
   36.37 +// var with both getter and conversion side effect
   36.38 +Object.defineProperty(this, "b", { get: function() {print("get b"); return {valueOf: function() { print("conv b"); return 10; }}; }});
   36.39 +
   36.40 +(function() {
   36.41 +    // var with toPrimitive conversion side effect
   36.42 +    var c = {valueOf: function() { print("conv c"); return 100; }};
   36.43 +
   36.44 +    print(b + (c + a));
   36.45 +    print(b + (c + b));
   36.46 +    print(b + (a + b));
   36.47 +    print(b + (b + c));
   36.48 +    print(b + (b + c));
   36.49 +    print(b + (c + (a - b)));
   36.50 +    print(b + (c + (c - b)));
   36.51 +    print(b + (c + (b - c)));
   36.52 +    print(b + (b + (a ? 2 : 3)));
   36.53 +    print(b + (b + (b ? 2 : 3)));
   36.54 +    print(b + (b + (c ? 2 : 3)));
   36.55 +    print(b + ((-c) + (-a)));
   36.56 +    print(b + ((-c) + (-b)));
   36.57 +    print(b + ((-c) + (-c)));
   36.58 +    try { print(b + new a); } catch (e) {}
   36.59 +    try { print(b + new b); } catch (e) {}
   36.60 +    try { print(b + new c); } catch (e) {}
   36.61 +})();
    37.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    37.2 +++ b/test/script/basic/JDK-8027042.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    37.3 @@ -0,0 +1,88 @@
    37.4 +get b
    37.5 +get a
    37.6 +conv c
    37.7 +conv b
    37.8 +111
    37.9 +get b
   37.10 +get b
   37.11 +conv c
   37.12 +conv b
   37.13 +conv b
   37.14 +120
   37.15 +get b
   37.16 +get a
   37.17 +get b
   37.18 +conv b
   37.19 +conv b
   37.20 +21
   37.21 +get b
   37.22 +get b
   37.23 +conv b
   37.24 +conv c
   37.25 +conv b
   37.26 +120
   37.27 +get b
   37.28 +get b
   37.29 +conv b
   37.30 +conv c
   37.31 +conv b
   37.32 +120
   37.33 +get b
   37.34 +get a
   37.35 +get b
   37.36 +conv b
   37.37 +conv c
   37.38 +conv b
   37.39 +101
   37.40 +get b
   37.41 +get b
   37.42 +conv c
   37.43 +conv b
   37.44 +conv c
   37.45 +conv b
   37.46 +200
   37.47 +get b
   37.48 +get b
   37.49 +conv b
   37.50 +conv c
   37.51 +conv c
   37.52 +conv b
   37.53 +20
   37.54 +get b
   37.55 +get b
   37.56 +get a
   37.57 +conv b
   37.58 +conv b
   37.59 +22
   37.60 +get b
   37.61 +get b
   37.62 +get b
   37.63 +conv b
   37.64 +conv b
   37.65 +22
   37.66 +get b
   37.67 +get b
   37.68 +conv b
   37.69 +conv b
   37.70 +22
   37.71 +get b
   37.72 +conv c
   37.73 +get a
   37.74 +conv b
   37.75 +-91
   37.76 +get b
   37.77 +conv c
   37.78 +get b
   37.79 +conv b
   37.80 +conv b
   37.81 +-100
   37.82 +get b
   37.83 +conv c
   37.84 +conv c
   37.85 +conv b
   37.86 +-190
   37.87 +get b
   37.88 +get a
   37.89 +get b
   37.90 +get b
   37.91 +get b
    38.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    38.2 +++ b/test/script/basic/JDK-8027236.js	Tue Dec 03 14:13:15 2013 +0400
    38.3 @@ -0,0 +1,37 @@
    38.4 +/*
    38.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    38.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    38.7 + * 
    38.8 + * This code is free software; you can redistribute it and/or modify it
    38.9 + * under the terms of the GNU General Public License version 2 only, as
   38.10 + * published by the Free Software Foundation.
   38.11 + * 
   38.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   38.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   38.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   38.15 + * version 2 for more details (a copy is included in the LICENSE file that
   38.16 + * accompanied this code).
   38.17 + * 
   38.18 + * You should have received a copy of the GNU General Public License version
   38.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   38.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   38.21 + * 
   38.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   38.23 + * or visit www.oracle.com if you need additional information or have any
   38.24 + * questions.
   38.25 + */
   38.26 +
   38.27 +/**
   38.28 + * JDK-8027236: Ensure ScriptObject and ConsString aren't visible to Java
   38.29 + *
   38.30 + * @test
   38.31 + * @run
   38.32 + */
   38.33 +
   38.34 +// Check that ConsString is flattened
   38.35 +var m = new java.util.HashMap()
   38.36 +var x = "f"
   38.37 +x += "oo"
   38.38 +m.put(x, "bar")
   38.39 +print(m.get("foo"))
   38.40 +// Note: many more tests are run by the JavaExportImportTest TestNG class.
    39.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    39.2 +++ b/test/script/basic/JDK-8027236.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    39.3 @@ -0,0 +1,1 @@
    39.4 +bar
    40.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    40.2 +++ b/test/script/basic/JDK-8027562.js	Tue Dec 03 14:13:15 2013 +0400
    40.3 @@ -0,0 +1,39 @@
    40.4 +/*
    40.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    40.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    40.7 + * 
    40.8 + * This code is free software; you can redistribute it and/or modify it
    40.9 + * under the terms of the GNU General Public License version 2 only, as
   40.10 + * published by the Free Software Foundation.
   40.11 + * 
   40.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   40.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   40.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   40.15 + * version 2 for more details (a copy is included in the LICENSE file that
   40.16 + * accompanied this code).
   40.17 + * 
   40.18 + * You should have received a copy of the GNU General Public License version
   40.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   40.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   40.21 + * 
   40.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   40.23 + * or visit www.oracle.com if you need additional information or have any
   40.24 + * questions.
   40.25 + */
   40.26 +
   40.27 +/**
   40.28 + * JDK-8027562: eval should load second and subsequent arguments for side effect
   40.29 + *
   40.30 + * @test
   40.31 + * @run
   40.32 + */
   40.33 +
   40.34 +try {
   40.35 +    eval("", x);
   40.36 +    fail("should have thrown ReferenceError for 'x'");
   40.37 +} catch (e) {
   40.38 +    if (! (e instanceof ReferenceError)) {
   40.39 +        fail("Expected ReferenceError, got " + e);
   40.40 +    }
   40.41 +    print(e);
   40.42 +}
    41.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    41.2 +++ b/test/script/basic/JDK-8027562.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    41.3 @@ -0,0 +1,1 @@
    41.4 +ReferenceError: "x" is not defined
    42.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    42.2 +++ b/test/script/basic/JDK-8027700.js	Tue Dec 03 14:13:15 2013 +0400
    42.3 @@ -0,0 +1,54 @@
    42.4 +/*
    42.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    42.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    42.7 + * 
    42.8 + * This code is free software; you can redistribute it and/or modify it
    42.9 + * under the terms of the GNU General Public License version 2 only, as
   42.10 + * published by the Free Software Foundation.
   42.11 + * 
   42.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   42.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   42.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   42.15 + * version 2 for more details (a copy is included in the LICENSE file that
   42.16 + * accompanied this code).
   42.17 + * 
   42.18 + * You should have received a copy of the GNU General Public License version
   42.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   42.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   42.21 + * 
   42.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   42.23 + * or visit www.oracle.com if you need additional information or have any
   42.24 + * questions.
   42.25 + */
   42.26 +
   42.27 +/**
   42.28 + * JDK-8027700: function redeclaration checks missing for declaration binding instantiation
   42.29 + *
   42.30 + * @test
   42.31 + * @run
   42.32 + */
   42.33 +
   42.34 +Object.defineProperty(this,"x", {
   42.35 +        value:0,
   42.36 +        writable:true,
   42.37 +        enumerable:false
   42.38 +})
   42.39 +
   42.40 +try {
   42.41 +    eval("function x() {}");
   42.42 +    fail("should have thrown TypeError");
   42.43 +} catch (e) {
   42.44 +    if (! (e instanceof TypeError)) {
   42.45 +        fail("TypeError expected but got " + e);
   42.46 +    }
   42.47 +}
   42.48 +
   42.49 +Object.defineProperty(this, "foo", { value:0 }) 
   42.50 +try {
   42.51 +    eval("function foo() {}");
   42.52 +    fail("should have thrown TypeError");
   42.53 +} catch (e) {
   42.54 +    if (! (e instanceof TypeError)) {
   42.55 +        fail("TypeError expected but got " + e);
   42.56 +    }
   42.57 +}
    43.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    43.2 +++ b/test/script/basic/JDK-8027753.js	Tue Dec 03 14:13:15 2013 +0400
    43.3 @@ -0,0 +1,50 @@
    43.4 +/*
    43.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    43.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    43.7 + * 
    43.8 + * This code is free software; you can redistribute it and/or modify it
    43.9 + * under the terms of the GNU General Public License version 2 only, as
   43.10 + * published by the Free Software Foundation.
   43.11 + * 
   43.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   43.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   43.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   43.15 + * version 2 for more details (a copy is included in the LICENSE file that
   43.16 + * accompanied this code).
   43.17 + * 
   43.18 + * You should have received a copy of the GNU General Public License version
   43.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   43.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   43.21 + * 
   43.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   43.23 + * or visit www.oracle.com if you need additional information or have any
   43.24 + * questions.
   43.25 + */
   43.26 +
   43.27 +/**
   43.28 + * JDK-8027753: Support ScriptObject to JSObject, ScriptObjectMirror, Map, Bindings auto-conversion as well as explicit wrap, unwrap
   43.29 + *
   43.30 + * @test
   43.31 + * @run
   43.32 + */
   43.33 +
   43.34 +var ScriptUtils = Java.type("jdk.nashorn.api.scripting.ScriptUtils");
   43.35 +var ScriptObjectMirror = Java.type("jdk.nashorn.api.scripting.ScriptObjectMirror");
   43.36 +
   43.37 +var obj = { foo: 34, bar: 'hello' };
   43.38 +
   43.39 +var wrapped = ScriptUtils.wrap(obj);
   43.40 +if (! (wrapped instanceof ScriptObjectMirror)) {
   43.41 +    fail("ScriptUtils.wrap does not return a ScriptObjectMirror");
   43.42 +}
   43.43 +
   43.44 +print("wrapped.foo = " + wrapped.foo);
   43.45 +print("wrapped.bar = " + wrapped.bar);
   43.46 +
   43.47 +var unwrapped = ScriptUtils.unwrap(wrapped);
   43.48 +if (! (unwrapped instanceof Object)) {
   43.49 +    fail("ScriptUtils.unwrap does not return a ScriptObject");
   43.50 +}
   43.51 +
   43.52 +// same object unwrapped?
   43.53 +print(unwrapped === obj);
    44.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    44.2 +++ b/test/script/basic/JDK-8027753.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    44.3 @@ -0,0 +1,3 @@
    44.4 +wrapped.foo = 34
    44.5 +wrapped.bar = hello
    44.6 +true
    45.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    45.2 +++ b/test/script/basic/JDK-8027828.js	Tue Dec 03 14:13:15 2013 +0400
    45.3 @@ -0,0 +1,35 @@
    45.4 +/*
    45.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    45.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    45.7 + * 
    45.8 + * This code is free software; you can redistribute it and/or modify it
    45.9 + * under the terms of the GNU General Public License version 2 only, as
   45.10 + * published by the Free Software Foundation.
   45.11 + * 
   45.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   45.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   45.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   45.15 + * version 2 for more details (a copy is included in the LICENSE file that
   45.16 + * accompanied this code).
   45.17 + * 
   45.18 + * You should have received a copy of the GNU General Public License version
   45.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   45.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   45.21 + * 
   45.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   45.23 + * or visit www.oracle.com if you need additional information or have any
   45.24 + * questions.
   45.25 + */
   45.26 +
   45.27 +/**
   45.28 + * JDK-8027828: ClassCastException when converting return value of a Java method to boolean
   45.29 + *
   45.30 + * @test
   45.31 + * @run
   45.32 + */
   45.33 +
   45.34 +var x = new java.util.HashMap()
   45.35 +x.put('test', new java.io.File('test'))
   45.36 +if (x.get("test")) {
   45.37 +  print('Found!')
   45.38 +}
    46.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    46.2 +++ b/test/script/basic/JDK-8027828.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    46.3 @@ -0,0 +1,1 @@
    46.4 +Found!
    47.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    47.2 +++ b/test/script/basic/JDK-8028020.js	Tue Dec 03 14:13:15 2013 +0400
    47.3 @@ -0,0 +1,40 @@
    47.4 +/*
    47.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    47.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    47.7 + * 
    47.8 + * This code is free software; you can redistribute it and/or modify it
    47.9 + * under the terms of the GNU General Public License version 2 only, as
   47.10 + * published by the Free Software Foundation.
   47.11 + * 
   47.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   47.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   47.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   47.15 + * version 2 for more details (a copy is included in the LICENSE file that
   47.16 + * accompanied this code).
   47.17 + * 
   47.18 + * You should have received a copy of the GNU General Public License version
   47.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   47.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   47.21 + * 
   47.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   47.23 + * or visit www.oracle.com if you need additional information or have any
   47.24 + * questions.
   47.25 + */
   47.26 +
   47.27 +/**
   47.28 + * JDK-8028020: Function parameter as last expression in comma in return value causes bad type calculation
   47.29 + *
   47.30 + * @test
   47.31 + * @run
   47.32 + */
   47.33 +
   47.34 +function f(x) {
   47.35 +    return 1, x
   47.36 +}
   47.37 +
   47.38 +function g(x, y) {
   47.39 +    return x, y
   47.40 +}
   47.41 +
   47.42 +print(f("'1, x' works."))
   47.43 +print(g(42, "'x, y' works too."))
    48.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    48.2 +++ b/test/script/basic/JDK-8028020.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    48.3 @@ -0,0 +1,2 @@
    48.4 +'1, x' works.
    48.5 +'x, y' works too.
    49.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    49.2 +++ b/test/script/basic/convert.js	Tue Dec 03 14:13:15 2013 +0400
    49.3 @@ -0,0 +1,61 @@
    49.4 +/*
    49.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    49.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    49.7 + * 
    49.8 + * This code is free software; you can redistribute it and/or modify it
    49.9 + * under the terms of the GNU General Public License version 2 only, as
   49.10 + * published by the Free Software Foundation.
   49.11 + * 
   49.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   49.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   49.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   49.15 + * version 2 for more details (a copy is included in the LICENSE file that
   49.16 + * accompanied this code).
   49.17 + * 
   49.18 + * You should have received a copy of the GNU General Public License version
   49.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   49.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   49.21 + * 
   49.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   49.23 + * or visit www.oracle.com if you need additional information or have any
   49.24 + * questions.
   49.25 + */
   49.26 +
   49.27 +/**
   49.28 + * Tests for convert method of ScriptUtils.
   49.29 + *
   49.30 + * @test
   49.31 + * @run
   49.32 + */
   49.33 +
   49.34 +var ScriptUtils = Java.type("jdk.nashorn.api.scripting.ScriptUtils");
   49.35 +obj = { valueOf: function() { print("hello"); return 43.3; } };
   49.36 +
   49.37 +// object to double
   49.38 +print(ScriptUtils.convert(obj, java.lang.Number.class));
   49.39 +
   49.40 +// array to List
   49.41 +var arr = [3, 44, 23, 33];
   49.42 +var list = ScriptUtils.convert(arr, java.util.List.class);
   49.43 +print(list instanceof java.util.List)
   49.44 +print(list);
   49.45 +
   49.46 +// object to Map
   49.47 +obj = { foo: 333, bar: 'hello'};
   49.48 +var map = ScriptUtils.convert(obj, java.util.Map.class);
   49.49 +print(map instanceof java.util.Map);
   49.50 +for (m in map) {
   49.51 +   print(m + " " + map[m]);
   49.52 +}
   49.53 +
   49.54 +// object to String
   49.55 +obj = { toString: function() { print("in toString"); return "foo" } };
   49.56 +print(ScriptUtils.convert(obj, java.lang.String.class));
   49.57 +
   49.58 +// array to Java array
   49.59 +var jarr = ScriptUtils.convert(arr, Java.type("int[]"));
   49.60 +print(jarr instanceof Java.type("int[]"));
   49.61 +for (i in jarr) {
   49.62 +    print(jarr[i]);
   49.63 +}
   49.64 +
    50.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    50.2 +++ b/test/script/basic/convert.js.EXPECTED	Tue Dec 03 14:13:15 2013 +0400
    50.3 @@ -0,0 +1,14 @@
    50.4 +hello
    50.5 +43.3
    50.6 +true
    50.7 +[3, 44, 23, 33]
    50.8 +true
    50.9 +foo 333
   50.10 +bar hello
   50.11 +in toString
   50.12 +foo
   50.13 +true
   50.14 +3
   50.15 +44
   50.16 +23
   50.17 +33
    51.1 --- a/test/script/jfx.js	Sun Nov 03 07:33:34 2013 +0000
    51.2 +++ b/test/script/jfx.js	Tue Dec 03 14:13:15 2013 +0400
    51.3 @@ -37,13 +37,24 @@
    51.4  var Scene                = Java.type("javafx.scene.Scene");
    51.5  var Stage                = Java.type("javafx.stage.Stage");
    51.6  var File                 = Java.type("java.io.File");
    51.7 -var Timer                = Java.type("java.util.Timer");
    51.8 -var TimerTask            = Java.type("java.util.TimerTask");
    51.9  var OSInfo               = Java.type("sun.awt.OSInfo");
   51.10  var OSType               = Java.type("sun.awt.OSInfo.OSType");
   51.11  var StringBuffer         = Java.type("java.lang.StringBuffer");
   51.12 +var Paint                = Java.type("javafx.scene.paint.Paint");
   51.13 +var Color                = Java.type("javafx.scene.paint.Color");
   51.14 +var Image                = Java.type("javafx.scene.image.Image");
   51.15 +var Canvas               = Java.type("javafx.scene.canvas.Canvas");
   51.16 +var BorderPane           = Java.type("javafx.scene.layout.BorderPane");
   51.17 +var StackPane            = Java.type("javafx.scene.layout.StackPane");
   51.18 +var StrokeLineCap        = Java.type("javafx.scene.shape.StrokeLineCap");
   51.19 +var Platform             = Java.type("javafx.application.Platform");
   51.20 +var Runnable             = Java.type("java.lang.Runnable");
   51.21 +var RunnableExtend       = Java.extend(Runnable);
   51.22 +var AnimationTimer       = Java.type("javafx.animation.AnimationTimer");
   51.23 +var AnimationTimerExtend = Java.extend(AnimationTimer);
   51.24 +var Timer                = Java.type("java.util.Timer");
   51.25 +var TimerTask            = Java.type("java.util.TimerTask");
   51.26  
   51.27 -var WAIT = 2000;
   51.28  var TESTNAME = "test";
   51.29  var fsep = System.getProperty("file.separator");
   51.30  
   51.31 @@ -53,14 +64,16 @@
   51.32          run: function run() {
   51.33              var tmpdir = System.getProperty("java.io.tmpdir");
   51.34              var timenow = (new Date()).getTime();
   51.35 -            makeScreenShot(tmpdir + fsep + "screenshot" + timenow +".png");
   51.36 -            var dupImg = isDuplicateImages(tmpdir + fsep + "screenshot" + timenow +".png", __DIR__ + "jfx" + fsep + TESTNAME + fsep + "golden");
   51.37 -            (new File(mpdir + fsep + "screenshot" + timenow +".png")).delete();
   51.38 -            if (!dupImg) System.err.println("ERROR: screenshot does not match golden image");
   51.39 +            var scrShotTmp = tmpdir + fsep + "screenshot" + timenow +".png";
   51.40 +            var goldenImageDir = __DIR__ + "jfx" + fsep + TESTNAME + fsep + "golden";
   51.41 +            makeScreenShot(scrShotTmp);
   51.42 +            var dupImg = isDuplicateImages(scrShotTmp, goldenImageDir);
   51.43 +            (new File(scrShotTmp)).delete();
   51.44 +            if (!dupImg) System.err.println("ERROR: screenshot does not match the golden image");
   51.45              exit(0);
   51.46          }
   51.47      };
   51.48 -    raceTimer.schedule(timerTask, WAIT);
   51.49 +    raceTimer.schedule(timerTask, 100);
   51.50  }
   51.51  
   51.52  function makeScreenShot(shootToImg) {
   51.53 @@ -70,10 +83,10 @@
   51.54     imageJemmy.save(shootToImg);
   51.55  }
   51.56  
   51.57 -function isDuplicateImages(file1, file2) {
   51.58 -    var f1 = new File(file1);
   51.59 +function isDuplicateImages(screenShot, goldenDir) {
   51.60 +    var f1 = new File(screenShot);
   51.61      var f2;
   51.62 -    var sb = new StringBuffer(file2);
   51.63 +    var sb = new StringBuffer(goldenDir);
   51.64      if (OSInfo.getOSType() == OSType.WINDOWS) {
   51.65          f2 = new File(sb.append(fsep + "windows.png").toString());
   51.66      } else if (OSInfo.getOSType() == OSType.LINUX) {
   51.67 @@ -81,8 +94,6 @@
   51.68      } else if (OSInfo.getOSType() == OSType.MACOSX) {
   51.69          f2 = new File(sb.append(fsep + "macosx.png").toString());
   51.70      }
   51.71 -    print(f1.getAbsolutePath());
   51.72 -    print(f2.getAbsolutePath());
   51.73      if (f1.exists() && f2.exists()) {
   51.74          var image1 = new AWTImage(PNGDecoder.decode(f1.getAbsolutePath()));
   51.75          var image2 = new AWTImage(PNGDecoder.decode(f2.getAbsolutePath()));
    52.1 --- a/test/script/jfx/flyingimage.js	Sun Nov 03 07:33:34 2013 +0000
    52.2 +++ b/test/script/jfx/flyingimage.js	Tue Dec 03 14:13:15 2013 +0400
    52.3 @@ -31,15 +31,6 @@
    52.4  
    52.5  TESTNAME = "flyingimage";
    52.6  
    52.7 -var Image                = Java.type("javafx.scene.image.Image");
    52.8 -var Color                = Java.type("javafx.scene.paint.Color");
    52.9 -var Canvas               = Java.type("javafx.scene.canvas.Canvas");
   52.10 -var BorderPane           = Java.type("javafx.scene.layout.BorderPane");
   52.11 -var StackPane            = Java.type("javafx.scene.layout.StackPane");
   52.12 -var Font                 = Java.type("javafx.scene.text.Font");
   52.13 -var FontSmoothingType    = Java.type("javafx.scene.text.FontSmoothingType");
   52.14 -var Text                 = Java.type("javafx.scene.text.Text");
   52.15 -
   52.16  var WIDTH = 800;
   52.17  var HEIGHT = 600;
   52.18  var canvas = new Canvas(WIDTH, HEIGHT);
   52.19 @@ -48,10 +39,9 @@
   52.20  }
   52.21  var imageUrl = fileToURL(__DIR__ + "flyingimage/flyingimage.png");
   52.22  var img = new Image(imageUrl);
   52.23 -var font = new Font("Arial", 16);
   52.24 -var t = 0;
   52.25  var isFrameRendered = false;
   52.26  function renderFrame() {
   52.27 +    var t = frame;
   52.28      var gc = canvas.graphicsContext2D;
   52.29      gc.setFill(Color.web("#cccccc"));
   52.30      gc.fillRect(0, 0, WIDTH, HEIGHT);
   52.31 @@ -61,7 +51,7 @@
   52.32      var c = 200;
   52.33      var msc= 0.5 * HEIGHT / img.height;
   52.34      var sp0 = 0.003;
   52.35 -    for (var h = 0; h < c; h++, t++) {
   52.36 +    for (var h = 0; h < c; h++) {
   52.37          gc.setTransform(1, 0, 0, 1, 0, 0);
   52.38          var yh = h / (c - 1);
   52.39          gc.translate((0.5 + Math.sin(t * sp0 + h * 0.1) / 3) * WIDTH, 25 + (HEIGHT * 3 / 4 - 40) * (yh * yh));
   52.40 @@ -69,15 +59,26 @@
   52.41          gc.rotate(90 * Math.sin(t * sp0 + h * 0.1 + Math.PI));
   52.42          gc.scale(sc, sc);
   52.43          gc.drawImage(img, -img.width / 2, -img.height / 2);
   52.44 -     }
   52.45 +    }
   52.46      gc.setTransform(1, 0, 0, 1, 0, 0);
   52.47      isFrameRendered = true;
   52.48  }
   52.49  var stack = new StackPane();
   52.50  var pane = new BorderPane();
   52.51 -
   52.52  pane.setCenter(canvas);
   52.53  stack.getChildren().add(pane);
   52.54  $STAGE.scene = new Scene(stack);
   52.55 -renderFrame();
   52.56 -checkImageAndExit();
   52.57 +var frame = 0;
   52.58 +var timer = new AnimationTimerExtend() {
   52.59 +    handle: function handle(now) {
   52.60 +        if (frame < 200) {
   52.61 +            renderFrame();
   52.62 +            frame++;
   52.63 +        } else {
   52.64 +            checkImageAndExit();        
   52.65 +            timer.stop();
   52.66 +        }
   52.67 +    }
   52.68 +};
   52.69 +timer.start();
   52.70 + 
    53.1 Binary file test/script/jfx/flyingimage/flyingimage.png has changed
    54.1 Binary file test/script/jfx/flyingimage/golden/linux.png has changed
    55.1 Binary file test/script/jfx/flyingimage/golden/macosx.png has changed
    56.1 Binary file test/script/jfx/flyingimage/golden/windows.png has changed
    57.1 --- a/test/script/jfx/kaleidoscope.js	Sun Nov 03 07:33:34 2013 +0000
    57.2 +++ b/test/script/jfx/kaleidoscope.js	Tue Dec 03 14:13:15 2013 +0400
    57.3 @@ -30,13 +30,6 @@
    57.4   */
    57.5  
    57.6  TESTNAME = "kaleidoscope";
    57.7 -WAIT = 4000;
    57.8 -
    57.9 -var Paint                = Java.type("javafx.scene.paint.Paint");
   57.10 -var Canvas               = Java.type("javafx.scene.canvas.Canvas");
   57.11 -var BorderPane           = Java.type("javafx.scene.layout.BorderPane");
   57.12 -var StackPane            = Java.type("javafx.scene.layout.StackPane");
   57.13 -var StrokeLineCap        = Java.type("javafx.scene.shape.StrokeLineCap");
   57.14          
   57.15  var WIDTH = 800;
   57.16  var HEIGHT = 600;
   57.17 @@ -56,26 +49,28 @@
   57.18  var r,e;
   57.19  var fade;
   57.20  var prv_x,prv_y,prv_x2,prv_y2;
   57.21 +var isFrameRendered = false;
   57.22  
   57.23  function renderFrame() {
   57.24 -	a=0.2*angle;
   57.25 -	b=0.7*angle;
   57.26 -	r=0;
   57.27 -	fade=32;
   57.28 -	for(var i=0;i<6;i++)
   57.29 -		{
   57.30 -		c[i]=1.0/(i+1)/2;
   57.31 -		d[i]=1.0/(i+1)/2;
   57.32 -		}
   57.33 -	radius=Math.round((WIDTH+HEIGHT)/8);
   57.34 -	e=radius*0.2;
   57.35 -	p_x=Math.round(WIDTH/2);
   57.36 -	p_y=Math.round(HEIGHT/2);
   57.37 -	x=(radius*c[0])*Math.cos(a*d[1])+(radius*c[2])*Math.sin(a*d[3])+(radius*c[4])*Math.sin(a*d[5]);
   57.38 -	y=(radius*c[5])*Math.sin(a*d[4])+(radius*c[3])*Math.cos(a*d[2])+(radius*c[1])*Math.cos(a*d[0]);
   57.39 -    for (i = 0; i < 800; i++) {
   57.40 -        anim();
   57.41 +	if (!isFrameRendered) {
   57.42 +        a=0.2*angle;
   57.43 +		b=0.7*angle;
   57.44 +		r=0;
   57.45 +		fade=32;
   57.46 +		for(var i=0;i<6;i++)
   57.47 +			{
   57.48 +			c[i]=1.0/(i+1)/2;
   57.49 +			d[i]=1.0/(i+1)/2;
   57.50 +			}
   57.51 +		radius=Math.round((WIDTH+HEIGHT)/8);
   57.52 +		e=radius*0.2;
   57.53 +		p_x=Math.round(WIDTH/2);
   57.54 +		p_y=Math.round(HEIGHT/2);
   57.55 +		x=(radius*c[0])*Math.cos(a*d[1])+(radius*c[2])*Math.sin(a*d[3])+(radius*c[4])*Math.sin(a*d[5]);
   57.56 +		y=(radius*c[5])*Math.sin(a*d[4])+(radius*c[3])*Math.cos(a*d[2])+(radius*c[1])*Math.cos(a*d[0]);
   57.57 +        isFrameRendered = true;
   57.58      }
   57.59 +    anim();
   57.60  }
   57.61  
   57.62  function anim() {
   57.63 @@ -154,9 +149,19 @@
   57.64  
   57.65  var stack = new StackPane();
   57.66  var pane = new BorderPane();
   57.67 -
   57.68  pane.setCenter(canvas);
   57.69  stack.getChildren().add(pane);
   57.70  $STAGE.scene = new Scene(stack);
   57.71 -renderFrame();
   57.72 -checkImageAndExit();
   57.73 \ No newline at end of file
   57.74 +var frame = 0;
   57.75 +var timer = new AnimationTimerExtend() {
   57.76 +    handle: function handle(now) {
   57.77 +        if (frame < 800) {
   57.78 +            renderFrame();
   57.79 +            frame++;
   57.80 +        } else {
   57.81 +            checkImageAndExit();
   57.82 +            timer.stop();
   57.83 +        }
   57.84 +    }
   57.85 +};
   57.86 +timer.start();
    58.1 Binary file test/script/jfx/kaleidoscope/golden/linux.png has changed
    59.1 Binary file test/script/jfx/kaleidoscope/golden/macosx.png has changed
    60.1 Binary file test/script/jfx/kaleidoscope/golden/windows.png has changed
    61.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    61.2 +++ b/test/script/jfx/spread.js	Tue Dec 03 14:13:15 2013 +0400
    61.3 @@ -0,0 +1,222 @@
    61.4 +/*
    61.5 + * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
    61.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    61.7 + * 
    61.8 + * This code is free software; you can redistribute it and/or modify it
    61.9 + * under the terms of the GNU General Public License version 2 only, as
   61.10 + * published by the Free Software Foundation.
   61.11 + * 
   61.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   61.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   61.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   61.15 + * version 2 for more details (a copy is included in the LICENSE file that
   61.16 + * accompanied this code).
   61.17 + * 
   61.18 + * You should have received a copy of the GNU General Public License version
   61.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   61.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   61.21 + * 
   61.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   61.23 + * or visit www.oracle.com if you need additional information or have any
   61.24 + * questions.
   61.25 + */
   61.26 +
   61.27 +/**
   61.28 + * Testing JavaFX canvas run by Nashorn.
   61.29 + *
   61.30 + * @test/nocompare
   61.31 + * @run
   61.32 + * @fork
   61.33 + */
   61.34 + 
   61.35 +TESTNAME = "spread";
   61.36 +
   61.37 +var WIDTH = 800;
   61.38 +var HEIGHT = 600;
   61.39 +var canvas = new Canvas(WIDTH, HEIGHT);
   61.40 +var context = canvas.graphicsContext2D;
   61.41 +
   61.42 +/* "Spread" tech demo of canvas by Tom Theisen
   61.43 + *
   61.44 + * This will animate a sequence of branch structures in a canvas element.
   61.45 + * Each frame, a new direction is calculated, similar to the last frame.
   61.46 + */
   61.47 +
   61.48 +var start_width = 20;           // starting width of each branch
   61.49 +var frame_time = 30;            // milliseconds per frame
   61.50 +var straighten_factor = 0.95;   // value from 0 to 1, factor applied to direction_offset every frame
   61.51 +var curviness = 0.2;            // amount of random direction change each frame
   61.52 +
   61.53 +var color_speed = 0.03;     // speed at which colors change when cycling is enabled
   61.54 +var branch_shrink = 0.95;   // factor by which branches shrink every frame
   61.55 +var min_width = 1;          // minimum WIDTH for branch, after which they are discontinued
   61.56 +var branch_opacity = 0.4;   // opacity of lines drawn
   61.57 +var branch_count = 3;       // branch count per tree
   61.58 +var branch_bud_size = 0.5;  // ratio of original branch size at which branch will split
   61.59 +var branch_bud_angle = 1;   // angle offset for split branch;
   61.60 +
   61.61 +var paper;                  // reference to graphics context
   61.62 +var branches = Object();    // linked list of active branches
   61.63 +var color_styles = [];      // pre-computed list of colors as styles. format: (r,g,b,a)    
   61.64 +var direction_offset = 0;   // current direction offset in radians.  this is applied to all branches.
   61.65 +var frame = 0;              // frame counter
   61.66 +var timespent = 0;          // total time spent so far, used to calculate average frame render duration
   61.67 +var frameratespan;          // html span element for updating performance number
   61.68 +
   61.69 +// preferences object, contains an attribute for each user setting
   61.70 +var prefs = {
   61.71 +    wrap: true,             // causes branches reaching edge of viewable area to appear on opposite side
   61.72 +    fade: false,             // fade existing graphics on each frame
   61.73 +    cycle: true,            // gradually change colors each frame
   61.74 +    new_branch_frames: 20    // number of frames elapsed between each auto-generated tree
   61.75 +};
   61.76 +
   61.77 +// create tree at the specified position with number of branches
   61.78 +function create_tree(branches, start_width, position, branch_count) {
   61.79 +    var angle_offset = Math.PI * 2 / branch_count;
   61.80 +    for (var i = 0; i < branch_count; ++i) {
   61.81 +        branch_add(branches, new Branch(position, angle_offset * i, start_width));
   61.82 +    }
   61.83 +}
   61.84 +
   61.85 +// add branch to collection
   61.86 +function branch_add(branches, branch) {
   61.87 +    branch.next = branches.next;
   61.88 +    branches.next = branch;
   61.89 +}
   61.90 +
   61.91 +// get the coordinates for the position of a new tree
   61.92 +// use the center of the canvas
   61.93 +function get_new_tree_center(width, height) {
   61.94 +    return {
   61.95 +        x: 0.5 * width, 
   61.96 +        y: 0.5 * height 
   61.97 +    };
   61.98 +}
   61.99 +
  61.100 +// Branch constructor
  61.101 +// position has x and y properties
  61.102 +// direction is in radians
  61.103 +function Branch(position, direction, width) {
  61.104 +    this.x = position.x;
  61.105 +    this.y = position.y;
  61.106 +    this.width = width;
  61.107 +    this.original_width = width;
  61.108 +    this.direction = direction;
  61.109 +}
  61.110 +
  61.111 +// update position, direction and width of a particular branch
  61.112 +function branch_update(branches, branch, paper) {
  61.113 +    paper.beginPath();
  61.114 +    paper.lineWidth = branch.width;
  61.115 +    paper.moveTo(branch.x, branch.y);
  61.116 +    
  61.117 +    branch.width *= branch_shrink;
  61.118 +    branch.direction += direction_offset;
  61.119 +    branch.x += Math.cos(branch.direction) * branch.width;
  61.120 +    branch.y += Math.sin(branch.direction) * branch.width;
  61.121 +    
  61.122 +    paper.lineTo(branch.x, branch.y);
  61.123 +    paper.stroke();
  61.124 +    
  61.125 +    if (prefs.wrap) wrap_branch(branch, WIDTH, HEIGHT);
  61.126 +
  61.127 +    if (branch.width < branch.original_width * branch_bud_size) {
  61.128 +        branch.original_width *= branch_bud_size;
  61.129 +        branch_add(branches, new Branch(branch, branch.direction + 1, branch.original_width));
  61.130 +    }
  61.131 +}
  61.132 +
  61.133 +function draw_frame() {
  61.134 +    if (prefs.fade) {
  61.135 +        paper.fillRect(0, 0, WIDTH, HEIGHT);
  61.136 +    }
  61.137 +
  61.138 +    if (prefs.cycle) {
  61.139 +        paper.setStroke(Paint.valueOf(color_styles[frame % color_styles.length]));
  61.140 +    }
  61.141 +
  61.142 +    if (frame++ % prefs.new_branch_frames == 0) {
  61.143 +        create_tree(branches, start_width, get_new_tree_center(WIDTH, HEIGHT), branch_count);
  61.144 +    }
  61.145 +    
  61.146 +    direction_offset += (0.35 + (frame % 200) * 0.0015) * curviness - curviness / 2;
  61.147 +    direction_offset *= straighten_factor;
  61.148 +    
  61.149 +    var branch = branches;
  61.150 +    var prev_branch = branches;
  61.151 +    while (branch = branch.next) {
  61.152 +        branch_update(branches, branch, paper);
  61.153 +        
  61.154 +        if (branch.width < min_width) {
  61.155 +            // remove branch from list
  61.156 +            prev_branch.next = branch.next;
  61.157 +        }
  61.158 +        
  61.159 +        prev_branch = branch;
  61.160 +    }
  61.161 +}
  61.162 +
  61.163 +// constrain branch position to visible area by "wrapping" from edge to edge
  61.164 +function wrap_branch(branch, WIDTH, HEIGHT) {
  61.165 +    branch.x = positive_mod(branch.x, WIDTH);
  61.166 +    branch.y = positive_mod(branch.y, HEIGHT);
  61.167 +}
  61.168 +
  61.169 +// for a < 0, b > 0, javascript returns a negative number for a % b
  61.170 +// this is a variant of the % operator that adds b to the result in this case
  61.171 +function positive_mod(a, b) {
  61.172 +    // ECMA 262 11.5.3: Applying the % Operator 
  61.173 +    // remainder operator does not convert operands to integers,
  61.174 +    // although negative results are possible
  61.175 +
  61.176 +    return ((a % b) + b) % b;
  61.177 +}
  61.178 +
  61.179 +// pre-compute color styles that will be used for color cycling
  61.180 +function populate_colors(color_speed, color_styles, branch_opacity) {
  61.181 +    // used in calculation of RGB values
  61.182 +    var two_thirds_pi = Math.PI * 2 / 3;
  61.183 +    var four_thirds_pi = Math.PI * 4 / 3;
  61.184 +    var two_pi = Math.PI * 2;
  61.185 +
  61.186 +    // hue does represent hue, but not in the conventional HSL scheme
  61.187 +    for(var hue = 0; hue < two_pi; hue += color_speed) {
  61.188 +        var r = Math.floor(Math.sin(hue) * 128 + 128);
  61.189 +        var g = Math.floor(Math.sin(hue + two_thirds_pi) * 128 + 128);
  61.190 +        var b = Math.floor(Math.sin(hue + four_thirds_pi) * 128 + 128);
  61.191 +        color = "rgba(" + [r, g, b, branch_opacity].join() + ")";
  61.192 +
  61.193 +        color_styles.push(color);
  61.194 +    }
  61.195 +}
  61.196 +
  61.197 +// apply initial settings to canvas object
  61.198 +function setup_canvas() {
  61.199 +    paper = canvas.graphicsContext2D;
  61.200 +    paper.setFill(Paint.valueOf('rgb(0, 0, 0)'));
  61.201 +    paper.fillRect(0, 0, WIDTH, HEIGHT);
  61.202 +    paper.setFill(Paint.valueOf("rgba(0, 0, 0, 0.005)"));
  61.203 +    paper.setStroke(Paint.valueOf("rgba(128, 128, 64, " + String(branch_opacity) + ")"));
  61.204 +}
  61.205 +
  61.206 +populate_colors(color_speed, color_styles, branch_opacity);
  61.207 +setup_canvas();
  61.208 +
  61.209 +var stack = new StackPane();
  61.210 +var pane = new BorderPane();
  61.211 +pane.setCenter(canvas);
  61.212 +stack.getChildren().add(pane);
  61.213 +$STAGE.scene = new Scene(stack);
  61.214 +var timer = new AnimationTimerExtend() {
  61.215 +    handle: function handle(now) {
  61.216 +        if (frame < 200) {
  61.217 +		    draw_frame();
  61.218 +        } else {
  61.219 +            checkImageAndExit();
  61.220 +            timer.stop();
  61.221 +        }
  61.222 +    }
  61.223 +};
  61.224 +timer.start();
  61.225 +
    62.1 Binary file test/script/jfx/spread/golden/linux.png has changed
    63.1 Binary file test/script/jfx/spread/golden/macosx.png has changed
    64.1 Binary file test/script/jfx/spread/golden/windows.png has changed
    65.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    65.2 +++ b/test/src/jdk/nashorn/api/javaaccess/ConsStringTest.java	Tue Dec 03 14:13:15 2013 +0400
    65.3 @@ -0,0 +1,99 @@
    65.4 +/*
    65.5 + * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
    65.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    65.7 + *
    65.8 + * This code is free software; you can redistribute it and/or modify it
    65.9 + * under the terms of the GNU General Public License version 2 only, as
   65.10 + * published by the Free Software Foundation.  Oracle designates this
   65.11 + * particular file as subject to the "Classpath" exception as provided
   65.12 + * by Oracle in the LICENSE file that accompanied this code.
   65.13 + *
   65.14 + * This code is distributed in the hope that it will be useful, but WITHOUT
   65.15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   65.16 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   65.17 + * version 2 for more details (a copy is included in the LICENSE file that
   65.18 + * accompanied this code).
   65.19 + *
   65.20 + * You should have received a copy of the GNU General Public License version
   65.21 + * 2 along with this work; if not, write to the Free Software Foundation,
   65.22 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   65.23 + *
   65.24 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   65.25 + * or visit www.oracle.com if you need additional information or have any
   65.26 + * questions.
   65.27 + */
   65.28 +
   65.29 +package jdk.nashorn.api.javaaccess;
   65.30 +
   65.31 +import static org.testng.AssertJUnit.assertEquals;
   65.32 +
   65.33 +import java.util.HashMap;
   65.34 +import java.util.Map;
   65.35 +import javax.script.Bindings;
   65.36 +import javax.script.ScriptContext;
   65.37 +import javax.script.ScriptEngine;
   65.38 +import javax.script.ScriptEngineManager;
   65.39 +import javax.script.ScriptException;
   65.40 +import jdk.nashorn.api.scripting.JSObject;
   65.41 +import org.testng.TestNG;
   65.42 +import org.testng.annotations.AfterClass;
   65.43 +import org.testng.annotations.BeforeClass;
   65.44 +import org.testng.annotations.Test;
   65.45 +
   65.46 +public class ConsStringTest {
   65.47 +    private static ScriptEngine e = null;
   65.48 +
   65.49 +    public static void main(final String[] args) {
   65.50 +        TestNG.main(args);
   65.51 +    }
   65.52 +
   65.53 +    @BeforeClass
   65.54 +    public static void setUpClass() throws ScriptException {
   65.55 +        e = new ScriptEngineManager().getEngineByName("nashorn");
   65.56 +    }
   65.57 +
   65.58 +    @AfterClass
   65.59 +    public static void tearDownClass() {
   65.60 +        e = null;
   65.61 +    }
   65.62 +
   65.63 +    @Test
   65.64 +    public void testConsStringFlattening() throws ScriptException {
   65.65 +        final Bindings b = e.getBindings(ScriptContext.ENGINE_SCOPE);
   65.66 +        final Map<Object, Object> m = new HashMap<>();
   65.67 +        b.put("m", m);
   65.68 +        e.eval("var x = 'f'; x += 'oo'; var y = 'b'; y += 'ar'; m.put(x, y)");
   65.69 +        assertEquals("bar", m.get("foo"));
   65.70 +    }
   65.71 +
   65.72 +    @Test
   65.73 +    public void testConsStringFromMirror() throws ScriptException {
   65.74 +        final Bindings b = e.getBindings(ScriptContext.ENGINE_SCOPE);
   65.75 +        final Map<Object, Object> m = new HashMap<>();
   65.76 +        e.eval("var x = 'f'; x += 'oo'; var obj = {x: x};");
   65.77 +        assertEquals("foo", ((JSObject)b.get("obj")).getMember("x"));
   65.78 +    }
   65.79 +
   65.80 +    @Test
   65.81 +    public void testArrayConsString() throws ScriptException {
   65.82 +        final Bindings b = e.getBindings(ScriptContext.ENGINE_SCOPE);
   65.83 +        final ArrayHolder h = new ArrayHolder();
   65.84 +        b.put("h", h);
   65.85 +        e.eval("var x = 'f'; x += 'oo'; h.array = [x];");
   65.86 +        assertEquals(1, h.array.length);
   65.87 +        assertEquals("foo", h.array[0]);
   65.88 +    }
   65.89 +
   65.90 +
   65.91 +    public static class ArrayHolder {
   65.92 +        private Object[] array;
   65.93 +
   65.94 +        public void setArray(Object[] array) {
   65.95 +            this.array = array;
   65.96 +        }
   65.97 +
   65.98 +        public Object[] getArray() {
   65.99 +            return array;
  65.100 +        }
  65.101 +    }
  65.102 +}
    66.1 --- a/test/src/jdk/nashorn/api/scripting/ScriptEngineTest.java	Sun Nov 03 07:33:34 2013 +0000
    66.2 +++ b/test/src/jdk/nashorn/api/scripting/ScriptEngineTest.java	Tue Dec 03 14:13:15 2013 +0400
    66.3 @@ -523,6 +523,18 @@
    66.4          assertEquals(sw.toString(), println("34 true hello"));
    66.5      }
    66.6  
    66.7 +    @Test
    66.8 +    public void scriptObjectAutoConversionTest() throws ScriptException {
    66.9 +        final ScriptEngineManager m = new ScriptEngineManager();
   66.10 +        final ScriptEngine e = m.getEngineByName("nashorn");
   66.11 +        e.eval("obj = { foo: 'hello' }");
   66.12 +        e.put("Window", e.eval("Packages.jdk.nashorn.api.scripting.Window"));
   66.13 +        assertEquals(e.eval("Window.funcJSObject(obj)"), "hello");
   66.14 +        assertEquals(e.eval("Window.funcScriptObjectMirror(obj)"), "hello");
   66.15 +        assertEquals(e.eval("Window.funcMap(obj)"), "hello");
   66.16 +        assertEquals(e.eval("Window.funcJSObject(obj)"), "hello");
   66.17 +    }
   66.18 +
   66.19      private static final String LINE_SEPARATOR = System.getProperty("line.separator");
   66.20  
   66.21      // Returns String that would be the result of calling PrintWriter.println
    67.1 --- a/test/src/jdk/nashorn/api/scripting/ScriptObjectMirrorTest.java	Sun Nov 03 07:33:34 2013 +0000
    67.2 +++ b/test/src/jdk/nashorn/api/scripting/ScriptObjectMirrorTest.java	Tue Dec 03 14:13:15 2013 +0400
    67.3 @@ -26,6 +26,7 @@
    67.4  package jdk.nashorn.api.scripting;
    67.5  
    67.6  import java.util.HashMap;
    67.7 +import java.util.List;
    67.8  import java.util.Map;
    67.9  import javax.script.ScriptEngine;
   67.10  import javax.script.ScriptEngineManager;
   67.11 @@ -227,4 +228,28 @@
   67.12          final Object newObj = ((ScriptObjectMirror)e2obj.getMember("foo")).newObject();
   67.13          assertTrue(newObj instanceof ScriptObjectMirror);
   67.14      }
   67.15 +
   67.16 +    @Test
   67.17 +    public void conversionTest() throws ScriptException {
   67.18 +        final ScriptEngineManager m = new ScriptEngineManager();
   67.19 +        final ScriptEngine e = m.getEngineByName("nashorn");
   67.20 +        final ScriptObjectMirror arr = (ScriptObjectMirror)e.eval("[33, 45, 23]");
   67.21 +        final int[] intArr = arr.to(int[].class);
   67.22 +        assertEquals(intArr[0], 33);
   67.23 +        assertEquals(intArr[1], 45);
   67.24 +        assertEquals(intArr[2], 23);
   67.25 +
   67.26 +        final List<?> list = arr.to(List.class);
   67.27 +        assertEquals(list.get(0), 33);
   67.28 +        assertEquals(list.get(1), 45);
   67.29 +        assertEquals(list.get(2), 23);
   67.30 +
   67.31 +        ScriptObjectMirror obj = (ScriptObjectMirror)e.eval(
   67.32 +            "({ valueOf: function() { return 42 } })");
   67.33 +        assertEquals(Double.valueOf(42.0), obj.to(Double.class));
   67.34 +
   67.35 +        obj = (ScriptObjectMirror)e.eval(
   67.36 +            "({ toString: function() { return 'foo' } })");
   67.37 +        assertEquals("foo", obj.to(String.class));
   67.38 +    }
   67.39  }
    68.1 --- a/test/src/jdk/nashorn/api/scripting/Window.java	Sun Nov 03 07:33:34 2013 +0000
    68.2 +++ b/test/src/jdk/nashorn/api/scripting/Window.java	Tue Dec 03 14:13:15 2013 +0400
    68.3 @@ -25,6 +25,9 @@
    68.4  
    68.5  package jdk.nashorn.api.scripting;
    68.6  
    68.7 +import java.util.Map;
    68.8 +import javax.script.Bindings;
    68.9 +
   68.10  public class Window {
   68.11  
   68.12      private String location = "http://localhost:8080/window";
   68.13 @@ -63,4 +66,20 @@
   68.14          System.out.println("window.setTimeout: " + delay + ", code: " + code);
   68.15          return 0;
   68.16      }
   68.17 +
   68.18 +    public static Object funcJSObject(final JSObject jsobj) {
   68.19 +        return jsobj.getMember("foo");
   68.20 +    }
   68.21 +
   68.22 +    public static Object funcScriptObjectMirror(final ScriptObjectMirror sobj) {
   68.23 +        return sobj.get("foo");
   68.24 +    }
   68.25 +
   68.26 +    public static Object funcMap(final Map<?,?> map) {
   68.27 +        return map.get("foo");
   68.28 +    }
   68.29 +
   68.30 +    public static Object funcBindings(final Bindings bindings) {
   68.31 +        return bindings.get("foo");
   68.32 +    }
   68.33  }

mercurial