Home | History | Annotate | Download | only in src
      1 /*
      2  * Copyright (C) 2016 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 public class Main {
     18 
     19   // TODO: make something like this work when b/26700769 is done.
     20   // CHECK-START-X86_64: int Main.bits32(int) disassembly (after)
     21   // CHECK-DAG: popcnt
     22 
     23 
     24   /// CHECK-START: int Main.$noinline$BitCountBoolean(boolean) intrinsics_recognition (after)
     25   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:IntegerBitCount
     26   /// CHECK-DAG:                      Return [<<Result>>]
     27   private static int $noinline$BitCountBoolean(boolean x) {
     28     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     29     return Integer.bitCount(x ? 1 : 0);
     30   }
     31 
     32   /// CHECK-START: int Main.$noinline$BitCountByte(byte) intrinsics_recognition (after)
     33   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:IntegerBitCount
     34   /// CHECK-DAG:                      Return [<<Result>>]
     35   private static int $noinline$BitCountByte(byte x) {
     36     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     37     return Integer.bitCount(x);
     38   }
     39 
     40   /// CHECK-START: int Main.$noinline$BitCountShort(short) intrinsics_recognition (after)
     41   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:IntegerBitCount
     42   /// CHECK-DAG:                      Return [<<Result>>]
     43   private static int $noinline$BitCountShort(short x) {
     44     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     45     return Integer.bitCount(x);
     46   }
     47 
     48   /// CHECK-START: int Main.$noinline$BitCountChar(char) intrinsics_recognition (after)
     49   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:IntegerBitCount
     50   /// CHECK-DAG:                      Return [<<Result>>]
     51   private static int $noinline$BitCountChar(char x) {
     52     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     53     return Integer.bitCount(x);
     54   }
     55 
     56   /// CHECK-START: int Main.$noinline$BitCountInt(int) intrinsics_recognition (after)
     57   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:IntegerBitCount
     58   /// CHECK-DAG:                      Return [<<Result>>]
     59   private static int $noinline$BitCountInt(int x) {
     60     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     61     return Integer.bitCount(x);
     62   }
     63 
     64   /// CHECK-START: int Main.$noinline$BitCountLong(long) intrinsics_recognition (after)
     65   /// CHECK-DAG:     <<Result:i\d+>>  InvokeStaticOrDirect intrinsic:LongBitCount
     66   /// CHECK-DAG:                      Return [<<Result>>]
     67   private static int $noinline$BitCountLong(long x) {
     68     if (doThrow) { throw new Error(); }  // Try defeating inlining.
     69     return Long.bitCount(x);
     70   }
     71 
     72   public static void testBitCountBoolean() {
     73     expectEqualsInt($noinline$BitCountBoolean(false), 0);
     74     expectEqualsInt($noinline$BitCountBoolean(true), 1);
     75   }
     76 
     77   public static void testBitCountByte() {
     78     // Number of bits in an 32-bit integer representing the sign
     79     // extension of a byte value widened to an int.
     80     int signExtensionSize = Integer.SIZE - Byte.SIZE;
     81     // Sign bit position in a byte.
     82     int signBit = Byte.SIZE - 1;
     83 
     84     expectEqualsInt($noinline$BitCountByte((byte) 0x00), 0);
     85     expectEqualsInt($noinline$BitCountByte((byte) 0x01), 1);
     86     expectEqualsInt($noinline$BitCountByte((byte) 0x10), 1);
     87     expectEqualsInt($noinline$BitCountByte((byte) 0x11), 2);
     88     expectEqualsInt($noinline$BitCountByte((byte) 0x03), 2);
     89     expectEqualsInt($noinline$BitCountByte((byte) 0x70), 3);
     90     expectEqualsInt($noinline$BitCountByte((byte) 0xF0), 4 + signExtensionSize);
     91     expectEqualsInt($noinline$BitCountByte((byte) 0x0F), 4);
     92     expectEqualsInt($noinline$BitCountByte((byte) 0x12), 2);
     93     expectEqualsInt($noinline$BitCountByte((byte) 0x9A), 4 + signExtensionSize);
     94     expectEqualsInt($noinline$BitCountByte((byte) 0xFF), 8 + signExtensionSize);
     95 
     96     for (int i = 0; i < Byte.SIZE; i++) {
     97       expectEqualsInt($noinline$BitCountByte((byte) (1 << i)),
     98                       (i < signBit) ? 1 : 1 + signExtensionSize);
     99     }
    100   }
    101 
    102   public static void testBitCountShort() {
    103     // Number of bits in an 32-bit integer representing the sign
    104     // extension of a short value widened to an int.
    105     int signExtensionSize = Integer.SIZE - Short.SIZE;
    106     // Sign bit position in a short.
    107     int signBit = Short.SIZE - 1;
    108 
    109     expectEqualsInt($noinline$BitCountShort((short) 0x0000), 0);
    110     expectEqualsInt($noinline$BitCountShort((short) 0x0001), 1);
    111     expectEqualsInt($noinline$BitCountShort((short) 0x1000), 1);
    112     expectEqualsInt($noinline$BitCountShort((short) 0x1001), 2);
    113     expectEqualsInt($noinline$BitCountShort((short) 0x0003), 2);
    114     expectEqualsInt($noinline$BitCountShort((short) 0x7000), 3);
    115     expectEqualsInt($noinline$BitCountShort((short) 0x0F00), 4);
    116     expectEqualsInt($noinline$BitCountShort((short) 0x0011), 2);
    117     expectEqualsInt($noinline$BitCountShort((short) 0x1100), 2);
    118     expectEqualsInt($noinline$BitCountShort((short) 0x1111), 4);
    119     expectEqualsInt($noinline$BitCountShort((short) 0x1234), 5);
    120     expectEqualsInt($noinline$BitCountShort((short) 0x9ABC), 9 + signExtensionSize);
    121     expectEqualsInt($noinline$BitCountShort((short) 0xFFFF), 16 + signExtensionSize);
    122 
    123     for (int i = 0; i < Short.SIZE; i++) {
    124       expectEqualsInt($noinline$BitCountShort((short) (1 << i)),
    125                       (i < signBit) ? 1 : 1 + signExtensionSize);
    126     }
    127   }
    128 
    129   public static void testBitCountChar() {
    130     expectEqualsInt($noinline$BitCountChar((char) 0x0000), 0);
    131     expectEqualsInt($noinline$BitCountChar((char) 0x0001), 1);
    132     expectEqualsInt($noinline$BitCountChar((char) 0x1000), 1);
    133     expectEqualsInt($noinline$BitCountChar((char) 0x1001), 2);
    134     expectEqualsInt($noinline$BitCountChar((char) 0x0003), 2);
    135     expectEqualsInt($noinline$BitCountChar((char) 0x7000), 3);
    136     expectEqualsInt($noinline$BitCountChar((char) 0x0F00), 4);
    137     expectEqualsInt($noinline$BitCountChar((char) 0x0011), 2);
    138     expectEqualsInt($noinline$BitCountChar((char) 0x1100), 2);
    139     expectEqualsInt($noinline$BitCountChar((char) 0x1111), 4);
    140     expectEqualsInt($noinline$BitCountChar((char) 0x1234), 5);
    141     expectEqualsInt($noinline$BitCountChar((char) 0x9ABC), 9);
    142     expectEqualsInt($noinline$BitCountChar((char) 0xFFFF), 16);
    143 
    144     for (int i = 0; i < Character.SIZE; i++) {
    145       expectEqualsInt($noinline$BitCountChar((char) (1 << i)), 1);
    146     }
    147   }
    148 
    149   public static void testBitCountInt() {
    150     expectEqualsInt($noinline$BitCountInt(0x00000000), 0);
    151     expectEqualsInt($noinline$BitCountInt(0x00000001), 1);
    152     expectEqualsInt($noinline$BitCountInt(0x10000000), 1);
    153     expectEqualsInt($noinline$BitCountInt(0x10000001), 2);
    154     expectEqualsInt($noinline$BitCountInt(0x00000003), 2);
    155     expectEqualsInt($noinline$BitCountInt(0x70000000), 3);
    156     expectEqualsInt($noinline$BitCountInt(0x000F0000), 4);
    157     expectEqualsInt($noinline$BitCountInt(0x00001111), 4);
    158     expectEqualsInt($noinline$BitCountInt(0x11110000), 4);
    159     expectEqualsInt($noinline$BitCountInt(0x11111111), 8);
    160     expectEqualsInt($noinline$BitCountInt(0x12345678), 13);
    161     expectEqualsInt($noinline$BitCountInt(0x9ABCDEF0), 19);
    162     expectEqualsInt($noinline$BitCountInt(0xFFFFFFFF), 32);
    163 
    164     for (int i = 0; i < Integer.SIZE; i++) {
    165       expectEqualsInt($noinline$BitCountInt(1 << i), 1);
    166     }
    167   }
    168 
    169   public static void testBitCountLong() {
    170     expectEqualsInt($noinline$BitCountLong(0x0000000000000000L), 0);
    171     expectEqualsInt($noinline$BitCountLong(0x0000000000000001L), 1);
    172     expectEqualsInt($noinline$BitCountLong(0x1000000000000000L), 1);
    173     expectEqualsInt($noinline$BitCountLong(0x1000000000000001L), 2);
    174     expectEqualsInt($noinline$BitCountLong(0x0000000000000003L), 2);
    175     expectEqualsInt($noinline$BitCountLong(0x7000000000000000L), 3);
    176     expectEqualsInt($noinline$BitCountLong(0x000F000000000000L), 4);
    177     expectEqualsInt($noinline$BitCountLong(0x0000000011111111L), 8);
    178     expectEqualsInt($noinline$BitCountLong(0x1111111100000000L), 8);
    179     expectEqualsInt($noinline$BitCountLong(0x1111111111111111L), 16);
    180     expectEqualsInt($noinline$BitCountLong(0x123456789ABCDEF1L), 33);
    181     expectEqualsInt($noinline$BitCountLong(0xFFFFFFFFFFFFFFFFL), 64);
    182 
    183     for (int i = 0; i < Long.SIZE; i++) {
    184       expectEqualsInt($noinline$BitCountLong(1L << i), 1);
    185     }
    186   }
    187 
    188   public static void main(String args[]) {
    189     testBitCountBoolean();
    190     testBitCountByte();
    191     testBitCountShort();
    192     testBitCountChar();
    193     testBitCountInt();
    194     testBitCountLong();
    195 
    196     System.out.println("passed");
    197   }
    198 
    199   private static void expectEqualsInt(int expected, int result) {
    200     if (expected != result) {
    201       throw new Error("Expected: " + expected + ", found: " + result);
    202     }
    203   }
    204 
    205   private static boolean doThrow = false;
    206 }
    207