Setting missing props on all Java source files.


git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@2374 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/dev/core/src/com/google/gwt/dev/jjs/impl/LongCastNormalizer.java b/dev/core/src/com/google/gwt/dev/jjs/impl/LongCastNormalizer.java
index b82b4bb..a340914 100644
--- a/dev/core/src/com/google/gwt/dev/jjs/impl/LongCastNormalizer.java
+++ b/dev/core/src/com/google/gwt/dev/jjs/impl/LongCastNormalizer.java
@@ -1,217 +1,217 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.dev.jjs.impl;

-

-import com.google.gwt.dev.jjs.ast.Context;

-import com.google.gwt.dev.jjs.ast.JBinaryOperation;

-import com.google.gwt.dev.jjs.ast.JCastOperation;

-import com.google.gwt.dev.jjs.ast.JConditional;

-import com.google.gwt.dev.jjs.ast.JExpression;

-import com.google.gwt.dev.jjs.ast.JDeclarationStatement;

-import com.google.gwt.dev.jjs.ast.JMethod;

-import com.google.gwt.dev.jjs.ast.JMethodCall;

-import com.google.gwt.dev.jjs.ast.JModVisitor;

-import com.google.gwt.dev.jjs.ast.JNewArray;

-import com.google.gwt.dev.jjs.ast.JParameter;

-import com.google.gwt.dev.jjs.ast.JPrimitiveType;

-import com.google.gwt.dev.jjs.ast.JProgram;

-import com.google.gwt.dev.jjs.ast.JReturnStatement;

-import com.google.gwt.dev.jjs.ast.JType;

-

-import java.util.List;

-

-/**

- * Synthesize explicit casts to and from the primitive long type where such a

- * cast would have been implicit. The explicit casts serve as markers for

- * {@link CastNormalizer}.

- */

-public class LongCastNormalizer {

-

-  /**

-   * Synthesize casts to longs and from long to trigger conversions.

-   */

-  private class ImplicitCastVisitor extends JModVisitor {

-

-    private JMethod currentMethod;

-    private final JPrimitiveType longType;

-

-    public ImplicitCastVisitor(JPrimitiveType longType) {

-      this.longType = longType;

-    }

-

-    @Override

-    public void endVisit(JBinaryOperation x, Context ctx) {

-      JType lhsType = x.getLhs().getType();

-      JType rhsType = x.getRhs().getType();

-      JType resultType = x.getType();

-

-      if (resultType == program.getTypeJavaLangString()) {

-        // Don't mess with concat.

-        return;

-      }

-

-      // Special case: shift operators always coerce a long RHS to int.

-      if (x.getOp().isShiftOperator()) {

-        if (rhsType == longType) {

-          rhsType = program.getTypePrimitiveInt();

-        }

-      } else if (lhsType == longType || rhsType == longType) {

-        // We must coerce lhs and rhs to the same type, either long or a float.

-

-        // Assume a long type.

-        JType coerceTo = longType;

-

-        // But double / float takes precedence over long.

-        JPrimitiveType floatType = program.getTypePrimitiveFloat();

-        JPrimitiveType doubleType = program.getTypePrimitiveDouble();

-        // See if the lhs can coerce the rhs

-        if ((lhsType == floatType || lhsType == doubleType)) {

-          coerceTo = lhsType;

-        }

-        if (x.getOp().isAssignment()) {

-          // In an assignment, the lhs must coerce the rhs

-          coerceTo = lhsType;

-        } else if ((rhsType == floatType || rhsType == doubleType)) {

-          coerceTo = rhsType;

-        }

-        lhsType = rhsType = coerceTo;

-      }

-

-      JExpression newLhs = checkAndReplace(x.getLhs(), lhsType);

-      JExpression newRhs = checkAndReplace(x.getRhs(), rhsType);

-      if (newLhs != x.getLhs() || newRhs != x.getRhs()) {

-        JBinaryOperation binOp = new JBinaryOperation(program,

-            x.getSourceInfo(), resultType, x.getOp(), newLhs, newRhs);

-        ctx.replaceMe(binOp);

-      }

-    }

-

-    @Override

-    public void endVisit(JConditional x, Context ctx) {

-      JExpression newThen = checkAndReplace(x.getThenExpr(), x.getType());

-      JExpression newElse = checkAndReplace(x.getElseExpr(), x.getType());

-      if (newThen != x.getThenExpr() || newElse != x.getElseExpr()) {

-        JConditional newCond = new JConditional(program, x.getSourceInfo(),

-            x.getType(), x.getIfTest(), newThen, newElse);

-        ctx.replaceMe(newCond);

-      }

-    }

-

-    @Override

-    public void endVisit(JDeclarationStatement x, Context ctx) {

-      JExpression init = x.getInitializer();

-      if (init != null) {

-        init = checkAndReplace(init, x.getVariableRef().getType());

-        if (init != x.getInitializer()) {

-          JDeclarationStatement newStmt = new JDeclarationStatement(program,

-              x.getSourceInfo(), x.getVariableRef(), init);

-          ctx.replaceMe(newStmt);

-        }

-      }

-    }

-

-    @Override

-    public void endVisit(JMethod x, Context ctx) {

-      currentMethod = null;

-    }

-

-    @Override

-    public void endVisit(JMethodCall x, Context ctx) {

-      List<JParameter> params = x.getTarget().params;

-      List<JExpression> args = x.getArgs();

-      for (int i = 0; i < params.size(); ++i) {

-        JParameter param = params.get(i);

-        JExpression arg = args.get(i);

-        JExpression newArg = checkAndReplace(arg, param.getType());

-        if (arg != newArg) {

-          args.set(i, newArg);

-          this.didChange = true;

-        }

-      }

-    }

-

-    @Override

-    public void endVisit(JNewArray x, Context ctx) {

-      JType elementType = x.getArrayType().getElementType();

-      List<JExpression> initializers = x.initializers;

-      if (initializers != null) {

-        for (int i = 0; i < initializers.size(); ++i) {

-          JExpression initializer = initializers.get(i);

-          JExpression newInitializer = checkAndReplace(initializer, elementType);

-          if (initializer != newInitializer) {

-            initializers.set(i, newInitializer);

-            this.didChange = true;

-          }

-        }

-      }

-    }

-

-    @Override

-    public void endVisit(JReturnStatement x, Context ctx) {

-      JExpression expr = x.getExpr();

-      if (expr != null) {

-        JExpression newExpr = checkAndReplace(expr, currentMethod.getType());

-        if (expr != newExpr) {

-          JReturnStatement newStmt = new JReturnStatement(program,

-              x.getSourceInfo(), newExpr);

-          ctx.replaceMe(newStmt);

-        }

-      }

-    }

-

-    @Override

-    public boolean visit(JMethod x, Context ctx) {

-      currentMethod = x;

-      return true;

-    }

-

-    /**

-     * Returns an explicit cast if the target type is long and the input

-     * expression is not a long, or if the target type is floating point and the

-     * expression is a long.

-     */

-    private JExpression checkAndReplace(JExpression arg, JType targetType) {

-      JType argType = arg.getType();

-      if (targetType == argType) {

-        return arg;

-      }

-      if (targetType != longType && argType != longType) {

-        return arg;

-      }

-      // Synthesize a cast to long to force explicit conversion.

-      JCastOperation cast = new JCastOperation(program, arg.getSourceInfo(),

-          targetType, arg);

-      return cast;

-    }

-  }

-

-  public static void exec(JProgram program) {

-    new LongCastNormalizer(program).execImpl();

-  }

-

-  private final JProgram program;

-

-  private LongCastNormalizer(JProgram program) {

-    this.program = program;

-  }

-

-  private void execImpl() {

-    ImplicitCastVisitor visitor = new ImplicitCastVisitor(

-        program.getTypePrimitiveLong());

-    visitor.accept(program);

-  }

-

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.dev.jjs.impl;
+
+import com.google.gwt.dev.jjs.ast.Context;
+import com.google.gwt.dev.jjs.ast.JBinaryOperation;
+import com.google.gwt.dev.jjs.ast.JCastOperation;
+import com.google.gwt.dev.jjs.ast.JConditional;
+import com.google.gwt.dev.jjs.ast.JExpression;
+import com.google.gwt.dev.jjs.ast.JDeclarationStatement;
+import com.google.gwt.dev.jjs.ast.JMethod;
+import com.google.gwt.dev.jjs.ast.JMethodCall;
+import com.google.gwt.dev.jjs.ast.JModVisitor;
+import com.google.gwt.dev.jjs.ast.JNewArray;
+import com.google.gwt.dev.jjs.ast.JParameter;
+import com.google.gwt.dev.jjs.ast.JPrimitiveType;
+import com.google.gwt.dev.jjs.ast.JProgram;
+import com.google.gwt.dev.jjs.ast.JReturnStatement;
+import com.google.gwt.dev.jjs.ast.JType;
+
+import java.util.List;
+
+/**
+ * Synthesize explicit casts to and from the primitive long type where such a
+ * cast would have been implicit. The explicit casts serve as markers for
+ * {@link CastNormalizer}.
+ */
+public class LongCastNormalizer {
+
+  /**
+   * Synthesize casts to longs and from long to trigger conversions.
+   */
+  private class ImplicitCastVisitor extends JModVisitor {
+
+    private JMethod currentMethod;
+    private final JPrimitiveType longType;
+
+    public ImplicitCastVisitor(JPrimitiveType longType) {
+      this.longType = longType;
+    }
+
+    @Override
+    public void endVisit(JBinaryOperation x, Context ctx) {
+      JType lhsType = x.getLhs().getType();
+      JType rhsType = x.getRhs().getType();
+      JType resultType = x.getType();
+
+      if (resultType == program.getTypeJavaLangString()) {
+        // Don't mess with concat.
+        return;
+      }
+
+      // Special case: shift operators always coerce a long RHS to int.
+      if (x.getOp().isShiftOperator()) {
+        if (rhsType == longType) {
+          rhsType = program.getTypePrimitiveInt();
+        }
+      } else if (lhsType == longType || rhsType == longType) {
+        // We must coerce lhs and rhs to the same type, either long or a float.
+
+        // Assume a long type.
+        JType coerceTo = longType;
+
+        // But double / float takes precedence over long.
+        JPrimitiveType floatType = program.getTypePrimitiveFloat();
+        JPrimitiveType doubleType = program.getTypePrimitiveDouble();
+        // See if the lhs can coerce the rhs
+        if ((lhsType == floatType || lhsType == doubleType)) {
+          coerceTo = lhsType;
+        }
+        if (x.getOp().isAssignment()) {
+          // In an assignment, the lhs must coerce the rhs
+          coerceTo = lhsType;
+        } else if ((rhsType == floatType || rhsType == doubleType)) {
+          coerceTo = rhsType;
+        }
+        lhsType = rhsType = coerceTo;
+      }
+
+      JExpression newLhs = checkAndReplace(x.getLhs(), lhsType);
+      JExpression newRhs = checkAndReplace(x.getRhs(), rhsType);
+      if (newLhs != x.getLhs() || newRhs != x.getRhs()) {
+        JBinaryOperation binOp = new JBinaryOperation(program,
+            x.getSourceInfo(), resultType, x.getOp(), newLhs, newRhs);
+        ctx.replaceMe(binOp);
+      }
+    }
+
+    @Override
+    public void endVisit(JConditional x, Context ctx) {
+      JExpression newThen = checkAndReplace(x.getThenExpr(), x.getType());
+      JExpression newElse = checkAndReplace(x.getElseExpr(), x.getType());
+      if (newThen != x.getThenExpr() || newElse != x.getElseExpr()) {
+        JConditional newCond = new JConditional(program, x.getSourceInfo(),
+            x.getType(), x.getIfTest(), newThen, newElse);
+        ctx.replaceMe(newCond);
+      }
+    }
+
+    @Override
+    public void endVisit(JDeclarationStatement x, Context ctx) {
+      JExpression init = x.getInitializer();
+      if (init != null) {
+        init = checkAndReplace(init, x.getVariableRef().getType());
+        if (init != x.getInitializer()) {
+          JDeclarationStatement newStmt = new JDeclarationStatement(program,
+              x.getSourceInfo(), x.getVariableRef(), init);
+          ctx.replaceMe(newStmt);
+        }
+      }
+    }
+
+    @Override
+    public void endVisit(JMethod x, Context ctx) {
+      currentMethod = null;
+    }
+
+    @Override
+    public void endVisit(JMethodCall x, Context ctx) {
+      List<JParameter> params = x.getTarget().params;
+      List<JExpression> args = x.getArgs();
+      for (int i = 0; i < params.size(); ++i) {
+        JParameter param = params.get(i);
+        JExpression arg = args.get(i);
+        JExpression newArg = checkAndReplace(arg, param.getType());
+        if (arg != newArg) {
+          args.set(i, newArg);
+          this.didChange = true;
+        }
+      }
+    }
+
+    @Override
+    public void endVisit(JNewArray x, Context ctx) {
+      JType elementType = x.getArrayType().getElementType();
+      List<JExpression> initializers = x.initializers;
+      if (initializers != null) {
+        for (int i = 0; i < initializers.size(); ++i) {
+          JExpression initializer = initializers.get(i);
+          JExpression newInitializer = checkAndReplace(initializer, elementType);
+          if (initializer != newInitializer) {
+            initializers.set(i, newInitializer);
+            this.didChange = true;
+          }
+        }
+      }
+    }
+
+    @Override
+    public void endVisit(JReturnStatement x, Context ctx) {
+      JExpression expr = x.getExpr();
+      if (expr != null) {
+        JExpression newExpr = checkAndReplace(expr, currentMethod.getType());
+        if (expr != newExpr) {
+          JReturnStatement newStmt = new JReturnStatement(program,
+              x.getSourceInfo(), newExpr);
+          ctx.replaceMe(newStmt);
+        }
+      }
+    }
+
+    @Override
+    public boolean visit(JMethod x, Context ctx) {
+      currentMethod = x;
+      return true;
+    }
+
+    /**
+     * Returns an explicit cast if the target type is long and the input
+     * expression is not a long, or if the target type is floating point and the
+     * expression is a long.
+     */
+    private JExpression checkAndReplace(JExpression arg, JType targetType) {
+      JType argType = arg.getType();
+      if (targetType == argType) {
+        return arg;
+      }
+      if (targetType != longType && argType != longType) {
+        return arg;
+      }
+      // Synthesize a cast to long to force explicit conversion.
+      JCastOperation cast = new JCastOperation(program, arg.getSourceInfo(),
+          targetType, arg);
+      return cast;
+    }
+  }
+
+  public static void exec(JProgram program) {
+    new LongCastNormalizer(program).execImpl();
+  }
+
+  private final JProgram program;
+
+  private LongCastNormalizer(JProgram program) {
+    this.program = program;
+  }
+
+  private void execImpl() {
+    ImplicitCastVisitor visitor = new ImplicitCastVisitor(
+        program.getTypePrimitiveLong());
+    visitor.accept(program);
+  }
+
+}
diff --git a/dev/core/src/com/google/gwt/dev/jjs/impl/LongEmulationNormalizer.java b/dev/core/src/com/google/gwt/dev/jjs/impl/LongEmulationNormalizer.java
index 2b7a8c6..4987620 100644
--- a/dev/core/src/com/google/gwt/dev/jjs/impl/LongEmulationNormalizer.java
+++ b/dev/core/src/com/google/gwt/dev/jjs/impl/LongEmulationNormalizer.java
@@ -1,215 +1,215 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.dev.jjs.impl;

-

-import com.google.gwt.dev.jjs.InternalCompilerException;

-import com.google.gwt.dev.jjs.ast.Context;

-import com.google.gwt.dev.jjs.ast.JBinaryOperation;

-import com.google.gwt.dev.jjs.ast.JBinaryOperator;

-import com.google.gwt.dev.jjs.ast.JMethod;

-import com.google.gwt.dev.jjs.ast.JMethodCall;

-import com.google.gwt.dev.jjs.ast.JModVisitor;

-import com.google.gwt.dev.jjs.ast.JPostfixOperation;

-import com.google.gwt.dev.jjs.ast.JPrefixOperation;

-import com.google.gwt.dev.jjs.ast.JPrimitiveType;

-import com.google.gwt.dev.jjs.ast.JProgram;

-import com.google.gwt.dev.jjs.ast.JType;

-import com.google.gwt.dev.jjs.ast.JUnaryOperator;

-

-/**

- * Replaces long operations with calls to the emulation library. Depends on

- * {@link LongCastNormalizer} and {@link CompoundAssignmentNormalizer} having

- * been run.

- */

-public class LongEmulationNormalizer {

-

-  /**

-   * Replace all long math with calls into the long emulation library.

-   */

-  private class LongOpVisitor extends JModVisitor {

-

-    private final JPrimitiveType longType;

-

-    public LongOpVisitor(JPrimitiveType longType) {

-      this.longType = longType;

-    }

-

-    @Override

-    public void endVisit(JBinaryOperation x, Context ctx) {

-      // Concats are handled by CastNormalizer.ConcatVisitor.

-      if (x.getType() == program.getTypeJavaLangString()) {

-        return;

-      }

-      JType lhsType = x.getLhs().getType();

-      JType rhsType = x.getRhs().getType();

-      if (lhsType != longType) {

-        assert (rhsType != longType);

-        return;

-      }

-

-      String methodName = getEmulationMethod(x.getOp());

-      if (methodName == null) {

-        return;

-      }

-

-      // Check operand types.

-      switch (x.getOp()) {

-        case SHL:

-        case SHR:

-        case SHRU:

-          if (rhsType != program.getTypePrimitiveInt()) {

-            throw new InternalCompilerException(

-                "Expected right operand to be of type int");

-          }

-          break;

-        default:

-          if (rhsType != longType) {

-            throw new InternalCompilerException(

-                "Expected right operand to be of type long");

-          }

-      }

-

-      JMethod method = program.getIndexedMethod("LongLib." + methodName);

-      JMethodCall call = new JMethodCall(program, x.getSourceInfo(), null,

-          method, x.getType());

-      call.getArgs().add(x.getLhs());

-      call.getArgs().add(x.getRhs());

-      ctx.replaceMe(call);

-    }

-

-    @Override

-    public void endVisit(JPostfixOperation x, Context ctx) {

-      JType argType = x.getArg().getType();

-      if (argType == longType) {

-        throw new InternalCompilerException(

-            "Postfix operations on longs should not reach here");

-      }

-    }

-

-    @Override

-    public void endVisit(JPrefixOperation x, Context ctx) {

-      JType argType = x.getArg().getType();

-      if (argType != longType) {

-        return;

-      }

-

-      String methodName = getEmulationMethod(x.getOp());

-      JMethod method = program.getIndexedMethod("LongLib." + methodName);

-      JMethodCall call = new JMethodCall(program, x.getSourceInfo(), null,

-          method, x.getType());

-      call.getArgs().add(x.getArg());

-      ctx.replaceMe(call);

-    }

-

-    private String getEmulationMethod(JBinaryOperator op) {

-      switch (op) {

-        case MUL:

-          return "mul";

-        case DIV:

-          return "div";

-        case MOD:

-          return "mod";

-        case ADD:

-          return "add";

-        case SUB:

-          return "sub";

-        case SHL:

-          return "shl";

-        case SHR:

-          return "shr";

-        case SHRU:

-          return "shru";

-        case LT:

-          return "lt";

-        case LTE:

-          return "lte";

-        case GT:

-          return "gt";

-        case GTE:

-          return "gte";

-        case EQ:

-          return "eq";

-        case NEQ:

-          return "neq";

-        case BIT_AND:

-          return "and";

-        case BIT_XOR:

-          return "xor";

-        case BIT_OR:

-          return "or";

-

-        case AND:

-        case OR:

-          throw new InternalCompilerException(

-              "AND and OR should not have long operands");

-

-        case ASG:

-          // Nothing to do.

-          return null;

-

-        case ASG_ADD:

-        case ASG_SUB:

-        case ASG_MUL:

-        case ASG_DIV:

-        case ASG_MOD:

-        case ASG_SHL:

-        case ASG_SHR:

-        case ASG_SHRU:

-        case ASG_BIT_AND:

-        case ASG_BIT_OR:

-        case ASG_BIT_XOR:

-          throw new InternalCompilerException(

-              "Modifying long ops should not reach here");

-        default:

-          throw new InternalCompilerException("Should not reach here");

-      }

-    }

-

-    private String getEmulationMethod(JUnaryOperator op) {

-      switch (op) {

-        case INC:

-        case DEC:

-          throw new InternalCompilerException(

-              "Modifying long ops should not reach here");

-        case NEG:

-          return "neg";

-        case NOT:

-          throw new InternalCompilerException(

-              "NOT should not have a long operand");

-        case BIT_NOT:

-          return "not";

-        default:

-          throw new InternalCompilerException("Should not reach here");

-      }

-    }

-  }

-

-  public static void exec(JProgram program) {

-    new LongEmulationNormalizer(program).execImpl();

-  }

-

-  private final JProgram program;

-

-  private LongEmulationNormalizer(JProgram program) {

-    this.program = program;

-  }

-

-  private void execImpl() {

-    LongOpVisitor visitor = new LongOpVisitor(program.getTypePrimitiveLong());

-    visitor.accept(program);

-  }

-

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.dev.jjs.impl;
+
+import com.google.gwt.dev.jjs.InternalCompilerException;
+import com.google.gwt.dev.jjs.ast.Context;
+import com.google.gwt.dev.jjs.ast.JBinaryOperation;
+import com.google.gwt.dev.jjs.ast.JBinaryOperator;
+import com.google.gwt.dev.jjs.ast.JMethod;
+import com.google.gwt.dev.jjs.ast.JMethodCall;
+import com.google.gwt.dev.jjs.ast.JModVisitor;
+import com.google.gwt.dev.jjs.ast.JPostfixOperation;
+import com.google.gwt.dev.jjs.ast.JPrefixOperation;
+import com.google.gwt.dev.jjs.ast.JPrimitiveType;
+import com.google.gwt.dev.jjs.ast.JProgram;
+import com.google.gwt.dev.jjs.ast.JType;
+import com.google.gwt.dev.jjs.ast.JUnaryOperator;
+
+/**
+ * Replaces long operations with calls to the emulation library. Depends on
+ * {@link LongCastNormalizer} and {@link CompoundAssignmentNormalizer} having
+ * been run.
+ */
+public class LongEmulationNormalizer {
+
+  /**
+   * Replace all long math with calls into the long emulation library.
+   */
+  private class LongOpVisitor extends JModVisitor {
+
+    private final JPrimitiveType longType;
+
+    public LongOpVisitor(JPrimitiveType longType) {
+      this.longType = longType;
+    }
+
+    @Override
+    public void endVisit(JBinaryOperation x, Context ctx) {
+      // Concats are handled by CastNormalizer.ConcatVisitor.
+      if (x.getType() == program.getTypeJavaLangString()) {
+        return;
+      }
+      JType lhsType = x.getLhs().getType();
+      JType rhsType = x.getRhs().getType();
+      if (lhsType != longType) {
+        assert (rhsType != longType);
+        return;
+      }
+
+      String methodName = getEmulationMethod(x.getOp());
+      if (methodName == null) {
+        return;
+      }
+
+      // Check operand types.
+      switch (x.getOp()) {
+        case SHL:
+        case SHR:
+        case SHRU:
+          if (rhsType != program.getTypePrimitiveInt()) {
+            throw new InternalCompilerException(
+                "Expected right operand to be of type int");
+          }
+          break;
+        default:
+          if (rhsType != longType) {
+            throw new InternalCompilerException(
+                "Expected right operand to be of type long");
+          }
+      }
+
+      JMethod method = program.getIndexedMethod("LongLib." + methodName);
+      JMethodCall call = new JMethodCall(program, x.getSourceInfo(), null,
+          method, x.getType());
+      call.getArgs().add(x.getLhs());
+      call.getArgs().add(x.getRhs());
+      ctx.replaceMe(call);
+    }
+
+    @Override
+    public void endVisit(JPostfixOperation x, Context ctx) {
+      JType argType = x.getArg().getType();
+      if (argType == longType) {
+        throw new InternalCompilerException(
+            "Postfix operations on longs should not reach here");
+      }
+    }
+
+    @Override
+    public void endVisit(JPrefixOperation x, Context ctx) {
+      JType argType = x.getArg().getType();
+      if (argType != longType) {
+        return;
+      }
+
+      String methodName = getEmulationMethod(x.getOp());
+      JMethod method = program.getIndexedMethod("LongLib." + methodName);
+      JMethodCall call = new JMethodCall(program, x.getSourceInfo(), null,
+          method, x.getType());
+      call.getArgs().add(x.getArg());
+      ctx.replaceMe(call);
+    }
+
+    private String getEmulationMethod(JBinaryOperator op) {
+      switch (op) {
+        case MUL:
+          return "mul";
+        case DIV:
+          return "div";
+        case MOD:
+          return "mod";
+        case ADD:
+          return "add";
+        case SUB:
+          return "sub";
+        case SHL:
+          return "shl";
+        case SHR:
+          return "shr";
+        case SHRU:
+          return "shru";
+        case LT:
+          return "lt";
+        case LTE:
+          return "lte";
+        case GT:
+          return "gt";
+        case GTE:
+          return "gte";
+        case EQ:
+          return "eq";
+        case NEQ:
+          return "neq";
+        case BIT_AND:
+          return "and";
+        case BIT_XOR:
+          return "xor";
+        case BIT_OR:
+          return "or";
+
+        case AND:
+        case OR:
+          throw new InternalCompilerException(
+              "AND and OR should not have long operands");
+
+        case ASG:
+          // Nothing to do.
+          return null;
+
+        case ASG_ADD:
+        case ASG_SUB:
+        case ASG_MUL:
+        case ASG_DIV:
+        case ASG_MOD:
+        case ASG_SHL:
+        case ASG_SHR:
+        case ASG_SHRU:
+        case ASG_BIT_AND:
+        case ASG_BIT_OR:
+        case ASG_BIT_XOR:
+          throw new InternalCompilerException(
+              "Modifying long ops should not reach here");
+        default:
+          throw new InternalCompilerException("Should not reach here");
+      }
+    }
+
+    private String getEmulationMethod(JUnaryOperator op) {
+      switch (op) {
+        case INC:
+        case DEC:
+          throw new InternalCompilerException(
+              "Modifying long ops should not reach here");
+        case NEG:
+          return "neg";
+        case NOT:
+          throw new InternalCompilerException(
+              "NOT should not have a long operand");
+        case BIT_NOT:
+          return "not";
+        default:
+          throw new InternalCompilerException("Should not reach here");
+      }
+    }
+  }
+
+  public static void exec(JProgram program) {
+    new LongEmulationNormalizer(program).execImpl();
+  }
+
+  private final JProgram program;
+
+  private LongEmulationNormalizer(JProgram program) {
+    this.program = program;
+  }
+
+  private void execImpl() {
+    LongOpVisitor visitor = new LongOpVisitor(program.getTypePrimitiveLong());
+    visitor.accept(program);
+  }
+
+}
diff --git a/dev/core/src/com/google/gwt/dev/shell/JavaLong.java b/dev/core/src/com/google/gwt/dev/shell/JavaLong.java
index 3217f4f..649c38c 100644
--- a/dev/core/src/com/google/gwt/dev/shell/JavaLong.java
+++ b/dev/core/src/com/google/gwt/dev/shell/JavaLong.java
@@ -1,38 +1,38 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.dev.shell;

-

-/**

- * Hosted mode wrapper for a Java long value.

- */

-public class JavaLong {

-

-  private final long longVal;

-

-  public JavaLong(long longVal) {

-    this.longVal = longVal;

-  }

-

-  public long longValue() {

-    return longVal;

-  }

-

-  @Override

-  public String toString() {

-    return "Java long value: " + longVal;

-  }

-

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.dev.shell;
+
+/**
+ * Hosted mode wrapper for a Java long value.
+ */
+public class JavaLong {
+
+  private final long longVal;
+
+  public JavaLong(long longVal) {
+    this.longVal = longVal;
+  }
+
+  public long longValue() {
+    return longVal;
+  }
+
+  @Override
+  public String toString() {
+    return "Java long value: " + longVal;
+  }
+
+}
diff --git a/dev/core/test/com/google/gwt/lang/LongLibJreTest.java b/dev/core/test/com/google/gwt/lang/LongLibJreTest.java
index 3b2a76c..d8b5c85 100644
--- a/dev/core/test/com/google/gwt/lang/LongLibJreTest.java
+++ b/dev/core/test/com/google/gwt/lang/LongLibJreTest.java
@@ -1,86 +1,86 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.lang;

-

-import junit.framework.TestCase;

-

-/**

- * Test the LongLib class as a GWTTestCase.

- */

-public class LongLibJreTest extends TestCase {

-

-  static {

-    LongLib.RUN_IN_JVM = true;

-  }

-

-  private LongLibTestBase impl = new LongLibTestBase();

-

-  public void testAAAA() {

-    assertEquals(1.4e-45f, 1.401298464324817E-45, 0.0);

-  }

-  

-  public void testAdditive() {

-    impl.testAdditive();

-  }

-

-  public void testBitOps() {

-    impl.testBitOps();

-  }

-

-  public void testComparisons() {

-    impl.testComparisons();

-  }

-

-  public void testConversions() {

-    impl.testConversions();

-  }

-

-  public void testDiv() {

-    impl.testDiv();

-  }

-

-  public void testFactorial() {

-    impl.testFactorial();

-  }

-

-  public void testFromDouble() {

-    impl.testFromDouble();

-  }

-

-  public void testMinMax() {

-    impl.testMinMax();

-  }

-

-  public void testMultiplicative() {

-    impl.testMultiplicative();

-  }

-

-  public void testNegate() {

-    impl.testNegate();

-  }

-

-  public void testShift() {

-    impl.testShift();

-  }

-

-  public void testToHexString() {

-    impl.testToHexString();

-  }

-

-  public void testToString() {

-    impl.testToString();

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.lang;
+
+import junit.framework.TestCase;
+
+/**
+ * Test the LongLib class as a GWTTestCase.
+ */
+public class LongLibJreTest extends TestCase {
+
+  static {
+    LongLib.RUN_IN_JVM = true;
+  }
+
+  private LongLibTestBase impl = new LongLibTestBase();
+
+  public void testAAAA() {
+    assertEquals(1.4e-45f, 1.401298464324817E-45, 0.0);
+  }
+  
+  public void testAdditive() {
+    impl.testAdditive();
+  }
+
+  public void testBitOps() {
+    impl.testBitOps();
+  }
+
+  public void testComparisons() {
+    impl.testComparisons();
+  }
+
+  public void testConversions() {
+    impl.testConversions();
+  }
+
+  public void testDiv() {
+    impl.testDiv();
+  }
+
+  public void testFactorial() {
+    impl.testFactorial();
+  }
+
+  public void testFromDouble() {
+    impl.testFromDouble();
+  }
+
+  public void testMinMax() {
+    impl.testMinMax();
+  }
+
+  public void testMultiplicative() {
+    impl.testMultiplicative();
+  }
+
+  public void testNegate() {
+    impl.testNegate();
+  }
+
+  public void testShift() {
+    impl.testShift();
+  }
+
+  public void testToHexString() {
+    impl.testToHexString();
+  }
+
+  public void testToString() {
+    impl.testToString();
+  }
+}
diff --git a/dev/core/test/com/google/gwt/lang/LongLibTestBase.java b/dev/core/test/com/google/gwt/lang/LongLibTestBase.java
index 618df5a..2766669 100644
--- a/dev/core/test/com/google/gwt/lang/LongLibTestBase.java
+++ b/dev/core/test/com/google/gwt/lang/LongLibTestBase.java
@@ -1,353 +1,353 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.lang;

-

-import com.google.gwt.lang.LongLib.Const;

-

-import junit.framework.TestCase;

-

-/**

- * Test the LongLib class. The magic expected values were computed by using a

- * Java println on normal Java longs.

- */

-public class LongLibTestBase extends TestCase {

-

-  static void assertEquals(double[] expected, double[] actual) {

-    assertTrue("expected=" + LongLib.toString(expected) + "  actual="

-        + LongLib.toString(actual), LongLib.eq(expected, actual));

-  }

-

-  public void testAdditive() {

-    {

-      final double[] n1 = LongLib.fromInt(1234);

-      final double[] n2 = LongLib.fromInt(9876);

-      assertEquals(LongLib.fromInt(11110), LongLib.add(n1, n2));

-      assertEquals(LongLib.fromInt(-8642), LongLib.sub(n1, n2));

-    }

-

-    {

-      final double[] n1 = LongLib.fromInt(-1234);

-      final double[] n2 = LongLib.fromInt(9876);

-      assertEquals(LongLib.fromInt(8642), LongLib.add(n1, n2));

-      assertEquals(LongLib.fromInt(-11110), LongLib.sub(n1, n2));

-    }

-

-    {

-      final double[] n1 = LongLib.fromInt(-1234);

-      final double[] n2 = LongLib.fromInt(-9876);

-      assertEquals(LongLib.fromInt(-11110), LongLib.add(n1, n2));

-      assertEquals(LongLib.fromInt(8642), LongLib.sub(n1, n2));

-    }

-

-    {

-      final double[] n1 = longFromBits(0x12345678, 0xabcdabcd);

-      final double[] n2 = longFromBits(0x77773333, 0x22224444);

-      assertEquals(longFromBits(0x89ab89ab, 0xcdeff011), LongLib.add(n1, n2));

-      assertEquals(longFromBits(0x9abd2345, 0x89ab6789), LongLib.sub(n1, n2));

-    }

-  }

-

-  public void testBitOps() {

-    {

-      final double[] n1 = LongLib.fromInt(1234);

-      final double[] n2 = LongLib.fromInt(9876);

-

-      assertEquals(LongLib.fromInt(1168), LongLib.and(n1, n2));

-      assertEquals(LongLib.fromInt(9942), LongLib.or(n1, n2));

-      assertEquals(LongLib.fromInt(8774), LongLib.xor(n1, n2));

-      assertEquals(LongLib.fromInt(-1235), LongLib.not(n1));

-      assertEquals(LongLib.fromInt(-9877), LongLib.not(n2));

-    }

-

-    {

-      final double[] n1 = LongLib.fromInt(-1234);

-      final double[] n2 = LongLib.fromInt(9876);

-      assertEquals(LongLib.fromInt(8708), LongLib.and(n1, n2));

-      assertEquals(LongLib.fromInt(-66), LongLib.or(n1, n2));

-      assertEquals(LongLib.fromInt(-8774), LongLib.xor(n1, n2));

-      assertEquals(LongLib.fromInt(1233), LongLib.not(n1));

-      assertEquals(LongLib.fromInt(-9877), LongLib.not(n2));

-    }

-

-    {

-      final double[] n1 = LongLib.shl(LongLib.fromInt(0x1234), 32);

-      final double[] n2 = LongLib.shl(LongLib.fromInt(0x9876), 32);

-      assertEquals(LongLib.shl(LongLib.fromInt(0x1034), 32),

-          LongLib.and(n1, n2));

-      assertEquals(LongLib.shl(LongLib.fromInt(0x9a76), 32), LongLib.or(n1, n2));

-      assertEquals(LongLib.shl(LongLib.fromInt(0x8a42), 32),

-          LongLib.xor(n1, n2));

-      assertEquals(longFromBits(0xffffedcb, 0xffffffff), LongLib.not(n1));

-      assertEquals(longFromBits(0xffff6789, 0xffffffff), LongLib.not(n2));

-    }

-  }

-

-  public void testComparisons() {

-    assertTrue(LongLib.lt(LongLib.fromInt(10), LongLib.fromInt(11)));

-    assertTrue(LongLib.lte(LongLib.fromInt(10), LongLib.fromInt(11)));

-    assertTrue(!LongLib.eq(LongLib.fromInt(10), LongLib.fromInt(11)));

-    assertTrue(!LongLib.gte(LongLib.fromInt(10), LongLib.fromInt(11)));

-    assertTrue(!LongLib.gt(LongLib.fromInt(10), LongLib.fromInt(11)));

-

-    assertTrue(!LongLib.lt(LongLib.fromInt(10), LongLib.fromInt(10)));

-    assertTrue(LongLib.lte(LongLib.fromInt(10), LongLib.fromInt(10)));

-    assertTrue(LongLib.eq(LongLib.fromInt(10), LongLib.fromInt(10)));

-    assertTrue(LongLib.gte(LongLib.fromInt(10), LongLib.fromInt(10)));

-    assertTrue(!LongLib.gt(LongLib.fromInt(10), LongLib.fromInt(10)));

-

-    assertTrue(!LongLib.lt(LongLib.fromInt(12), LongLib.fromInt(11)));

-    assertTrue(!LongLib.lte(LongLib.fromInt(12), LongLib.fromInt(11)));

-    assertTrue(!LongLib.eq(LongLib.fromInt(12), LongLib.fromInt(11)));

-    assertTrue(LongLib.gte(LongLib.fromInt(12), LongLib.fromInt(11)));

-    assertTrue(LongLib.gt(LongLib.fromInt(12), LongLib.fromInt(11)));

-

-    // the following three comparisons cannot be implemented by

-    // subtracting the arguments, because the subtraction causes an overflow

-    final double[] largeNeg = longFromBits(0x82341234, 0x0);

-    final double[] largePos = longFromBits(0x12341234, 0x0);

-    assertTrue(LongLib.lt(largeNeg, largePos));

-

-    assertTrue(LongLib.lt(Const.MIN_VALUE, LongLib.fromInt(0)));

-    assertTrue(LongLib.gt(LongLib.fromInt(0), Const.MIN_VALUE));

-

-    final double[] largePosPlusOne = LongLib.add(largePos, LongLib.fromInt(1));

-

-    assertTrue(LongLib.lt(largePos, largePosPlusOne));

-    assertTrue(LongLib.lte(largePos, largePosPlusOne));

-    assertTrue(!LongLib.eq(largePos, largePosPlusOne));

-    assertTrue(!LongLib.gte(largePos, largePosPlusOne));

-    assertTrue(!LongLib.gt(largePos, largePosPlusOne));

-

-    assertTrue(!LongLib.lt(largePos, largePos));

-    assertTrue(LongLib.lte(largePos, largePos));

-    assertTrue(LongLib.eq(largePos, largePos));

-    assertTrue(LongLib.gte(largePos, largePos));

-    assertTrue(!LongLib.gt(largePos, largePos));

-

-    assertTrue(!LongLib.lt(largePosPlusOne, largePos));

-    assertTrue(!LongLib.lte(largePosPlusOne, largePos));

-    assertTrue(!LongLib.eq(largePosPlusOne, largePos));

-    assertTrue(LongLib.gte(largePosPlusOne, largePos));

-    assertTrue(LongLib.gt(largePosPlusOne, largePos));

-  }

-

-  public void testConversions() {

-    assertEquals(10, LongLib.toInt(longFromBits(0, 10)));

-    assertEquals(-10, LongLib.toInt(longFromBits(0, -10)));

-    assertEquals(-10, LongLib.toInt(longFromBits(100, -10)));

-    assertEquals(-10, LongLib.toInt(longFromBits(-100000, -10)));

-  }

-

-  public void testDiv() {

-    double[] deadBeef = LongLib.typeChange(0xdeadbeefdeadbeefL);

-    double[] ten = LongLib.fromInt(10);

-    assertEquals(LongLib.typeChange(-240105308887621659L), LongLib.div(

-        deadBeef, ten));

-    assertEquals(Const.ZERO, LongLib.div(Const.ONE, Const.TWO));

-    assertEquals(LongLib.typeChange(4611686018427387903L), LongLib.div(

-        Const.MAX_VALUE, Const.TWO));

-  }

-

-  public void testFactorial() {

-    double[] fact18 = fact(LongLib.fromInt(18));

-    double[] fact17 = fact(LongLib.fromInt(17));

-    assertEquals(LongLib.fromInt(18), LongLib.div(fact18, fact17));

-  }

-

-  public void testFromDouble() {

-    // these tests are based on JLS3, section 5.1.3

-

-    assertEquals(LongLib.fromInt(10), LongLib.fromDouble(10.5));

-    assertEquals(LongLib.fromInt(-10), LongLib.fromDouble(-10.5));

-    assertEquals(LongLib.shl(LongLib.fromInt(1), 55),

-        LongLib.fromDouble(Math.pow(2.0, 55) + 0.5));

-    assertEquals(LongLib.neg(LongLib.shl(LongLib.fromInt(1), 55)),

-        LongLib.fromDouble(-Math.pow(2.0, 55) - 0.5));

-

-    assertEquals(LongLib.fromInt(0), LongLib.fromDouble(Double.NaN));

-

-    assertEquals(Const.MAX_VALUE, LongLib.fromDouble(Math.pow(2.0, 100)));

-    assertEquals(Const.MAX_VALUE, LongLib.fromDouble(Double.POSITIVE_INFINITY));

-    assertEquals(Const.MIN_VALUE, LongLib.fromDouble(-Math.pow(2.0, 100)));

-    assertEquals(Const.MIN_VALUE, LongLib.fromDouble(Double.NEGATIVE_INFINITY));

-  }

-

-  public void testMinMax() {

-    assertEquals(Const.MIN_VALUE, LongLib.shl(LongLib.fromInt(1), 63));

-    assertEquals(Const.MAX_VALUE, LongLib.neg(LongLib.add(Const.MIN_VALUE,

-        LongLib.fromInt(1))));

-  }

-

-  public void testMultiplicative() {

-    assertEquals(LongLib.fromInt(3333), LongLib.mul(LongLib.fromInt(1111),

-        LongLib.fromInt(3)));

-    assertEquals(LongLib.fromInt(-3333), LongLib.mul(LongLib.fromInt(1111),

-        LongLib.fromInt(-3)));

-    assertEquals(LongLib.fromInt(-3333), LongLib.mul(LongLib.fromInt(-1111),

-        LongLib.fromInt(3)));

-    assertEquals(LongLib.fromInt(3333), LongLib.mul(LongLib.fromInt(-1111),

-        LongLib.fromInt(-3)));

-    assertEquals(LongLib.fromInt(0), LongLib.mul(LongLib.fromInt(100),

-        LongLib.fromInt(0)));

-

-    assertEquals(longFromBits(0x7ff63f7c, 0x1df4d840), LongLib.mul(

-        longFromBits(0x12345678, 0x12345678), longFromBits(0x1234, 0x12345678)));

-    assertEquals(longFromBits(0x7ff63f7c, 0x1df4d840), LongLib.mul(

-        longFromBits(0xf2345678, 0x12345678), longFromBits(0x1234, 0x12345678)));

-    assertEquals(longFromBits(0x297e3f7c, 0x1df4d840), LongLib.mul(

-        longFromBits(0xf2345678, 0x12345678), longFromBits(0xffff1234,

-            0x12345678)));

-

-    assertEquals(LongLib.fromInt(0), LongLib.mul(Const.MIN_VALUE,

-        LongLib.fromInt(2)));

-    assertEquals(Const.MIN_VALUE, LongLib.mul(Const.MIN_VALUE,

-        LongLib.fromInt(1)));

-    assertEquals(Const.MIN_VALUE, LongLib.mul(Const.MIN_VALUE,

-        LongLib.fromInt(-1)));

-

-    assertEquals(LongLib.fromInt(1), LongLib.div(LongLib.fromInt(5),

-        LongLib.fromInt(5)));

-    assertEquals(LongLib.fromInt(333), LongLib.div(LongLib.fromInt(1000),

-        LongLib.fromInt(3)));

-    assertEquals(LongLib.fromInt(-333), LongLib.div(LongLib.fromInt(1000),

-        LongLib.fromInt(-3)));

-    assertEquals(LongLib.fromInt(-333), LongLib.div(LongLib.fromInt(-1000),

-        LongLib.fromInt(3)));

-    assertEquals(LongLib.fromInt(333), LongLib.div(LongLib.fromInt(-1000),

-        LongLib.fromInt(-3)));

-    assertEquals(LongLib.fromInt(0), LongLib.div(LongLib.fromInt(3),

-        LongLib.fromInt(1000)));

-    assertEquals(longFromBits(0x1003d0, 0xe84f5ae8), LongLib.div(longFromBits(

-        0x12345678, 0x12345678), longFromBits(0x0, 0x123)));

-    assertEquals(longFromBits(0x0, 0x10003), LongLib.div(longFromBits(

-        0x12345678, 0x12345678), longFromBits(0x1234, 0x12345678)));

-    assertEquals(longFromBits(0xffffffff, 0xffff3dfe), LongLib.div(

-        longFromBits(0xf2345678, 0x12345678), longFromBits(0x1234, 0x12345678)));

-    assertEquals(longFromBits(0x0, 0xeda), LongLib.div(longFromBits(0xf2345678,

-        0x12345678), longFromBits(0xffff1234, 0x12345678)));

-

-    try {

-      LongLib.div(LongLib.fromInt(1), LongLib.fromInt(0));

-      fail("Expected an ArithmeticException");

-    } catch (ArithmeticException e) {

-    }

-

-    assertEquals(longFromBits(0xc0000000, 0x00000000), LongLib.div(

-        Const.MIN_VALUE, LongLib.fromInt(2)));

-    assertEquals(Const.MIN_VALUE, LongLib.div(Const.MIN_VALUE,

-        LongLib.fromInt(1)));

-    assertEquals(Const.MIN_VALUE, LongLib.div(Const.MIN_VALUE,

-        LongLib.fromInt(-1))); // JLS3 section 15.17.2

-  }

-

-  public void testNegate() {

-    assertEquals(LongLib.fromInt(-1), LongLib.neg(LongLib.fromInt(1)));

-    assertEquals(LongLib.fromInt(1), LongLib.neg(LongLib.fromInt(-1)));

-

-    // JLS3 15.15.4

-    assertEquals(Const.MIN_VALUE, LongLib.neg(Const.MIN_VALUE));

-  }

-

-  public void testShift() {

-    assertEquals(longFromBits(0xd048d115, 0x9d159c00), LongLib.shl(

-        longFromBits(0x12341234, 0x45674567), 10));

-    assertEquals(longFromBits(0x48d04, 0x8d1159d1), LongLib.shr(longFromBits(

-        0x12341234, 0x45674567), 10));

-    assertEquals(longFromBits(0x48d04, 0x8d1159d1), LongLib.shru(longFromBits(

-        0x12341234, 0x45674567), 10));

-    assertEquals(longFromBits(0xd048d115, 0x9d159c00), LongLib.shl(

-        longFromBits(0x92341234, 0x45674567), 10));

-    assertEquals(longFromBits(0xffe48d04, 0x8d1159d1), LongLib.shr(

-        longFromBits(0x92341234, 0x45674567), 10));

-    assertEquals(longFromBits(0x248d04, 0x8d1159d1), LongLib.shru(longFromBits(

-        0x92341234, 0x45674567), 10));

-

-    assertEquals(LongLib.fromInt(-1), LongLib.shr(LongLib.fromInt(-1), 10));

-

-    assertEquals(LongLib.fromInt(-1 << 5), LongLib.shl(LongLib.fromInt(-1), 5));

-    assertEquals(LongLib.fromInt(-1), LongLib.shl(LongLib.fromInt(-1), 0));

-    assertEquals(LongLib.neg(LongLib.typeChange(0x4000000000000000L)),

-        LongLib.shr(LongLib.shl(LongLib.fromInt(1), 63), 1));

-    assertEquals(LongLib.fromInt(0), LongLib.shl(LongLib.shl(

-        LongLib.fromInt(-1), 32), 32));

-    assertEquals(Const.MIN_VALUE, LongLib.shl(Const.MIN_VALUE, 0));

-    assertEquals(LongLib.fromInt(0), LongLib.shl(Const.MIN_VALUE, 1));

-    assertEquals(longFromBits(0xfffffffc, 0x00000000), LongLib.shr(

-        LongLib.neg(longFromBits(8, 0)), 1));

-    assertEquals(longFromBits(0x7ffffffc, 0x0), LongLib.shru(

-        LongLib.neg(longFromBits(8, 0)), 1));

-  }

-

-  // Issue 1198, and also a good exercise of several methods.

-  public void testToHexString() {

-    double[] deadbeaf12341234 = longFromBits(0xdeadbeaf, 0x12341234);

-

-    assertEquals("deadbeaf12341234", toHexString(deadbeaf12341234));

-  }

-

-  public void testToString() {

-    assertEquals("0", LongLib.toString(LongLib.fromInt(0)));

-    assertEquals("1", LongLib.toString(LongLib.fromInt(1)));

-    assertEquals("-1", LongLib.toString(LongLib.fromInt(-1)));

-    assertEquals("-10", LongLib.toString(LongLib.fromInt(-10)));

-    assertEquals("-9223372036854775808", LongLib.toString(Const.MIN_VALUE));

-

-    int top = 922337201;

-    int bottom = 967490662;

-    double[] fullnum = LongLib.add(LongLib.mul(LongLib.fromInt(1000000000),

-        LongLib.fromInt(top)), LongLib.fromInt(bottom));

-

-    assertEquals("922337201967490662", LongLib.toString(fullnum));

-    assertEquals("-922337201967490662", LongLib.toString(LongLib.neg(fullnum)));

-  }

-

-  private double[] fact(double[] n) {

-    if (LongLib.eq(n, LongLib.fromInt(0))) {

-      return LongLib.fromInt(1);

-    } else {

-      return LongLib.mul(n, fact(LongLib.sub(n, LongLib.fromInt(1))));

-    }

-  }

-

-  private double[] longFromBits(int top, int bottom) {

-    double[] topHalf = LongLib.shl(LongLib.fromInt(top), 32);

-    double[] bottomHalf = LongLib.fromInt(bottom);

-    if (LongLib.lt(bottomHalf, Const.ZERO)) {

-      bottomHalf = LongLib.add(bottomHalf, LongLib.shl(LongLib.fromInt(1), 32));

-    }

-    double[] total = LongLib.add(topHalf, bottomHalf);

-    return total;

-  }

-

-  private String toHexString(double[] x) {

-    // copied from the GWT Long class and modified for double[]

-    double[] zero = LongLib.fromInt(0);

-

-    if (LongLib.eq(x, zero)) {

-      return "0";

-    }

-    String[] hexDigits = new String[] {

-        "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "a", "b", "c", "d",

-        "e", "f"};

-    String hexStr = "";

-    while (!LongLib.eq(x, zero)) {

-      int nibble = LongLib.toInt(x) & 0xF;

-      hexStr = hexDigits[nibble] + hexStr;

-      x = LongLib.shru(x, 4);

-    }

-    return hexStr;

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.lang;
+
+import com.google.gwt.lang.LongLib.Const;
+
+import junit.framework.TestCase;
+
+/**
+ * Test the LongLib class. The magic expected values were computed by using a
+ * Java println on normal Java longs.
+ */
+public class LongLibTestBase extends TestCase {
+
+  static void assertEquals(double[] expected, double[] actual) {
+    assertTrue("expected=" + LongLib.toString(expected) + "  actual="
+        + LongLib.toString(actual), LongLib.eq(expected, actual));
+  }
+
+  public void testAdditive() {
+    {
+      final double[] n1 = LongLib.fromInt(1234);
+      final double[] n2 = LongLib.fromInt(9876);
+      assertEquals(LongLib.fromInt(11110), LongLib.add(n1, n2));
+      assertEquals(LongLib.fromInt(-8642), LongLib.sub(n1, n2));
+    }
+
+    {
+      final double[] n1 = LongLib.fromInt(-1234);
+      final double[] n2 = LongLib.fromInt(9876);
+      assertEquals(LongLib.fromInt(8642), LongLib.add(n1, n2));
+      assertEquals(LongLib.fromInt(-11110), LongLib.sub(n1, n2));
+    }
+
+    {
+      final double[] n1 = LongLib.fromInt(-1234);
+      final double[] n2 = LongLib.fromInt(-9876);
+      assertEquals(LongLib.fromInt(-11110), LongLib.add(n1, n2));
+      assertEquals(LongLib.fromInt(8642), LongLib.sub(n1, n2));
+    }
+
+    {
+      final double[] n1 = longFromBits(0x12345678, 0xabcdabcd);
+      final double[] n2 = longFromBits(0x77773333, 0x22224444);
+      assertEquals(longFromBits(0x89ab89ab, 0xcdeff011), LongLib.add(n1, n2));
+      assertEquals(longFromBits(0x9abd2345, 0x89ab6789), LongLib.sub(n1, n2));
+    }
+  }
+
+  public void testBitOps() {
+    {
+      final double[] n1 = LongLib.fromInt(1234);
+      final double[] n2 = LongLib.fromInt(9876);
+
+      assertEquals(LongLib.fromInt(1168), LongLib.and(n1, n2));
+      assertEquals(LongLib.fromInt(9942), LongLib.or(n1, n2));
+      assertEquals(LongLib.fromInt(8774), LongLib.xor(n1, n2));
+      assertEquals(LongLib.fromInt(-1235), LongLib.not(n1));
+      assertEquals(LongLib.fromInt(-9877), LongLib.not(n2));
+    }
+
+    {
+      final double[] n1 = LongLib.fromInt(-1234);
+      final double[] n2 = LongLib.fromInt(9876);
+      assertEquals(LongLib.fromInt(8708), LongLib.and(n1, n2));
+      assertEquals(LongLib.fromInt(-66), LongLib.or(n1, n2));
+      assertEquals(LongLib.fromInt(-8774), LongLib.xor(n1, n2));
+      assertEquals(LongLib.fromInt(1233), LongLib.not(n1));
+      assertEquals(LongLib.fromInt(-9877), LongLib.not(n2));
+    }
+
+    {
+      final double[] n1 = LongLib.shl(LongLib.fromInt(0x1234), 32);
+      final double[] n2 = LongLib.shl(LongLib.fromInt(0x9876), 32);
+      assertEquals(LongLib.shl(LongLib.fromInt(0x1034), 32),
+          LongLib.and(n1, n2));
+      assertEquals(LongLib.shl(LongLib.fromInt(0x9a76), 32), LongLib.or(n1, n2));
+      assertEquals(LongLib.shl(LongLib.fromInt(0x8a42), 32),
+          LongLib.xor(n1, n2));
+      assertEquals(longFromBits(0xffffedcb, 0xffffffff), LongLib.not(n1));
+      assertEquals(longFromBits(0xffff6789, 0xffffffff), LongLib.not(n2));
+    }
+  }
+
+  public void testComparisons() {
+    assertTrue(LongLib.lt(LongLib.fromInt(10), LongLib.fromInt(11)));
+    assertTrue(LongLib.lte(LongLib.fromInt(10), LongLib.fromInt(11)));
+    assertTrue(!LongLib.eq(LongLib.fromInt(10), LongLib.fromInt(11)));
+    assertTrue(!LongLib.gte(LongLib.fromInt(10), LongLib.fromInt(11)));
+    assertTrue(!LongLib.gt(LongLib.fromInt(10), LongLib.fromInt(11)));
+
+    assertTrue(!LongLib.lt(LongLib.fromInt(10), LongLib.fromInt(10)));
+    assertTrue(LongLib.lte(LongLib.fromInt(10), LongLib.fromInt(10)));
+    assertTrue(LongLib.eq(LongLib.fromInt(10), LongLib.fromInt(10)));
+    assertTrue(LongLib.gte(LongLib.fromInt(10), LongLib.fromInt(10)));
+    assertTrue(!LongLib.gt(LongLib.fromInt(10), LongLib.fromInt(10)));
+
+    assertTrue(!LongLib.lt(LongLib.fromInt(12), LongLib.fromInt(11)));
+    assertTrue(!LongLib.lte(LongLib.fromInt(12), LongLib.fromInt(11)));
+    assertTrue(!LongLib.eq(LongLib.fromInt(12), LongLib.fromInt(11)));
+    assertTrue(LongLib.gte(LongLib.fromInt(12), LongLib.fromInt(11)));
+    assertTrue(LongLib.gt(LongLib.fromInt(12), LongLib.fromInt(11)));
+
+    // the following three comparisons cannot be implemented by
+    // subtracting the arguments, because the subtraction causes an overflow
+    final double[] largeNeg = longFromBits(0x82341234, 0x0);
+    final double[] largePos = longFromBits(0x12341234, 0x0);
+    assertTrue(LongLib.lt(largeNeg, largePos));
+
+    assertTrue(LongLib.lt(Const.MIN_VALUE, LongLib.fromInt(0)));
+    assertTrue(LongLib.gt(LongLib.fromInt(0), Const.MIN_VALUE));
+
+    final double[] largePosPlusOne = LongLib.add(largePos, LongLib.fromInt(1));
+
+    assertTrue(LongLib.lt(largePos, largePosPlusOne));
+    assertTrue(LongLib.lte(largePos, largePosPlusOne));
+    assertTrue(!LongLib.eq(largePos, largePosPlusOne));
+    assertTrue(!LongLib.gte(largePos, largePosPlusOne));
+    assertTrue(!LongLib.gt(largePos, largePosPlusOne));
+
+    assertTrue(!LongLib.lt(largePos, largePos));
+    assertTrue(LongLib.lte(largePos, largePos));
+    assertTrue(LongLib.eq(largePos, largePos));
+    assertTrue(LongLib.gte(largePos, largePos));
+    assertTrue(!LongLib.gt(largePos, largePos));
+
+    assertTrue(!LongLib.lt(largePosPlusOne, largePos));
+    assertTrue(!LongLib.lte(largePosPlusOne, largePos));
+    assertTrue(!LongLib.eq(largePosPlusOne, largePos));
+    assertTrue(LongLib.gte(largePosPlusOne, largePos));
+    assertTrue(LongLib.gt(largePosPlusOne, largePos));
+  }
+
+  public void testConversions() {
+    assertEquals(10, LongLib.toInt(longFromBits(0, 10)));
+    assertEquals(-10, LongLib.toInt(longFromBits(0, -10)));
+    assertEquals(-10, LongLib.toInt(longFromBits(100, -10)));
+    assertEquals(-10, LongLib.toInt(longFromBits(-100000, -10)));
+  }
+
+  public void testDiv() {
+    double[] deadBeef = LongLib.typeChange(0xdeadbeefdeadbeefL);
+    double[] ten = LongLib.fromInt(10);
+    assertEquals(LongLib.typeChange(-240105308887621659L), LongLib.div(
+        deadBeef, ten));
+    assertEquals(Const.ZERO, LongLib.div(Const.ONE, Const.TWO));
+    assertEquals(LongLib.typeChange(4611686018427387903L), LongLib.div(
+        Const.MAX_VALUE, Const.TWO));
+  }
+
+  public void testFactorial() {
+    double[] fact18 = fact(LongLib.fromInt(18));
+    double[] fact17 = fact(LongLib.fromInt(17));
+    assertEquals(LongLib.fromInt(18), LongLib.div(fact18, fact17));
+  }
+
+  public void testFromDouble() {
+    // these tests are based on JLS3, section 5.1.3
+
+    assertEquals(LongLib.fromInt(10), LongLib.fromDouble(10.5));
+    assertEquals(LongLib.fromInt(-10), LongLib.fromDouble(-10.5));
+    assertEquals(LongLib.shl(LongLib.fromInt(1), 55),
+        LongLib.fromDouble(Math.pow(2.0, 55) + 0.5));
+    assertEquals(LongLib.neg(LongLib.shl(LongLib.fromInt(1), 55)),
+        LongLib.fromDouble(-Math.pow(2.0, 55) - 0.5));
+
+    assertEquals(LongLib.fromInt(0), LongLib.fromDouble(Double.NaN));
+
+    assertEquals(Const.MAX_VALUE, LongLib.fromDouble(Math.pow(2.0, 100)));
+    assertEquals(Const.MAX_VALUE, LongLib.fromDouble(Double.POSITIVE_INFINITY));
+    assertEquals(Const.MIN_VALUE, LongLib.fromDouble(-Math.pow(2.0, 100)));
+    assertEquals(Const.MIN_VALUE, LongLib.fromDouble(Double.NEGATIVE_INFINITY));
+  }
+
+  public void testMinMax() {
+    assertEquals(Const.MIN_VALUE, LongLib.shl(LongLib.fromInt(1), 63));
+    assertEquals(Const.MAX_VALUE, LongLib.neg(LongLib.add(Const.MIN_VALUE,
+        LongLib.fromInt(1))));
+  }
+
+  public void testMultiplicative() {
+    assertEquals(LongLib.fromInt(3333), LongLib.mul(LongLib.fromInt(1111),
+        LongLib.fromInt(3)));
+    assertEquals(LongLib.fromInt(-3333), LongLib.mul(LongLib.fromInt(1111),
+        LongLib.fromInt(-3)));
+    assertEquals(LongLib.fromInt(-3333), LongLib.mul(LongLib.fromInt(-1111),
+        LongLib.fromInt(3)));
+    assertEquals(LongLib.fromInt(3333), LongLib.mul(LongLib.fromInt(-1111),
+        LongLib.fromInt(-3)));
+    assertEquals(LongLib.fromInt(0), LongLib.mul(LongLib.fromInt(100),
+        LongLib.fromInt(0)));
+
+    assertEquals(longFromBits(0x7ff63f7c, 0x1df4d840), LongLib.mul(
+        longFromBits(0x12345678, 0x12345678), longFromBits(0x1234, 0x12345678)));
+    assertEquals(longFromBits(0x7ff63f7c, 0x1df4d840), LongLib.mul(
+        longFromBits(0xf2345678, 0x12345678), longFromBits(0x1234, 0x12345678)));
+    assertEquals(longFromBits(0x297e3f7c, 0x1df4d840), LongLib.mul(
+        longFromBits(0xf2345678, 0x12345678), longFromBits(0xffff1234,
+            0x12345678)));
+
+    assertEquals(LongLib.fromInt(0), LongLib.mul(Const.MIN_VALUE,
+        LongLib.fromInt(2)));
+    assertEquals(Const.MIN_VALUE, LongLib.mul(Const.MIN_VALUE,
+        LongLib.fromInt(1)));
+    assertEquals(Const.MIN_VALUE, LongLib.mul(Const.MIN_VALUE,
+        LongLib.fromInt(-1)));
+
+    assertEquals(LongLib.fromInt(1), LongLib.div(LongLib.fromInt(5),
+        LongLib.fromInt(5)));
+    assertEquals(LongLib.fromInt(333), LongLib.div(LongLib.fromInt(1000),
+        LongLib.fromInt(3)));
+    assertEquals(LongLib.fromInt(-333), LongLib.div(LongLib.fromInt(1000),
+        LongLib.fromInt(-3)));
+    assertEquals(LongLib.fromInt(-333), LongLib.div(LongLib.fromInt(-1000),
+        LongLib.fromInt(3)));
+    assertEquals(LongLib.fromInt(333), LongLib.div(LongLib.fromInt(-1000),
+        LongLib.fromInt(-3)));
+    assertEquals(LongLib.fromInt(0), LongLib.div(LongLib.fromInt(3),
+        LongLib.fromInt(1000)));
+    assertEquals(longFromBits(0x1003d0, 0xe84f5ae8), LongLib.div(longFromBits(
+        0x12345678, 0x12345678), longFromBits(0x0, 0x123)));
+    assertEquals(longFromBits(0x0, 0x10003), LongLib.div(longFromBits(
+        0x12345678, 0x12345678), longFromBits(0x1234, 0x12345678)));
+    assertEquals(longFromBits(0xffffffff, 0xffff3dfe), LongLib.div(
+        longFromBits(0xf2345678, 0x12345678), longFromBits(0x1234, 0x12345678)));
+    assertEquals(longFromBits(0x0, 0xeda), LongLib.div(longFromBits(0xf2345678,
+        0x12345678), longFromBits(0xffff1234, 0x12345678)));
+
+    try {
+      LongLib.div(LongLib.fromInt(1), LongLib.fromInt(0));
+      fail("Expected an ArithmeticException");
+    } catch (ArithmeticException e) {
+    }
+
+    assertEquals(longFromBits(0xc0000000, 0x00000000), LongLib.div(
+        Const.MIN_VALUE, LongLib.fromInt(2)));
+    assertEquals(Const.MIN_VALUE, LongLib.div(Const.MIN_VALUE,
+        LongLib.fromInt(1)));
+    assertEquals(Const.MIN_VALUE, LongLib.div(Const.MIN_VALUE,
+        LongLib.fromInt(-1))); // JLS3 section 15.17.2
+  }
+
+  public void testNegate() {
+    assertEquals(LongLib.fromInt(-1), LongLib.neg(LongLib.fromInt(1)));
+    assertEquals(LongLib.fromInt(1), LongLib.neg(LongLib.fromInt(-1)));
+
+    // JLS3 15.15.4
+    assertEquals(Const.MIN_VALUE, LongLib.neg(Const.MIN_VALUE));
+  }
+
+  public void testShift() {
+    assertEquals(longFromBits(0xd048d115, 0x9d159c00), LongLib.shl(
+        longFromBits(0x12341234, 0x45674567), 10));
+    assertEquals(longFromBits(0x48d04, 0x8d1159d1), LongLib.shr(longFromBits(
+        0x12341234, 0x45674567), 10));
+    assertEquals(longFromBits(0x48d04, 0x8d1159d1), LongLib.shru(longFromBits(
+        0x12341234, 0x45674567), 10));
+    assertEquals(longFromBits(0xd048d115, 0x9d159c00), LongLib.shl(
+        longFromBits(0x92341234, 0x45674567), 10));
+    assertEquals(longFromBits(0xffe48d04, 0x8d1159d1), LongLib.shr(
+        longFromBits(0x92341234, 0x45674567), 10));
+    assertEquals(longFromBits(0x248d04, 0x8d1159d1), LongLib.shru(longFromBits(
+        0x92341234, 0x45674567), 10));
+
+    assertEquals(LongLib.fromInt(-1), LongLib.shr(LongLib.fromInt(-1), 10));
+
+    assertEquals(LongLib.fromInt(-1 << 5), LongLib.shl(LongLib.fromInt(-1), 5));
+    assertEquals(LongLib.fromInt(-1), LongLib.shl(LongLib.fromInt(-1), 0));
+    assertEquals(LongLib.neg(LongLib.typeChange(0x4000000000000000L)),
+        LongLib.shr(LongLib.shl(LongLib.fromInt(1), 63), 1));
+    assertEquals(LongLib.fromInt(0), LongLib.shl(LongLib.shl(
+        LongLib.fromInt(-1), 32), 32));
+    assertEquals(Const.MIN_VALUE, LongLib.shl(Const.MIN_VALUE, 0));
+    assertEquals(LongLib.fromInt(0), LongLib.shl(Const.MIN_VALUE, 1));
+    assertEquals(longFromBits(0xfffffffc, 0x00000000), LongLib.shr(
+        LongLib.neg(longFromBits(8, 0)), 1));
+    assertEquals(longFromBits(0x7ffffffc, 0x0), LongLib.shru(
+        LongLib.neg(longFromBits(8, 0)), 1));
+  }
+
+  // Issue 1198, and also a good exercise of several methods.
+  public void testToHexString() {
+    double[] deadbeaf12341234 = longFromBits(0xdeadbeaf, 0x12341234);
+
+    assertEquals("deadbeaf12341234", toHexString(deadbeaf12341234));
+  }
+
+  public void testToString() {
+    assertEquals("0", LongLib.toString(LongLib.fromInt(0)));
+    assertEquals("1", LongLib.toString(LongLib.fromInt(1)));
+    assertEquals("-1", LongLib.toString(LongLib.fromInt(-1)));
+    assertEquals("-10", LongLib.toString(LongLib.fromInt(-10)));
+    assertEquals("-9223372036854775808", LongLib.toString(Const.MIN_VALUE));
+
+    int top = 922337201;
+    int bottom = 967490662;
+    double[] fullnum = LongLib.add(LongLib.mul(LongLib.fromInt(1000000000),
+        LongLib.fromInt(top)), LongLib.fromInt(bottom));
+
+    assertEquals("922337201967490662", LongLib.toString(fullnum));
+    assertEquals("-922337201967490662", LongLib.toString(LongLib.neg(fullnum)));
+  }
+
+  private double[] fact(double[] n) {
+    if (LongLib.eq(n, LongLib.fromInt(0))) {
+      return LongLib.fromInt(1);
+    } else {
+      return LongLib.mul(n, fact(LongLib.sub(n, LongLib.fromInt(1))));
+    }
+  }
+
+  private double[] longFromBits(int top, int bottom) {
+    double[] topHalf = LongLib.shl(LongLib.fromInt(top), 32);
+    double[] bottomHalf = LongLib.fromInt(bottom);
+    if (LongLib.lt(bottomHalf, Const.ZERO)) {
+      bottomHalf = LongLib.add(bottomHalf, LongLib.shl(LongLib.fromInt(1), 32));
+    }
+    double[] total = LongLib.add(topHalf, bottomHalf);
+    return total;
+  }
+
+  private String toHexString(double[] x) {
+    // copied from the GWT Long class and modified for double[]
+    double[] zero = LongLib.fromInt(0);
+
+    if (LongLib.eq(x, zero)) {
+      return "0";
+    }
+    String[] hexDigits = new String[] {
+        "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "a", "b", "c", "d",
+        "e", "f"};
+    String hexStr = "";
+    while (!LongLib.eq(x, zero)) {
+      int nibble = LongLib.toInt(x) & 0xF;
+      hexStr = hexDigits[nibble] + hexStr;
+      x = LongLib.shru(x, 4);
+    }
+    return hexStr;
+  }
+}
diff --git a/user/src/com/google/gwt/user/client/ui/MenuItemSeparator.java b/user/src/com/google/gwt/user/client/ui/MenuItemSeparator.java
index 4973c2d..5d0bd89 100644
--- a/user/src/com/google/gwt/user/client/ui/MenuItemSeparator.java
+++ b/user/src/com/google/gwt/user/client/ui/MenuItemSeparator.java
@@ -1,56 +1,56 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.client.ui;

-

-import com.google.gwt.user.client.DOM;

-import com.google.gwt.user.client.Element;

-

-/**

- * A separator that can be placed in a

- * {@link com.google.gwt.user.client.ui.MenuBar}.

- */

-public class MenuItemSeparator extends UIObject {

-

-  private static final String STYLENAME_DEFAULT = "gwt-MenuItemSeparator";

-

-  private MenuBar parentMenu;

-

-  /**

-   * Constructs a new {@link MenuItemSeparator}.

-   */

-  public MenuItemSeparator() {

-    setElement(DOM.createTD());

-    setStyleName(STYLENAME_DEFAULT);

-    

-    // Add an inner element for styling purposes

-    Element div = DOM.createDiv();

-    DOM.appendChild(getElement(), div);

-    setStyleName(div, "content");

-  }

-

-  /**

-   * Gets the menu that contains this item.

-   * 

-   * @return the parent menu, or <code>null</code> if none exists.

-   */

-  public MenuBar getParentMenu() {

-    return parentMenu;

-  }

-

-  void setParentMenu(MenuBar parentMenu) {

-    this.parentMenu = parentMenu;

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.client.ui;
+
+import com.google.gwt.user.client.DOM;
+import com.google.gwt.user.client.Element;
+
+/**
+ * A separator that can be placed in a
+ * {@link com.google.gwt.user.client.ui.MenuBar}.
+ */
+public class MenuItemSeparator extends UIObject {
+
+  private static final String STYLENAME_DEFAULT = "gwt-MenuItemSeparator";
+
+  private MenuBar parentMenu;
+
+  /**
+   * Constructs a new {@link MenuItemSeparator}.
+   */
+  public MenuItemSeparator() {
+    setElement(DOM.createTD());
+    setStyleName(STYLENAME_DEFAULT);
+    
+    // Add an inner element for styling purposes
+    Element div = DOM.createDiv();
+    DOM.appendChild(getElement(), div);
+    setStyleName(div, "content");
+  }
+
+  /**
+   * Gets the menu that contains this item.
+   * 
+   * @return the parent menu, or <code>null</code> if none exists.
+   */
+  public MenuBar getParentMenu() {
+    return parentMenu;
+  }
+
+  void setParentMenu(MenuBar parentMenu) {
+    this.parentMenu = parentMenu;
+  }
+}
diff --git a/user/super/com/google/gwt/emul/java/lang/ArithmeticException.java b/user/super/com/google/gwt/emul/java/lang/ArithmeticException.java
index 0f1a68a..faf821e 100644
--- a/user/super/com/google/gwt/emul/java/lang/ArithmeticException.java
+++ b/user/super/com/google/gwt/emul/java/lang/ArithmeticException.java
@@ -1,32 +1,32 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package java.lang;

-

-/**

- * NOTE: in GWT this is only thrown for division by zero on longs.

- * 

- * See <a

- * href="http://java.sun.com/j2se/1.5.0/docs/api/java/lang/ArrayIndexOutOfBoundsException.html">the

- * official Java API doc</a> for details.

- */

-public class ArithmeticException extends RuntimeException {

-  public ArithmeticException(String explanation) {

-    super(explanation);

-  }

-  public ArithmeticException() {

-    super();

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package java.lang;
+
+/**
+ * NOTE: in GWT this is only thrown for division by zero on longs.
+ * 
+ * See <a
+ * href="http://java.sun.com/j2se/1.5.0/docs/api/java/lang/ArrayIndexOutOfBoundsException.html">the
+ * official Java API doc</a> for details.
+ */
+public class ArithmeticException extends RuntimeException {
+  public ArithmeticException(String explanation) {
+    super(explanation);
+  }
+  public ArithmeticException() {
+    super();
+  }
+}
diff --git a/user/super/com/google/gwt/emul/java/util/HashMap.java b/user/super/com/google/gwt/emul/java/util/HashMap.java
index 713057d..3657ab7 100644
--- a/user/super/com/google/gwt/emul/java/util/HashMap.java
+++ b/user/super/com/google/gwt/emul/java/util/HashMap.java
@@ -1,65 +1,65 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package java.util;

-

-import java.io.Serializable;

-

-/**

- * Implementation of Map interface based on a hash table. <a

- * href="http://java.sun.com/j2se/1.5.0/docs/api/java/util/HashMap.html">[Sun

- * docs]</a>

- * 

- * @param <K> key type

- * @param <V> value type

- */

-public class HashMap<K, V> extends AbstractHashMap<K, V> implements Cloneable,

-    Serializable {

-

-  public HashMap() {

-  }

-

-  public HashMap(int ignored) {

-    // This implementation of HashMap has no need of initial capacities.

-    this(ignored, 0);

-  }

-

-  public HashMap(int ignored, float alsoIgnored) {

-    // This implementation of HashMap has no need of load factors or capacities.

-    if (ignored < 0 || alsoIgnored < 0) {

-      throw new IllegalArgumentException(

-          "initial capacity was negative or load factor was non-positive");

-    }

-  }

-

-  public HashMap(Map<? extends K, ? extends V> toBeCopied) {

-    super(toBeCopied);

-  }

-

-  @Override

-  public Object clone() {

-    return new HashMap<K, V>(this);

-  }

-

-  @Override

-  protected boolean equals(Object value1, Object value2) {

-    return Utility.equalsWithNullCheck(value1, value2);

-  }

-

-  @Override

-  protected int getHashCode(Object key) {

-    return key.hashCode();

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package java.util;
+
+import java.io.Serializable;
+
+/**
+ * Implementation of Map interface based on a hash table. <a
+ * href="http://java.sun.com/j2se/1.5.0/docs/api/java/util/HashMap.html">[Sun
+ * docs]</a>
+ * 
+ * @param <K> key type
+ * @param <V> value type
+ */
+public class HashMap<K, V> extends AbstractHashMap<K, V> implements Cloneable,
+    Serializable {
+
+  public HashMap() {
+  }
+
+  public HashMap(int ignored) {
+    // This implementation of HashMap has no need of initial capacities.
+    this(ignored, 0);
+  }
+
+  public HashMap(int ignored, float alsoIgnored) {
+    // This implementation of HashMap has no need of load factors or capacities.
+    if (ignored < 0 || alsoIgnored < 0) {
+      throw new IllegalArgumentException(
+          "initial capacity was negative or load factor was non-positive");
+    }
+  }
+
+  public HashMap(Map<? extends K, ? extends V> toBeCopied) {
+    super(toBeCopied);
+  }
+
+  @Override
+  public Object clone() {
+    return new HashMap<K, V>(this);
+  }
+
+  @Override
+  protected boolean equals(Object value1, Object value2) {
+    return Utility.equalsWithNullCheck(value1, value2);
+  }
+
+  @Override
+  protected int getHashCode(Object key) {
+    return key.hashCode();
+  }
+}
diff --git a/user/test/com/google/gwt/emultest/java/lang/LongTest.java b/user/test/com/google/gwt/emultest/java/lang/LongTest.java
index 9b7aece..273e98b 100644
--- a/user/test/com/google/gwt/emultest/java/lang/LongTest.java
+++ b/user/test/com/google/gwt/emultest/java/lang/LongTest.java
@@ -1,144 +1,144 @@
-/*

- * Copyright 2007 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.emultest.java.lang;

-

-import com.google.gwt.junit.client.GWTTestCase;

-

-/**

- * TODO: document me.

- */

-public class LongTest extends GWTTestCase {

-

-  public String getModuleName() {

-    return "com.google.gwt.emultest.EmulSuite";

-  }

-

-  public void testBinaryString() {

-    assertEquals("10001111101101101111011110001100100000000",

-        Long.toBinaryString(1234500000000L));

-    assertEquals("0", Long.toBinaryString(0L));

-    assertEquals(

-        "1111111111111111111111101110000010010010000100001110011100000000",

-        Long.toBinaryString(-1234500000000L));

-  }

-

-  public void testBitCount() {

-    assertEquals(0, Long.bitCount(0));

-    assertEquals(1, Long.bitCount(1));

-    assertEquals(64, Long.bitCount(-1));

-    assertEquals(63, Long.bitCount(Long.MAX_VALUE));

-    assertEquals(1, Long.bitCount(Long.MIN_VALUE));

-  }

-

-  public void testConstants() {

-    assertEquals(64, Long.SIZE);

-    assertEquals(0x7fffffffffffffffL, Long.MAX_VALUE);

-    assertEquals(0x8000000000000000L, Long.MIN_VALUE);

-  }

-

-  public void testHighestOneBit() {

-    assertEquals(0, Long.highestOneBit(0));

-    assertEquals(Long.MIN_VALUE, Long.highestOneBit(-1));

-    assertEquals(Long.MIN_VALUE, Long.highestOneBit(-256));

-    assertEquals(1, Long.highestOneBit(1));

-    assertEquals(0x80, Long.highestOneBit(0x88));

-    assertEquals(0x4000000000000000L, Long.highestOneBit(Long.MAX_VALUE));

-  }

-

-  public void testLowestOneBit() {

-    assertEquals(0, Long.lowestOneBit(0));

-    assertEquals(1, Long.lowestOneBit(-1));

-    assertEquals(0x100, Long.lowestOneBit(-256));

-    assertEquals(1, Long.lowestOneBit(1));

-    assertEquals(0x80, Long.lowestOneBit(0x780));

-    assertEquals(Long.MIN_VALUE, Long.lowestOneBit(Long.MIN_VALUE));

-  }

-

-  public void testNumberOfLeadingZeros() {

-    assertEquals(64, Long.numberOfLeadingZeros(0));

-    assertEquals(63, Long.numberOfLeadingZeros(1));

-    assertEquals(0, Long.numberOfLeadingZeros(-1));

-    assertEquals(32, Long.numberOfLeadingZeros(0x80000000L));

-    assertEquals(1, Long.numberOfLeadingZeros(Long.MAX_VALUE));

-    assertEquals(0, Long.numberOfLeadingZeros(Long.MIN_VALUE));

-    assertEquals(0, Long.numberOfLeadingZeros(-0x80000000L));

-  }

-

-  public void testNumberOfTrailingZeros() {

-    assertEquals(64, Long.numberOfTrailingZeros(0));

-    assertEquals(0, Long.numberOfTrailingZeros(1));

-    assertEquals(0, Long.numberOfTrailingZeros(-1));

-    assertEquals(31, Long.numberOfTrailingZeros(0x80000000L));

-    assertEquals(0, Long.numberOfTrailingZeros(Long.MAX_VALUE));

-    assertEquals(63, Long.numberOfTrailingZeros(Long.MIN_VALUE));

-    assertEquals(20, Long.numberOfTrailingZeros(-0x7ff00000L));

-  }

-

-  public void testReverse() {

-    assertEquals(0L, Long.reverse(0L));

-    assertEquals(-1L, Long.reverse(-1L));

-    assertEquals(Long.MIN_VALUE, Long.reverse(1L));

-    assertEquals(1L, Long.reverse(Long.MIN_VALUE));

-    assertEquals(0xaaaaaaaaaaaaaaaaL, Long.reverse(0x5555555555555555L));

-    assertEquals(0xaaaaaaaa00000000L, Long.reverse(0x55555555L));

-    assertEquals(0xaa00aa00aa00aa00L, Long.reverse(0x0055005500550055L));

-    assertEquals(0x5555555555555555L, Long.reverse(0xaaaaaaaaaaaaaaaaL));

-    assertEquals(0x55555555L, Long.reverse(0xaaaaaaaa00000000L));

-    assertEquals(0x0055005500550055L, Long.reverse(0xaa00aa00aa00aa00L));

-  }

-

-  public void testReverseBytes() {

-    assertEquals(0, Long.reverseBytes(0));

-    assertEquals(-1, Long.reverseBytes(-1));

-    assertEquals(0x80L, Long.reverseBytes(Long.MIN_VALUE));

-    assertEquals(Long.MIN_VALUE, Long.reverseBytes(0x80L));

-    assertEquals(0xf0debc9a78563412L, Long.reverseBytes(0x123456789abcdef0L));

-  }

-

-  public void testRotateLeft() {

-    assertEquals(0, Long.rotateLeft(0, 4));

-    assertEquals(0x2, Long.rotateLeft(1, 1));

-    assertEquals(0x10, Long.rotateLeft(1, 4));

-    assertEquals(-1, Long.rotateLeft(-1, 4));

-    assertEquals(Long.MIN_VALUE, Long.rotateLeft(0x4000000000000000L, 1));

-    assertEquals(1, Long.rotateLeft(Long.MIN_VALUE, 1));

-  }

-

-  public void testRotateRight() {

-    assertEquals(0, Long.rotateRight(0, 4));

-    assertEquals(Long.MIN_VALUE, Long.rotateRight(1, 1));

-    assertEquals(0x1000000000000000L, Long.rotateRight(1, 4));

-    assertEquals(-1, Long.rotateRight(-1, 4));

-  }

-

-  public void testSignum() {

-    assertEquals(0, Long.signum(0));

-    assertEquals(1, Long.signum(1));

-    assertEquals(-1, Long.signum(-1));

-    assertEquals(1, Long.signum(Long.MAX_VALUE));

-    assertEquals(-1, Long.signum(Long.MIN_VALUE));

-  }

-

-  public void testStaticValueOf() {

-    assertEquals(Long.MIN_VALUE, Long.valueOf(Long.MIN_VALUE).longValue());

-    assertEquals(Long.MAX_VALUE, Long.valueOf(Long.MAX_VALUE).longValue());

-  }

-

-  public void testToHexString() {

-    assertEquals("1234500000000", Long.toHexString(0x1234500000000L));

-    assertEquals("fff1234500000000", Long.toHexString(0xFFF1234500000000L));

-  }

-}

+/*
+ * Copyright 2007 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.emultest.java.lang;
+
+import com.google.gwt.junit.client.GWTTestCase;
+
+/**
+ * TODO: document me.
+ */
+public class LongTest extends GWTTestCase {
+
+  public String getModuleName() {
+    return "com.google.gwt.emultest.EmulSuite";
+  }
+
+  public void testBinaryString() {
+    assertEquals("10001111101101101111011110001100100000000",
+        Long.toBinaryString(1234500000000L));
+    assertEquals("0", Long.toBinaryString(0L));
+    assertEquals(
+        "1111111111111111111111101110000010010010000100001110011100000000",
+        Long.toBinaryString(-1234500000000L));
+  }
+
+  public void testBitCount() {
+    assertEquals(0, Long.bitCount(0));
+    assertEquals(1, Long.bitCount(1));
+    assertEquals(64, Long.bitCount(-1));
+    assertEquals(63, Long.bitCount(Long.MAX_VALUE));
+    assertEquals(1, Long.bitCount(Long.MIN_VALUE));
+  }
+
+  public void testConstants() {
+    assertEquals(64, Long.SIZE);
+    assertEquals(0x7fffffffffffffffL, Long.MAX_VALUE);
+    assertEquals(0x8000000000000000L, Long.MIN_VALUE);
+  }
+
+  public void testHighestOneBit() {
+    assertEquals(0, Long.highestOneBit(0));
+    assertEquals(Long.MIN_VALUE, Long.highestOneBit(-1));
+    assertEquals(Long.MIN_VALUE, Long.highestOneBit(-256));
+    assertEquals(1, Long.highestOneBit(1));
+    assertEquals(0x80, Long.highestOneBit(0x88));
+    assertEquals(0x4000000000000000L, Long.highestOneBit(Long.MAX_VALUE));
+  }
+
+  public void testLowestOneBit() {
+    assertEquals(0, Long.lowestOneBit(0));
+    assertEquals(1, Long.lowestOneBit(-1));
+    assertEquals(0x100, Long.lowestOneBit(-256));
+    assertEquals(1, Long.lowestOneBit(1));
+    assertEquals(0x80, Long.lowestOneBit(0x780));
+    assertEquals(Long.MIN_VALUE, Long.lowestOneBit(Long.MIN_VALUE));
+  }
+
+  public void testNumberOfLeadingZeros() {
+    assertEquals(64, Long.numberOfLeadingZeros(0));
+    assertEquals(63, Long.numberOfLeadingZeros(1));
+    assertEquals(0, Long.numberOfLeadingZeros(-1));
+    assertEquals(32, Long.numberOfLeadingZeros(0x80000000L));
+    assertEquals(1, Long.numberOfLeadingZeros(Long.MAX_VALUE));
+    assertEquals(0, Long.numberOfLeadingZeros(Long.MIN_VALUE));
+    assertEquals(0, Long.numberOfLeadingZeros(-0x80000000L));
+  }
+
+  public void testNumberOfTrailingZeros() {
+    assertEquals(64, Long.numberOfTrailingZeros(0));
+    assertEquals(0, Long.numberOfTrailingZeros(1));
+    assertEquals(0, Long.numberOfTrailingZeros(-1));
+    assertEquals(31, Long.numberOfTrailingZeros(0x80000000L));
+    assertEquals(0, Long.numberOfTrailingZeros(Long.MAX_VALUE));
+    assertEquals(63, Long.numberOfTrailingZeros(Long.MIN_VALUE));
+    assertEquals(20, Long.numberOfTrailingZeros(-0x7ff00000L));
+  }
+
+  public void testReverse() {
+    assertEquals(0L, Long.reverse(0L));
+    assertEquals(-1L, Long.reverse(-1L));
+    assertEquals(Long.MIN_VALUE, Long.reverse(1L));
+    assertEquals(1L, Long.reverse(Long.MIN_VALUE));
+    assertEquals(0xaaaaaaaaaaaaaaaaL, Long.reverse(0x5555555555555555L));
+    assertEquals(0xaaaaaaaa00000000L, Long.reverse(0x55555555L));
+    assertEquals(0xaa00aa00aa00aa00L, Long.reverse(0x0055005500550055L));
+    assertEquals(0x5555555555555555L, Long.reverse(0xaaaaaaaaaaaaaaaaL));
+    assertEquals(0x55555555L, Long.reverse(0xaaaaaaaa00000000L));
+    assertEquals(0x0055005500550055L, Long.reverse(0xaa00aa00aa00aa00L));
+  }
+
+  public void testReverseBytes() {
+    assertEquals(0, Long.reverseBytes(0));
+    assertEquals(-1, Long.reverseBytes(-1));
+    assertEquals(0x80L, Long.reverseBytes(Long.MIN_VALUE));
+    assertEquals(Long.MIN_VALUE, Long.reverseBytes(0x80L));
+    assertEquals(0xf0debc9a78563412L, Long.reverseBytes(0x123456789abcdef0L));
+  }
+
+  public void testRotateLeft() {
+    assertEquals(0, Long.rotateLeft(0, 4));
+    assertEquals(0x2, Long.rotateLeft(1, 1));
+    assertEquals(0x10, Long.rotateLeft(1, 4));
+    assertEquals(-1, Long.rotateLeft(-1, 4));
+    assertEquals(Long.MIN_VALUE, Long.rotateLeft(0x4000000000000000L, 1));
+    assertEquals(1, Long.rotateLeft(Long.MIN_VALUE, 1));
+  }
+
+  public void testRotateRight() {
+    assertEquals(0, Long.rotateRight(0, 4));
+    assertEquals(Long.MIN_VALUE, Long.rotateRight(1, 1));
+    assertEquals(0x1000000000000000L, Long.rotateRight(1, 4));
+    assertEquals(-1, Long.rotateRight(-1, 4));
+  }
+
+  public void testSignum() {
+    assertEquals(0, Long.signum(0));
+    assertEquals(1, Long.signum(1));
+    assertEquals(-1, Long.signum(-1));
+    assertEquals(1, Long.signum(Long.MAX_VALUE));
+    assertEquals(-1, Long.signum(Long.MIN_VALUE));
+  }
+
+  public void testStaticValueOf() {
+    assertEquals(Long.MIN_VALUE, Long.valueOf(Long.MIN_VALUE).longValue());
+    assertEquals(Long.MAX_VALUE, Long.valueOf(Long.MAX_VALUE).longValue());
+  }
+
+  public void testToHexString() {
+    assertEquals("1234500000000", Long.toHexString(0x1234500000000L));
+    assertEquals("fff1234500000000", Long.toHexString(0xFFF1234500000000L));
+  }
+}
diff --git a/user/test/com/google/gwt/emultest/java/util/ArrayListTest.java b/user/test/com/google/gwt/emultest/java/util/ArrayListTest.java
index 65fb249..3bb2b86 100644
--- a/user/test/com/google/gwt/emultest/java/util/ArrayListTest.java
+++ b/user/test/com/google/gwt/emultest/java/util/ArrayListTest.java
@@ -1,73 +1,73 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.emultest.java.util;

-

-import java.util.ArrayList;

-import java.util.List;

-

-/**

- * Tests ArrayList class (and by extension, AbstractList).

- */

-@SuppressWarnings("unchecked")

-public class ArrayListTest extends ListTestBase {

-

-  private static final class ArrayListWithRemoveRange extends ArrayList {

-    @Override

-    public void removeRange(int fromIndex, int toIndex) {

-      super.removeRange(fromIndex, toIndex);

-    }

-  }

-

-  public void testRemoveRange() {

-    ArrayListWithRemoveRange l = new ArrayListWithRemoveRange();

-    for (int i = 0; i < 10; i++) {

-      l.add(new Integer(i));

-    }

-    try {

-      l.removeRange(-1, 1);

-      fail();

-    } catch (IndexOutOfBoundsException expected) {

-    }

-

-    try {

-      l.removeRange(2, 1);

-      fail();

-    } catch (IndexOutOfBoundsException expected) {

-    }

-

-    try {

-      l.removeRange(2, 11);

-      fail();

-    } catch (IndexOutOfBoundsException expected) {

-    }

-

-    l.removeRange(3, 5);

-    assertEquals(8, l.size());

-    for (int i = 0; i < 3; i++) {

-      Integer elem = (Integer) l.get(i);

-      assertEquals(i, elem.intValue());

-    }

-    for (int i = 3; i < 8; i++) {

-      Integer elem = (Integer) l.get(i);

-      assertEquals(i + 2, elem.intValue());

-    }

-  }

-

-  @Override

-  protected List makeEmptyList() {

-    return new ArrayList();

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.emultest.java.util;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Tests ArrayList class (and by extension, AbstractList).
+ */
+@SuppressWarnings("unchecked")
+public class ArrayListTest extends ListTestBase {
+
+  private static final class ArrayListWithRemoveRange extends ArrayList {
+    @Override
+    public void removeRange(int fromIndex, int toIndex) {
+      super.removeRange(fromIndex, toIndex);
+    }
+  }
+
+  public void testRemoveRange() {
+    ArrayListWithRemoveRange l = new ArrayListWithRemoveRange();
+    for (int i = 0; i < 10; i++) {
+      l.add(new Integer(i));
+    }
+    try {
+      l.removeRange(-1, 1);
+      fail();
+    } catch (IndexOutOfBoundsException expected) {
+    }
+
+    try {
+      l.removeRange(2, 1);
+      fail();
+    } catch (IndexOutOfBoundsException expected) {
+    }
+
+    try {
+      l.removeRange(2, 11);
+      fail();
+    } catch (IndexOutOfBoundsException expected) {
+    }
+
+    l.removeRange(3, 5);
+    assertEquals(8, l.size());
+    for (int i = 0; i < 3; i++) {
+      Integer elem = (Integer) l.get(i);
+      assertEquals(i, elem.intValue());
+    }
+    for (int i = 3; i < 8; i++) {
+      Integer elem = (Integer) l.get(i);
+      assertEquals(i + 2, elem.intValue());
+    }
+  }
+
+  @Override
+  protected List makeEmptyList() {
+    return new ArrayList();
+  }
+}
diff --git a/user/test/com/google/gwt/user/client/ui/MenuBarTest.java b/user/test/com/google/gwt/user/client/ui/MenuBarTest.java
index fcfeff0..e679232 100644
--- a/user/test/com/google/gwt/user/client/ui/MenuBarTest.java
+++ b/user/test/com/google/gwt/user/client/ui/MenuBarTest.java
@@ -1,177 +1,177 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.client.ui;

-

-import com.google.gwt.junit.client.GWTTestCase;

-import com.google.gwt.user.client.Command;

-import com.google.gwt.user.client.DeferredCommand;

-

-import java.util.List;

-

-/**

- * Tests the DockPanel widget.

- */

-public class MenuBarTest extends GWTTestCase {

-  @Override

-  public String getModuleName() {

-    return "com.google.gwt.user.DebugTest";

-  }

-

-  /**

-   * Test adding and removing {@link MenuItem}s and {@link MenuItemSeparator}s

-   * from a menu.

-   */

-  public void testAddRemoveItems() {

-    // Create a menu bar

-    MenuBar bar = new MenuBar(true);

-

-    // Create a blank command

-    Command blankCommand = new Command() {

-      public void execute() {

-      }

-    };

-

-    // Add an item, default to text

-    MenuItem item0 = bar.addItem("<b>test</b>", blankCommand);

-    assertEquals("<b>test</b>", item0.getText());

-    assertEquals(blankCommand, item0.getCommand());

-    assertEquals(bar, item0.getParentMenu());

-

-    // Add a separator

-    MenuItemSeparator separator0 = bar.addSeparator();

-    assertEquals(bar, separator0.getParentMenu());

-

-    // Add another item, force to html

-    MenuItem item1 = bar.addItem("<b>test1</b>", true, blankCommand);

-    assertEquals("test1", item1.getText());

-    assertEquals(blankCommand, item1.getCommand());

-    assertEquals(bar, item1.getParentMenu());

-

-    // Get all items

-    List<MenuItem> items = bar.getItems();

-    assertEquals(item0, items.get(0));

-    assertEquals(item1, items.get(1));

-

-    // Remove an item

-    bar.removeItem(item0);

-    assertEquals(item1, items.get(0));

-    assertNull(item0.getParentMenu());

-

-    // Remove the separator

-    bar.removeSeparator(separator0);

-    assertEquals(item1, items.get(0));

-    assertNull(separator0.getParentMenu());

-    

-    // Add a bunch of items and clear them all

-    MenuItem item2 = bar.addItem("test2", true, blankCommand);

-    MenuItemSeparator separator1 = bar.addSeparator();

-    MenuItem item3 = bar.addItem("test3", true, blankCommand);

-    MenuItemSeparator separator2 = bar.addSeparator();

-    MenuItem item4 = bar.addItem("test4", true, blankCommand);

-    MenuItemSeparator separator3 = bar.addSeparator();

-    bar.clearItems();

-    assertEquals(0, bar.getItems().size());

-    assertNull(item2.getParentMenu());

-    assertNull(item3.getParentMenu());

-    assertNull(item4.getParentMenu());

-    assertNull(separator1.getParentMenu());

-    assertNull(separator2.getParentMenu());

-    assertNull(separator3.getParentMenu());

-  }

-

-  public void testDebugId() {

-    Command emptyCommand = new Command() {

-      public void execute() {

-      }

-    };

-

-    // Create a sub menu

-    MenuBar subMenu = new MenuBar(true);

-    subMenu.addItem("sub0", emptyCommand);

-    subMenu.addItem("sub1", emptyCommand);

-    subMenu.addItem("sub2", emptyCommand);

-

-    // Create a menu bar

-    MenuBar bar = new MenuBar(false);

-    bar.setAnimationEnabled(false);

-    bar.setAutoOpen(true);

-    bar.addItem("top0", emptyCommand);

-    bar.addItem("top1", emptyCommand);

-    MenuItem top2 = bar.addItem("top2", subMenu);

-    RootPanel.get().add(bar);

-    

-    // Open the item with a submenu

-    bar.itemOver(top2);

-

-    // Set the Debug Id

-    bar.ensureDebugId("myMenu");

-    UIObjectTest.assertDebugId("myMenu", bar.getElement());

-

-    DeferredCommand.addCommand(new Command() {

-      public void execute() {

-        UIObjectTest.assertDebugIdContents("myMenu-item0", "top0");

-        UIObjectTest.assertDebugIdContents("myMenu-item1", "top1");

-        UIObjectTest.assertDebugIdContents("myMenu-item2", "top2");

-

-        UIObjectTest.assertDebugIdContents("myMenu-item2-item0", "sub0");

-        UIObjectTest.assertDebugIdContents("myMenu-item2-item1", "sub1");

-        UIObjectTest.assertDebugIdContents("myMenu-item2-item2", "sub2");

-        finishTest();

-      }

-    });

-    delayTestFinish(250);

-  }

-

-  /**

-   * Test that the selected item points to the correct item.

-   */

-  public void testSelectedItem() {

-    // Create a menu bar

-    MenuBar bar = new MenuBar(true);

-

-    // Create a blank command

-    Command blankCommand = new Command() {

-      public void execute() {

-      }

-    };

-

-    // Add some items

-    MenuItem item0 = bar.addItem("item0", blankCommand);

-    MenuItem item1 = bar.addItem("item1", blankCommand);

-    MenuItem item2 = bar.addItem("item2", blankCommand);

-    MenuItem item3 = bar.addItem("item3", blankCommand);

-    MenuItem item4 = bar.addItem("item4", blankCommand);

-

-    // Test setting the selected item

-    assertNull(bar.getSelectedItem());

-    bar.selectItem(item1);

-    assertEquals(item1, bar.getSelectedItem());

-

-    // Test removing the selected item

-    bar.removeItem(item1);

-    assertNull(bar.getSelectedItem());

-

-    // Test removing an item that is not selected

-    bar.selectItem(item3);

-    assertEquals(item3, bar.getSelectedItem());

-    bar.removeItem(item2);

-    assertEquals(item3, bar.getSelectedItem());

-

-    // Test clearing all items

-    bar.clearItems();

-    assertNull(bar.getSelectedItem());

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.client.ui;
+
+import com.google.gwt.junit.client.GWTTestCase;
+import com.google.gwt.user.client.Command;
+import com.google.gwt.user.client.DeferredCommand;
+
+import java.util.List;
+
+/**
+ * Tests the DockPanel widget.
+ */
+public class MenuBarTest extends GWTTestCase {
+  @Override
+  public String getModuleName() {
+    return "com.google.gwt.user.DebugTest";
+  }
+
+  /**
+   * Test adding and removing {@link MenuItem}s and {@link MenuItemSeparator}s
+   * from a menu.
+   */
+  public void testAddRemoveItems() {
+    // Create a menu bar
+    MenuBar bar = new MenuBar(true);
+
+    // Create a blank command
+    Command blankCommand = new Command() {
+      public void execute() {
+      }
+    };
+
+    // Add an item, default to text
+    MenuItem item0 = bar.addItem("<b>test</b>", blankCommand);
+    assertEquals("<b>test</b>", item0.getText());
+    assertEquals(blankCommand, item0.getCommand());
+    assertEquals(bar, item0.getParentMenu());
+
+    // Add a separator
+    MenuItemSeparator separator0 = bar.addSeparator();
+    assertEquals(bar, separator0.getParentMenu());
+
+    // Add another item, force to html
+    MenuItem item1 = bar.addItem("<b>test1</b>", true, blankCommand);
+    assertEquals("test1", item1.getText());
+    assertEquals(blankCommand, item1.getCommand());
+    assertEquals(bar, item1.getParentMenu());
+
+    // Get all items
+    List<MenuItem> items = bar.getItems();
+    assertEquals(item0, items.get(0));
+    assertEquals(item1, items.get(1));
+
+    // Remove an item
+    bar.removeItem(item0);
+    assertEquals(item1, items.get(0));
+    assertNull(item0.getParentMenu());
+
+    // Remove the separator
+    bar.removeSeparator(separator0);
+    assertEquals(item1, items.get(0));
+    assertNull(separator0.getParentMenu());
+    
+    // Add a bunch of items and clear them all
+    MenuItem item2 = bar.addItem("test2", true, blankCommand);
+    MenuItemSeparator separator1 = bar.addSeparator();
+    MenuItem item3 = bar.addItem("test3", true, blankCommand);
+    MenuItemSeparator separator2 = bar.addSeparator();
+    MenuItem item4 = bar.addItem("test4", true, blankCommand);
+    MenuItemSeparator separator3 = bar.addSeparator();
+    bar.clearItems();
+    assertEquals(0, bar.getItems().size());
+    assertNull(item2.getParentMenu());
+    assertNull(item3.getParentMenu());
+    assertNull(item4.getParentMenu());
+    assertNull(separator1.getParentMenu());
+    assertNull(separator2.getParentMenu());
+    assertNull(separator3.getParentMenu());
+  }
+
+  public void testDebugId() {
+    Command emptyCommand = new Command() {
+      public void execute() {
+      }
+    };
+
+    // Create a sub menu
+    MenuBar subMenu = new MenuBar(true);
+    subMenu.addItem("sub0", emptyCommand);
+    subMenu.addItem("sub1", emptyCommand);
+    subMenu.addItem("sub2", emptyCommand);
+
+    // Create a menu bar
+    MenuBar bar = new MenuBar(false);
+    bar.setAnimationEnabled(false);
+    bar.setAutoOpen(true);
+    bar.addItem("top0", emptyCommand);
+    bar.addItem("top1", emptyCommand);
+    MenuItem top2 = bar.addItem("top2", subMenu);
+    RootPanel.get().add(bar);
+    
+    // Open the item with a submenu
+    bar.itemOver(top2);
+
+    // Set the Debug Id
+    bar.ensureDebugId("myMenu");
+    UIObjectTest.assertDebugId("myMenu", bar.getElement());
+
+    DeferredCommand.addCommand(new Command() {
+      public void execute() {
+        UIObjectTest.assertDebugIdContents("myMenu-item0", "top0");
+        UIObjectTest.assertDebugIdContents("myMenu-item1", "top1");
+        UIObjectTest.assertDebugIdContents("myMenu-item2", "top2");
+
+        UIObjectTest.assertDebugIdContents("myMenu-item2-item0", "sub0");
+        UIObjectTest.assertDebugIdContents("myMenu-item2-item1", "sub1");
+        UIObjectTest.assertDebugIdContents("myMenu-item2-item2", "sub2");
+        finishTest();
+      }
+    });
+    delayTestFinish(250);
+  }
+
+  /**
+   * Test that the selected item points to the correct item.
+   */
+  public void testSelectedItem() {
+    // Create a menu bar
+    MenuBar bar = new MenuBar(true);
+
+    // Create a blank command
+    Command blankCommand = new Command() {
+      public void execute() {
+      }
+    };
+
+    // Add some items
+    MenuItem item0 = bar.addItem("item0", blankCommand);
+    MenuItem item1 = bar.addItem("item1", blankCommand);
+    MenuItem item2 = bar.addItem("item2", blankCommand);
+    MenuItem item3 = bar.addItem("item3", blankCommand);
+    MenuItem item4 = bar.addItem("item4", blankCommand);
+
+    // Test setting the selected item
+    assertNull(bar.getSelectedItem());
+    bar.selectItem(item1);
+    assertEquals(item1, bar.getSelectedItem());
+
+    // Test removing the selected item
+    bar.removeItem(item1);
+    assertNull(bar.getSelectedItem());
+
+    // Test removing an item that is not selected
+    bar.selectItem(item3);
+    assertEquals(item3, bar.getSelectedItem());
+    bar.removeItem(item2);
+    assertEquals(item3, bar.getSelectedItem());
+
+    // Test clearing all items
+    bar.clearItems();
+    assertNull(bar.getSelectedItem());
+  }
+}
diff --git a/user/test/com/google/gwt/user/client/ui/PasswordTextBoxTest.java b/user/test/com/google/gwt/user/client/ui/PasswordTextBoxTest.java
index 1386e13..81caf30 100644
--- a/user/test/com/google/gwt/user/client/ui/PasswordTextBoxTest.java
+++ b/user/test/com/google/gwt/user/client/ui/PasswordTextBoxTest.java
@@ -1,27 +1,27 @@
-/*

- * Copyright 2007 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.client.ui;

-

-/**

- * Tests {@link PasswordTextBox}.

- */

-public class PasswordTextBoxTest extends TextBoxTest {

-

-  @Override

-  protected TextBox createTextBoxBase() {

-    return new PasswordTextBox();

-  }

-}

+/*
+ * Copyright 2007 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.client.ui;
+
+/**
+ * Tests {@link PasswordTextBox}.
+ */
+public class PasswordTextBoxTest extends TextBoxTest {
+
+  @Override
+  protected TextBox createTextBoxBase() {
+    return new PasswordTextBox();
+  }
+}
diff --git a/user/test/com/google/gwt/user/client/ui/TextBoxBaseTestBase.java b/user/test/com/google/gwt/user/client/ui/TextBoxBaseTestBase.java
index c17295f..76fdb1d 100644
--- a/user/test/com/google/gwt/user/client/ui/TextBoxBaseTestBase.java
+++ b/user/test/com/google/gwt/user/client/ui/TextBoxBaseTestBase.java
@@ -1,88 +1,88 @@
-/*

- * Copyright 2007 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.client.ui;

-

-import com.google.gwt.junit.client.GWTTestCase;

-

-/**

- * Abstract base test for {@link TextBox}, {@link TextArea}, and

- * {@link PasswordTextBox}.

- */

-public abstract class TextBoxBaseTestBase extends GWTTestCase {

-

-  public String getModuleName() {

-    return "com.google.gwt.user.User";

-  }

-

-  protected abstract TextBoxBase createTextBoxBase();

-

-  /**

-   * Tests that {@link TextArea#setText(String)} appropriately converts nulls to

-   * empty strings.

-   */

-  public void testNullMeansEmptyString() {

-    TextBoxBase area = createTextBoxBase();

-    area.setText(null);

-    assertEquals("setText(null) should result in empty string", "",

-        area.getText());

-  }

-

-  /**

-   * Tests that {@link TextArea#setCursorPos(int)} updates the cursor position

-   * correctly.

-   */

-  public void testMovingCursor() {

-    TextBoxBase area = createTextBoxBase();

-    RootPanel.get().add(area);

-    area.setText("abcd");

-    for (int i = 0; i < 4; i++) {

-      area.setCursorPos(i);

-      assertEquals(i, area.getCursorPos());

-    }

-  }

-

-  /**

-   * Tests various text selection methods in text area.

-   */

-  public void disabledTestSelection() {

-    TextBoxBase area = createTextBoxBase();

-    assertEquals("", area.getSelectedText());

-    area.selectAll();

-    assertEquals(0, area.getSelectionLength());

-    try {

-      area.setSelectionRange(0, 1);

-      fail("Should have thrown IndexOutOfBoundsException");

-    } catch (IndexOutOfBoundsException e) {

-      // Expected.

-    }

-

-    // IE bug: if not attached to dom, setSelectionRange fails.

-    RootPanel.get().add(area);

-    area.setText("a");

-

-    area.selectAll();

-    assertEquals(1, area.getSelectionLength());

-

-    area.setText("");

-    assertEquals(0, area.getSelectionLength());

-    area.setText("abcde");

-    area.setSelectionRange(2, 2);

-    assertEquals(2, area.getCursorPos());

-

-    // Check for setting 0;

-    area.setSelectionRange(0, 0);

-  }

-}

+/*
+ * Copyright 2007 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.client.ui;
+
+import com.google.gwt.junit.client.GWTTestCase;
+
+/**
+ * Abstract base test for {@link TextBox}, {@link TextArea}, and
+ * {@link PasswordTextBox}.
+ */
+public abstract class TextBoxBaseTestBase extends GWTTestCase {
+
+  public String getModuleName() {
+    return "com.google.gwt.user.User";
+  }
+
+  protected abstract TextBoxBase createTextBoxBase();
+
+  /**
+   * Tests that {@link TextArea#setText(String)} appropriately converts nulls to
+   * empty strings.
+   */
+  public void testNullMeansEmptyString() {
+    TextBoxBase area = createTextBoxBase();
+    area.setText(null);
+    assertEquals("setText(null) should result in empty string", "",
+        area.getText());
+  }
+
+  /**
+   * Tests that {@link TextArea#setCursorPos(int)} updates the cursor position
+   * correctly.
+   */
+  public void testMovingCursor() {
+    TextBoxBase area = createTextBoxBase();
+    RootPanel.get().add(area);
+    area.setText("abcd");
+    for (int i = 0; i < 4; i++) {
+      area.setCursorPos(i);
+      assertEquals(i, area.getCursorPos());
+    }
+  }
+
+  /**
+   * Tests various text selection methods in text area.
+   */
+  public void disabledTestSelection() {
+    TextBoxBase area = createTextBoxBase();
+    assertEquals("", area.getSelectedText());
+    area.selectAll();
+    assertEquals(0, area.getSelectionLength());
+    try {
+      area.setSelectionRange(0, 1);
+      fail("Should have thrown IndexOutOfBoundsException");
+    } catch (IndexOutOfBoundsException e) {
+      // Expected.
+    }
+
+    // IE bug: if not attached to dom, setSelectionRange fails.
+    RootPanel.get().add(area);
+    area.setText("a");
+
+    area.selectAll();
+    assertEquals(1, area.getSelectionLength());
+
+    area.setText("");
+    assertEquals(0, area.getSelectionLength());
+    area.setText("abcde");
+    area.setSelectionRange(2, 2);
+    assertEquals(2, area.getCursorPos());
+
+    // Check for setting 0;
+    area.setSelectionRange(0, 0);
+  }
+}
diff --git a/user/test/com/google/gwt/user/client/ui/TextBoxTest.java b/user/test/com/google/gwt/user/client/ui/TextBoxTest.java
index 129a8a9..42a6963 100644
--- a/user/test/com/google/gwt/user/client/ui/TextBoxTest.java
+++ b/user/test/com/google/gwt/user/client/ui/TextBoxTest.java
@@ -1,47 +1,47 @@
-/*

- * Copyright 2007 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.client.ui;

-

-/**

- * Testing TextBox.

- */

-public class TextBoxTest extends TextBoxBaseTestBase {

-

-  @Override

-  protected TextBox createTextBoxBase() {

-    return new TextBox();

-  }

-

-  public void testMaxLength() {

-    TextBox b = createTextBoxBase();

-    b.setMaxLength(5);

-    assertEquals(5, b.getMaxLength());

-    // As our setText does not honor max length, no way to text it in the wild

-    // here.

-  }

- 

-  public void testMinLength() {

-    TextBox b = createTextBoxBase();

-    b.setVisibleLength(5);

-

-    // Make sure maxLength is independent from visible length.

-    b.setMaxLength(10);

-    assertEquals(10, b.getMaxLength());

-

-    // Now check visible length.

-    assertEquals(5, b.getVisibleLength());

-  }

-}

+/*
+ * Copyright 2007 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.client.ui;
+
+/**
+ * Testing TextBox.
+ */
+public class TextBoxTest extends TextBoxBaseTestBase {
+
+  @Override
+  protected TextBox createTextBoxBase() {
+    return new TextBox();
+  }
+
+  public void testMaxLength() {
+    TextBox b = createTextBoxBase();
+    b.setMaxLength(5);
+    assertEquals(5, b.getMaxLength());
+    // As our setText does not honor max length, no way to text it in the wild
+    // here.
+  }
+ 
+  public void testMinLength() {
+    TextBox b = createTextBoxBase();
+    b.setVisibleLength(5);
+
+    // Make sure maxLength is independent from visible length.
+    b.setMaxLength(10);
+    assertEquals(10, b.getMaxLength());
+
+    // Now check visible length.
+    assertEquals(5, b.getVisibleLength());
+  }
+}
diff --git a/user/test/com/google/gwt/user/rebind/rpc/SerializableTypeOracleBuilderTest.java b/user/test/com/google/gwt/user/rebind/rpc/SerializableTypeOracleBuilderTest.java
index bdd4d32..1d7fe84 100644
--- a/user/test/com/google/gwt/user/rebind/rpc/SerializableTypeOracleBuilderTest.java
+++ b/user/test/com/google/gwt/user/rebind/rpc/SerializableTypeOracleBuilderTest.java
@@ -1,349 +1,349 @@
-/*

- * Copyright 2008 Google Inc.

- * 

- * Licensed under the Apache License, Version 2.0 (the "License"); you may not

- * use this file except in compliance with the License. You may obtain a copy of

- * the License at

- * 

- * http://www.apache.org/licenses/LICENSE-2.0

- * 

- * Unless required by applicable law or agreed to in writing, software

- * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT

- * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the

- * License for the specific language governing permissions and limitations under

- * the License.

- */

-package com.google.gwt.user.rebind.rpc;

-

-import com.google.gwt.core.ext.BadPropertyValueException;

-import com.google.gwt.core.ext.PropertyOracle;

-import com.google.gwt.core.ext.TreeLogger;

-import com.google.gwt.core.ext.UnableToCompleteException;

-import com.google.gwt.core.ext.typeinfo.JClassType;

-import com.google.gwt.core.ext.typeinfo.JGenericType;

-import com.google.gwt.core.ext.typeinfo.JType;

-import com.google.gwt.core.ext.typeinfo.NotFoundException;

-import com.google.gwt.core.ext.typeinfo.TypeOracle;

-import com.google.gwt.dev.cfg.ModuleDef;

-import com.google.gwt.dev.cfg.ModuleDefLoader;

-import com.google.gwt.dev.util.log.AbstractTreeLogger;

-import com.google.gwt.dev.util.log.PrintWriterTreeLogger;

-import com.google.gwt.user.client.rpc.IncompatibleRemoteServiceException;

-import com.google.gwt.user.rebind.rpc.testcases.client.AbstractSerializableTypes;

-import com.google.gwt.user.rebind.rpc.testcases.client.CovariantArrays;

-import com.google.gwt.user.rebind.rpc.testcases.client.ManualSerialization;

-import com.google.gwt.user.rebind.rpc.testcases.client.MissingGwtTypeArgs;

-import com.google.gwt.user.rebind.rpc.testcases.client.ClassWithTypeParameterThatErasesToObject;

-import com.google.gwt.user.rebind.rpc.testcases.client.NoSerializableTypes;

-import com.google.gwt.user.rebind.rpc.testcases.client.NotAllSubtypesAreSerializable;

-import com.google.gwt.user.rebind.rpc.testcases.client.ObjectArrayInMethodSignature;

-import com.google.gwt.user.rebind.rpc.testcases.client.ObjectInMethodSignature;

-

-import junit.framework.TestCase;

-

-import java.util.Arrays;

-import java.util.Comparator;

-

-/**

- * Used to test the {@link SerializableTypeOracleBuilder}.

- */

-public class SerializableTypeOracleBuilderTest extends TestCase {

-  /**

-   * Used to test the results produced by the {@link SerializableTypeOracle}.

-   */

-  static class TypeInfo {

-    boolean maybeInstantiated;

-    final String sourceName;

-

-    TypeInfo(String binaryName, boolean maybeInstantiated) {

-      this.sourceName = makeSourceName(binaryName);

-      this.maybeInstantiated = maybeInstantiated;

-    }

-

-    public boolean equals(Object obj) {

-      if (this == obj) {

-        return true;

-      }

-

-      if (!(obj instanceof TypeInfo)) {

-        return false;

-      }

-

-      TypeInfo other = (TypeInfo) obj;

-      return sourceName.equals(other.sourceName)

-          && maybeInstantiated == other.maybeInstantiated;

-    }

-

-    public String toString() {

-      return "{ " + sourceName + ", " + Boolean.toString(maybeInstantiated)

-          + " }";

-    }

-  }

-

-  private static class MockPropertyOracle implements PropertyOracle {

-    public String getPropertyValue(TreeLogger logger, String propertyName) {

-      // Could mock "gwt.enforceRPCTypeVersioning" etc here

-      return "";

-    }

-

-    public String[] getPropertyValueSet(TreeLogger logger, String propertyName)

-        throws BadPropertyValueException {

-      return new String[] { "" };

-    }

-  }

-

-  /**

-   * No logger output will be written to the console.

-   */

-  private static final boolean SUPPRESS_LOGGER_OUTPUT = true;

-

-  private static TypeInfo[] getActualTypeInfo(SerializableTypeOracle sto) {

-    JType[] types = sto.getSerializableTypes();

-    TypeInfo[] actual = new TypeInfo[types.length];

-    for (int i = 0; i < types.length; ++i) {

-      JType type = types[i];

-      actual[i] = new TypeInfo(type.getParameterizedQualifiedSourceName(),

-          sto.maybeInstantiated(type));

-    }

-    sort(actual);

-    return actual;

-  }

-

-  private static String makeSourceName(String binaryName) {

-    return binaryName.replace('$', '.');

-  }

-

-  private static void sort(TypeInfo[] typeInfos) {

-    Arrays.sort(typeInfos, new Comparator<TypeInfo>() {

-      public int compare(TypeInfo ti1, TypeInfo ti2) {

-        if (ti1 == ti2) {

-          return 0;

-        }

-

-        return ti1.sourceName.compareTo(ti2.sourceName);

-      }

-    });

-  }

-

-  private static String toString(TypeInfo[] typeInfos) {

-    StringBuffer sb = new StringBuffer();

-    sb.append("[");

-    for (int i = 0; i < typeInfos.length; ++i) {

-      if (i != 0) {

-        sb.append(",");

-      }

-      sb.append(typeInfos[i].toString());

-      sb.append("\n");

-    }

-

-    sb.append("]");

-    return sb.toString();

-  }

-

-  private static void validateSTO(SerializableTypeOracle sto,

-      TypeInfo[] expected) {

-    sort(expected);

-    TypeInfo[] actual = getActualTypeInfo(sto);

-

-    assertTrue("Expected: \n" + toString(expected) + ",\n Actual: \n"

-        + toString(actual), Arrays.equals(expected, actual));

-  }

-

-  /**

-   * This could be your own tree logger, perhaps validating the error output.

-   */

-  private final TreeLogger logger = SUPPRESS_LOGGER_OUTPUT ? TreeLogger.NULL

-      : new PrintWriterTreeLogger();

-

-  private final ModuleDef moduleDef;

-

-  private final PropertyOracle propertyOracle = new MockPropertyOracle();

-

-  private final TypeOracle typeOracle;

-

-  public SerializableTypeOracleBuilderTest() throws UnableToCompleteException {

-    if (logger instanceof AbstractTreeLogger) {

-      ((AbstractTreeLogger) logger).setMaxDetail(TreeLogger.INFO);

-    }

-

-    moduleDef = ModuleDefLoader.createSyntheticModule(logger,

-        "com.google.gwt.user.rebind.rpc.testcases.RebindRPCTestCases.JUnit",

-        new String[] {

-            "com.google.gwt.user.rebind.rpc.testcases.RebindRPCTestCases",

-            "com.google.gwt.junit.JUnit"}, true);

-    typeOracle = moduleDef.getTypeOracle(logger);

-  }

-

-  /**

-   * Tests that both the generic and raw forms of type that has a type parameter

-   * that erases to object are not serializable.

-   * 

-   * @throws NotFoundException

-   */

-  public void testClassWithTypeParameterThatErasesToObject()

-      throws NotFoundException, UnableToCompleteException {

-    JGenericType genericType = typeOracle.getType(

-        ClassWithTypeParameterThatErasesToObject.class.getName().replace('$',

-            '.')).isGenericType();

-

-    // The generic form of the type should not be serializable.

-    SerializableTypeOracleBuilder genericStob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    assertFalse(genericStob.checkTypeInstantiable(logger, genericType, false));

-

-    // The raw form of the type should not be serializable.

-    SerializableTypeOracleBuilder rawStob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    assertFalse(rawStob.checkTypeInstantiable(logger, genericType.getRawType(),

-        false));

-  }

-

-  /**

-   * Tests that a method signature which returns an Array type also includes the

-   * possible covariant array types which could contain a serializable type.

-   */

-  public void testCovariantArrays() throws UnableToCompleteException,

-      NotFoundException {

-

-    JClassType testServiceClass = typeOracle.getType(CovariantArrays.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    SerializableTypeOracle sto = stob.build(propertyOracle, testServiceClass);

-

-    TypeInfo[] expected = new TypeInfo[] {

-        new TypeInfo(IncompatibleRemoteServiceException.class.getName(), true),

-        new TypeInfo(CovariantArrays.AA.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.BB.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.CC.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.DD.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.A.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.B.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.B.class.getName(), true),

-        new TypeInfo(CovariantArrays.C.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.D.class.getName() + "[]", true),

-        new TypeInfo(CovariantArrays.D.class.getName(), true),

-        new TypeInfo(Exception.class.getName(), false),

-        new TypeInfo(RuntimeException.class.getName(), false),

-        new TypeInfo(String.class.getName(), true),

-        new TypeInfo(Throwable.class.getName(), false)};

-    validateSTO(sto, expected);

-  }

-

-  /**

-   * Tests that a manually serialized type with a field that is not serializable

-   * does not cause the generator to fail.

-   */

-  public void testManualSerialization() throws NotFoundException,

-      UnableToCompleteException {

-    JClassType testServiceClass = typeOracle.getType(ManualSerialization.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    stob.build(propertyOracle, testServiceClass);

-  }

-

-  /**

-   * Tests that a missing gwt.typeArgs will not result in a failure. The set of

-   * types is not currently being checked.

-   */

-  public void testMissingGwtTypeArgs() throws NotFoundException,

-      UnableToCompleteException {

-    JClassType testServiceClass = typeOracle.getType(MissingGwtTypeArgs.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    stob.build(propertyOracle, testServiceClass);

-  }

-

-  /**

-   * Tests that a method signature which has no serializable types will result

-   * in a failure.

-   */

-  public void testNoSerializableTypes() throws NotFoundException,

-      UnableToCompleteException {

-    JClassType testServiceClass = typeOracle.getType(NoSerializableTypes.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    try {

-      stob.build(propertyOracle, testServiceClass);

-      fail("Should have thrown an UnableToCompleteException");

-    } catch (UnableToCompleteException ex) {

-      // expected to get here

-    }

-  }

-

-  /**

-   * Tests that a method signature which only has type whose inheritance

-   * hiearchy has a mix of serializable and unserializable types will not cause

-   * the generator fail. It also checks for the set of serializable types.

-   */

-  public void testNotAllSubtypesAreSerializable()

-      throws UnableToCompleteException, NotFoundException {

-

-    JClassType testServiceClass = typeOracle.getType(NotAllSubtypesAreSerializable.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    SerializableTypeOracle sto = stob.build(propertyOracle, testServiceClass);

-

-    TypeInfo[] expected = new TypeInfo[] {

-        new TypeInfo(IncompatibleRemoteServiceException.class.getName(), true),

-        new TypeInfo(

-            makeSourceName(NotAllSubtypesAreSerializable.B.class.getName()),

-            true),

-        new TypeInfo(

-            makeSourceName(NotAllSubtypesAreSerializable.D.class.getName()),

-            true), new TypeInfo(Exception.class.getName(), false),

-        new TypeInfo(RuntimeException.class.getName(), false),

-        new TypeInfo(String.class.getName(), true),

-        new TypeInfo(Throwable.class.getName(), false)};

-    validateSTO(sto, expected);

-  }

-

-  /**

-   * Tests that a method signature which only has Object in its signature fails.

-   */

-  public void testObjectArrayInMethodSignature() throws NotFoundException,

-      UnableToCompleteException {

-    JClassType testServiceClass = typeOracle.getType(ObjectArrayInMethodSignature.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    try {

-      stob.build(propertyOracle, testServiceClass);

-      fail("Expected UnableToCompleteException");

-    } catch (UnableToCompleteException e) {

-      // Should get here

-    }

-  }

-

-  /**

-   * Tests that a method signature which only has Object in its signature fails.

-   */

-  public void testObjectInMethodSignature() throws NotFoundException,

-      UnableToCompleteException {

-    JClassType testServiceClass = typeOracle.getType(ObjectInMethodSignature.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    try {

-      stob.build(propertyOracle, testServiceClass);

-      fail("Expected UnableToCompleteException");

-    } catch (UnableToCompleteException e) {

-      // Should get here

-    }

-  }

-

-  /**

-   * Tests that a method signature which only has abstract serializable types

-   * fails.

-   */

-  public void testOnlyAbstractSerializableTypes()

-      throws UnableToCompleteException, NotFoundException {

-

-    JClassType testServiceClass = typeOracle.getType(AbstractSerializableTypes.class.getName());

-    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(

-        logger, typeOracle);

-    try {

-      stob.build(propertyOracle, testServiceClass);

-      fail("Expected UnableToCompleteException");

-    } catch (UnableToCompleteException e) {

-      // Should get here

-    }

-  }

-}

+/*
+ * Copyright 2008 Google Inc.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.user.rebind.rpc;
+
+import com.google.gwt.core.ext.BadPropertyValueException;
+import com.google.gwt.core.ext.PropertyOracle;
+import com.google.gwt.core.ext.TreeLogger;
+import com.google.gwt.core.ext.UnableToCompleteException;
+import com.google.gwt.core.ext.typeinfo.JClassType;
+import com.google.gwt.core.ext.typeinfo.JGenericType;
+import com.google.gwt.core.ext.typeinfo.JType;
+import com.google.gwt.core.ext.typeinfo.NotFoundException;
+import com.google.gwt.core.ext.typeinfo.TypeOracle;
+import com.google.gwt.dev.cfg.ModuleDef;
+import com.google.gwt.dev.cfg.ModuleDefLoader;
+import com.google.gwt.dev.util.log.AbstractTreeLogger;
+import com.google.gwt.dev.util.log.PrintWriterTreeLogger;
+import com.google.gwt.user.client.rpc.IncompatibleRemoteServiceException;
+import com.google.gwt.user.rebind.rpc.testcases.client.AbstractSerializableTypes;
+import com.google.gwt.user.rebind.rpc.testcases.client.CovariantArrays;
+import com.google.gwt.user.rebind.rpc.testcases.client.ManualSerialization;
+import com.google.gwt.user.rebind.rpc.testcases.client.MissingGwtTypeArgs;
+import com.google.gwt.user.rebind.rpc.testcases.client.ClassWithTypeParameterThatErasesToObject;
+import com.google.gwt.user.rebind.rpc.testcases.client.NoSerializableTypes;
+import com.google.gwt.user.rebind.rpc.testcases.client.NotAllSubtypesAreSerializable;
+import com.google.gwt.user.rebind.rpc.testcases.client.ObjectArrayInMethodSignature;
+import com.google.gwt.user.rebind.rpc.testcases.client.ObjectInMethodSignature;
+
+import junit.framework.TestCase;
+
+import java.util.Arrays;
+import java.util.Comparator;
+
+/**
+ * Used to test the {@link SerializableTypeOracleBuilder}.
+ */
+public class SerializableTypeOracleBuilderTest extends TestCase {
+  /**
+   * Used to test the results produced by the {@link SerializableTypeOracle}.
+   */
+  static class TypeInfo {
+    boolean maybeInstantiated;
+    final String sourceName;
+
+    TypeInfo(String binaryName, boolean maybeInstantiated) {
+      this.sourceName = makeSourceName(binaryName);
+      this.maybeInstantiated = maybeInstantiated;
+    }
+
+    public boolean equals(Object obj) {
+      if (this == obj) {
+        return true;
+      }
+
+      if (!(obj instanceof TypeInfo)) {
+        return false;
+      }
+
+      TypeInfo other = (TypeInfo) obj;
+      return sourceName.equals(other.sourceName)
+          && maybeInstantiated == other.maybeInstantiated;
+    }
+
+    public String toString() {
+      return "{ " + sourceName + ", " + Boolean.toString(maybeInstantiated)
+          + " }";
+    }
+  }
+
+  private static class MockPropertyOracle implements PropertyOracle {
+    public String getPropertyValue(TreeLogger logger, String propertyName) {
+      // Could mock "gwt.enforceRPCTypeVersioning" etc here
+      return "";
+    }
+
+    public String[] getPropertyValueSet(TreeLogger logger, String propertyName)
+        throws BadPropertyValueException {
+      return new String[] { "" };
+    }
+  }
+
+  /**
+   * No logger output will be written to the console.
+   */
+  private static final boolean SUPPRESS_LOGGER_OUTPUT = true;
+
+  private static TypeInfo[] getActualTypeInfo(SerializableTypeOracle sto) {
+    JType[] types = sto.getSerializableTypes();
+    TypeInfo[] actual = new TypeInfo[types.length];
+    for (int i = 0; i < types.length; ++i) {
+      JType type = types[i];
+      actual[i] = new TypeInfo(type.getParameterizedQualifiedSourceName(),
+          sto.maybeInstantiated(type));
+    }
+    sort(actual);
+    return actual;
+  }
+
+  private static String makeSourceName(String binaryName) {
+    return binaryName.replace('$', '.');
+  }
+
+  private static void sort(TypeInfo[] typeInfos) {
+    Arrays.sort(typeInfos, new Comparator<TypeInfo>() {
+      public int compare(TypeInfo ti1, TypeInfo ti2) {
+        if (ti1 == ti2) {
+          return 0;
+        }
+
+        return ti1.sourceName.compareTo(ti2.sourceName);
+      }
+    });
+  }
+
+  private static String toString(TypeInfo[] typeInfos) {
+    StringBuffer sb = new StringBuffer();
+    sb.append("[");
+    for (int i = 0; i < typeInfos.length; ++i) {
+      if (i != 0) {
+        sb.append(",");
+      }
+      sb.append(typeInfos[i].toString());
+      sb.append("\n");
+    }
+
+    sb.append("]");
+    return sb.toString();
+  }
+
+  private static void validateSTO(SerializableTypeOracle sto,
+      TypeInfo[] expected) {
+    sort(expected);
+    TypeInfo[] actual = getActualTypeInfo(sto);
+
+    assertTrue("Expected: \n" + toString(expected) + ",\n Actual: \n"
+        + toString(actual), Arrays.equals(expected, actual));
+  }
+
+  /**
+   * This could be your own tree logger, perhaps validating the error output.
+   */
+  private final TreeLogger logger = SUPPRESS_LOGGER_OUTPUT ? TreeLogger.NULL
+      : new PrintWriterTreeLogger();
+
+  private final ModuleDef moduleDef;
+
+  private final PropertyOracle propertyOracle = new MockPropertyOracle();
+
+  private final TypeOracle typeOracle;
+
+  public SerializableTypeOracleBuilderTest() throws UnableToCompleteException {
+    if (logger instanceof AbstractTreeLogger) {
+      ((AbstractTreeLogger) logger).setMaxDetail(TreeLogger.INFO);
+    }
+
+    moduleDef = ModuleDefLoader.createSyntheticModule(logger,
+        "com.google.gwt.user.rebind.rpc.testcases.RebindRPCTestCases.JUnit",
+        new String[] {
+            "com.google.gwt.user.rebind.rpc.testcases.RebindRPCTestCases",
+            "com.google.gwt.junit.JUnit"}, true);
+    typeOracle = moduleDef.getTypeOracle(logger);
+  }
+
+  /**
+   * Tests that both the generic and raw forms of type that has a type parameter
+   * that erases to object are not serializable.
+   * 
+   * @throws NotFoundException
+   */
+  public void testClassWithTypeParameterThatErasesToObject()
+      throws NotFoundException, UnableToCompleteException {
+    JGenericType genericType = typeOracle.getType(
+        ClassWithTypeParameterThatErasesToObject.class.getName().replace('$',
+            '.')).isGenericType();
+
+    // The generic form of the type should not be serializable.
+    SerializableTypeOracleBuilder genericStob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    assertFalse(genericStob.checkTypeInstantiable(logger, genericType, false));
+
+    // The raw form of the type should not be serializable.
+    SerializableTypeOracleBuilder rawStob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    assertFalse(rawStob.checkTypeInstantiable(logger, genericType.getRawType(),
+        false));
+  }
+
+  /**
+   * Tests that a method signature which returns an Array type also includes the
+   * possible covariant array types which could contain a serializable type.
+   */
+  public void testCovariantArrays() throws UnableToCompleteException,
+      NotFoundException {
+
+    JClassType testServiceClass = typeOracle.getType(CovariantArrays.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    SerializableTypeOracle sto = stob.build(propertyOracle, testServiceClass);
+
+    TypeInfo[] expected = new TypeInfo[] {
+        new TypeInfo(IncompatibleRemoteServiceException.class.getName(), true),
+        new TypeInfo(CovariantArrays.AA.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.BB.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.CC.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.DD.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.A.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.B.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.B.class.getName(), true),
+        new TypeInfo(CovariantArrays.C.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.D.class.getName() + "[]", true),
+        new TypeInfo(CovariantArrays.D.class.getName(), true),
+        new TypeInfo(Exception.class.getName(), false),
+        new TypeInfo(RuntimeException.class.getName(), false),
+        new TypeInfo(String.class.getName(), true),
+        new TypeInfo(Throwable.class.getName(), false)};
+    validateSTO(sto, expected);
+  }
+
+  /**
+   * Tests that a manually serialized type with a field that is not serializable
+   * does not cause the generator to fail.
+   */
+  public void testManualSerialization() throws NotFoundException,
+      UnableToCompleteException {
+    JClassType testServiceClass = typeOracle.getType(ManualSerialization.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    stob.build(propertyOracle, testServiceClass);
+  }
+
+  /**
+   * Tests that a missing gwt.typeArgs will not result in a failure. The set of
+   * types is not currently being checked.
+   */
+  public void testMissingGwtTypeArgs() throws NotFoundException,
+      UnableToCompleteException {
+    JClassType testServiceClass = typeOracle.getType(MissingGwtTypeArgs.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    stob.build(propertyOracle, testServiceClass);
+  }
+
+  /**
+   * Tests that a method signature which has no serializable types will result
+   * in a failure.
+   */
+  public void testNoSerializableTypes() throws NotFoundException,
+      UnableToCompleteException {
+    JClassType testServiceClass = typeOracle.getType(NoSerializableTypes.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    try {
+      stob.build(propertyOracle, testServiceClass);
+      fail("Should have thrown an UnableToCompleteException");
+    } catch (UnableToCompleteException ex) {
+      // expected to get here
+    }
+  }
+
+  /**
+   * Tests that a method signature which only has type whose inheritance
+   * hiearchy has a mix of serializable and unserializable types will not cause
+   * the generator fail. It also checks for the set of serializable types.
+   */
+  public void testNotAllSubtypesAreSerializable()
+      throws UnableToCompleteException, NotFoundException {
+
+    JClassType testServiceClass = typeOracle.getType(NotAllSubtypesAreSerializable.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    SerializableTypeOracle sto = stob.build(propertyOracle, testServiceClass);
+
+    TypeInfo[] expected = new TypeInfo[] {
+        new TypeInfo(IncompatibleRemoteServiceException.class.getName(), true),
+        new TypeInfo(
+            makeSourceName(NotAllSubtypesAreSerializable.B.class.getName()),
+            true),
+        new TypeInfo(
+            makeSourceName(NotAllSubtypesAreSerializable.D.class.getName()),
+            true), new TypeInfo(Exception.class.getName(), false),
+        new TypeInfo(RuntimeException.class.getName(), false),
+        new TypeInfo(String.class.getName(), true),
+        new TypeInfo(Throwable.class.getName(), false)};
+    validateSTO(sto, expected);
+  }
+
+  /**
+   * Tests that a method signature which only has Object in its signature fails.
+   */
+  public void testObjectArrayInMethodSignature() throws NotFoundException,
+      UnableToCompleteException {
+    JClassType testServiceClass = typeOracle.getType(ObjectArrayInMethodSignature.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    try {
+      stob.build(propertyOracle, testServiceClass);
+      fail("Expected UnableToCompleteException");
+    } catch (UnableToCompleteException e) {
+      // Should get here
+    }
+  }
+
+  /**
+   * Tests that a method signature which only has Object in its signature fails.
+   */
+  public void testObjectInMethodSignature() throws NotFoundException,
+      UnableToCompleteException {
+    JClassType testServiceClass = typeOracle.getType(ObjectInMethodSignature.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    try {
+      stob.build(propertyOracle, testServiceClass);
+      fail("Expected UnableToCompleteException");
+    } catch (UnableToCompleteException e) {
+      // Should get here
+    }
+  }
+
+  /**
+   * Tests that a method signature which only has abstract serializable types
+   * fails.
+   */
+  public void testOnlyAbstractSerializableTypes()
+      throws UnableToCompleteException, NotFoundException {
+
+    JClassType testServiceClass = typeOracle.getType(AbstractSerializableTypes.class.getName());
+    SerializableTypeOracleBuilder stob = new SerializableTypeOracleBuilder(
+        logger, typeOracle);
+    try {
+      stob.build(propertyOracle, testServiceClass);
+      fail("Expected UnableToCompleteException");
+    } catch (UnableToCompleteException e) {
+      // Should get here
+    }
+  }
+}