1 /*
   2  * Copyright 2010 Google, Inc.  All Rights Reserved.
   3  * yamauchi@google.com (Hiroshi Yamauchi)
   4  */
   5 
   6 /*
   7  * @test
   8  * @bug 6921969
   9  * @summary Tests shorter long multiply sequences when the high 32 bits of long operands are known to be zero on x86_32
  10  * @run main/othervm -Xbatch -XX:-Inline -XX:CompileOnly=.testNormal,.testLeftOptimized,.testRightOptimized,.testOptimized,.testLeftOptimized_LoadUI2L,.testRightOptimized_LoadUI2L,.testOptimized_LoadUI2L TestMultiplyLongHiZero
  11  */
  12 
  13 // This test must run without any command line arguments.
  14 
  15 public class TestMultiplyLongHiZero {
  16 
  17   private static void check(long leftFactor, long rightFactor, long optimizedProduct, long constantProduct) {
  18     long normalProduct = leftFactor * rightFactor; // unaffected by the new optimization
  19     if (optimizedProduct != constantProduct || normalProduct != constantProduct) {
  20       throw new RuntimeException("Not all three products are equal: " +
  21                                  Long.toHexString(normalProduct) + ", " +
  22                                  Long.toHexString(optimizedProduct) + ", " +
  23                                  Long.toHexString(constantProduct));
  24     }
  25   }
  26 
  27   private static int initInt(String[] args, int v) {
  28     if (args.length > 0) {
  29       try {
  30         return Integer.valueOf(args[0]);
  31       } catch (NumberFormatException e) { }
  32     }
  33     return v;
  34   }
  35 
  36   private static final long mask32 = 0x00000000FFFFFFFFL;
  37 
  38   private static void testNormal(int leftFactor, int rightFactor, long constantProduct) {
  39     check((long) leftFactor,
  40           (long) rightFactor,
  41           (long) leftFactor * (long) rightFactor, // unaffected by the new optimization
  42           constantProduct);
  43   }
  44 
  45   private static void testLeftOptimized(int leftFactor, int rightFactor, long constantProduct) {
  46     check((leftFactor & mask32),
  47           (long) rightFactor,
  48           (leftFactor & mask32) * (long) rightFactor, // left factor optimized
  49           constantProduct);
  50   }
  51 
  52   private static void testRightOptimized(int leftFactor, int rightFactor, long constantProduct) {
  53     check((long) leftFactor,
  54           (rightFactor & mask32),
  55           (long) leftFactor * (rightFactor & mask32), // right factor optimized
  56           constantProduct);
  57   }
  58 
  59   private static void testOptimized(int leftFactor, int rightFactor, long constantProduct) {
  60     check((leftFactor & mask32),
  61           (rightFactor & mask32),
  62           (leftFactor & mask32) * (rightFactor & mask32), // both factors optimized
  63           constantProduct);
  64   }
  65 
  66   private static void testLeftOptimized_LoadUI2L(int leftFactor, int rightFactor, long constantProduct, int[] factors) {
  67     check((leftFactor & mask32),
  68           (long) rightFactor,
  69           (factors[0] & mask32) * (long) rightFactor, // left factor optimized
  70           constantProduct);
  71   }
  72 
  73   private static void testRightOptimized_LoadUI2L(int leftFactor, int rightFactor, long constantProduct, int[] factors) {
  74     check((long) leftFactor,
  75           (rightFactor & mask32),
  76           (long) leftFactor * (factors[1] & mask32), // right factor optimized
  77           constantProduct);
  78   }
  79 
  80   private static void testOptimized_LoadUI2L(int leftFactor, int rightFactor, long constantProduct, int[] factors) {
  81     check((leftFactor & mask32),
  82           (rightFactor & mask32),
  83           (factors[0] & mask32) * (factors[1] & mask32), // both factors optimized
  84           constantProduct);
  85   }
  86 
  87   private static void test(int leftFactor, int rightFactor,
  88                            long normalConstantProduct,
  89                            long leftOptimizedConstantProduct,
  90                            long rightOptimizedConstantProduct,
  91                            long optimizedConstantProduct) {
  92     int[] factors = new int[2];
  93     factors[0] = leftFactor;
  94     factors[1] = rightFactor;
  95     testNormal(leftFactor, rightFactor, normalConstantProduct);
  96     testLeftOptimized(leftFactor, rightFactor, leftOptimizedConstantProduct);
  97     testRightOptimized(leftFactor, rightFactor, rightOptimizedConstantProduct);
  98     testOptimized(leftFactor, rightFactor, optimizedConstantProduct);
  99     testLeftOptimized_LoadUI2L(leftFactor, rightFactor, leftOptimizedConstantProduct, factors);
 100     testRightOptimized_LoadUI2L(leftFactor, rightFactor, rightOptimizedConstantProduct, factors);
 101     testOptimized_LoadUI2L(leftFactor, rightFactor, optimizedConstantProduct, factors);
 102   }
 103 
 104   public static void main(String[] args) {
 105     for (int i = 0; i < 100000; ++i) { // Trigger compilation
 106       int i0 = initInt(args, 1);
 107       int i1 = initInt(args, 3);
 108       int i2 = initInt(args, -1);
 109       int i3 = initInt(args, 0x7FFFFFFF);
 110       test(i0, i1, 3L, 3L, 3L, 3L);
 111       test(i0, i2, -1L, -1L, 0xFFFFFFFFL, 0xFFFFFFFFL);
 112       test(i0, i3, 0x7FFFFFFFL, 0x7FFFFFFFL, 0x7FFFFFFFL, 0x7FFFFFFFL);
 113       test(i1, i2, -3L, -3L, 0x2FFFFFFFDL, 0x2FFFFFFFDL);
 114       test(i1, i3, 0x17FFFFFFDL, 0x17FFFFFFDL, 0x17FFFFFFDL, 0x17FFFFFFDL);
 115       test(i2, i3, 0xFFFFFFFF80000001L, 0x7FFFFFFE80000001L,
 116            0xFFFFFFFF80000001L, 0x7FFFFFFE80000001L);
 117     }
 118   }
 119 }