1dbbac8f812a866b1b53f3007721f66038d208549Aart Bik/*
2dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * Copyright (C) 2017 The Android Open Source Project
3dbbac8f812a866b1b53f3007721f66038d208549Aart Bik *
4dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * Licensed under the Apache License, Version 2.0 (the "License");
5dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * you may not use this file except in compliance with the License.
6dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * You may obtain a copy of the License at
7dbbac8f812a866b1b53f3007721f66038d208549Aart Bik *
8dbbac8f812a866b1b53f3007721f66038d208549Aart Bik *      http://www.apache.org/licenses/LICENSE-2.0
9dbbac8f812a866b1b53f3007721f66038d208549Aart Bik *
10dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * Unless required by applicable law or agreed to in writing, software
11dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * distributed under the License is distributed on an "AS IS" BASIS,
12dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * See the License for the specific language governing permissions and
14dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * limitations under the License.
15dbbac8f812a866b1b53f3007721f66038d208549Aart Bik */
16dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
17dbbac8f812a866b1b53f3007721f66038d208549Aart Bik/**
18dbbac8f812a866b1b53f3007721f66038d208549Aart Bik * Tests for SAD (sum of absolute differences).
19dbbac8f812a866b1b53f3007721f66038d208549Aart Bik */
20dbbac8f812a866b1b53f3007721f66038d208549Aart Bikpublic class Main {
21dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
22dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  // TODO: lower precision still coming, b/64091002
23dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
24dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  // TODO: consider unsigned SAD too, b/64091002
25dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
2668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static char sadChar2Char(char[] s1, char[] s2) {
27dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
28dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char sad = 0;
29dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
30dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += Math.abs(s1[i] - s2[i]);
31dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
32dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
33dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
34dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
3568ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static char sadChar2CharAlt(char[] s1, char[] s2) {
36dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
37dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char sad = 0;
38dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
39dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char s = s1[i];
40dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char p = s2[i];
41dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += s >= p ? s - p : p - s;
42dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
43dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
44dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
45dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
4668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static char sadChar2CharAlt2(char[] s1, char[] s2) {
47dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
48dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char sad = 0;
49dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
50dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char s = s1[i];
51dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char p = s2[i];
52dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      int x = s - p;
53dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      if (x < 0) x = -x;
54dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += x;
55dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
56dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
57dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
58dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
5968ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  /// CHECK-START: int Main.sadChar2Int(char[], char[]) loop_optimization (before)
60dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons0:i\d+>>  IntConstant 0                  loop:none
61dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons1:i\d+>>  IntConstant 1                  loop:none
62dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi1:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop:B\d+>> outer_loop:none
63dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi2:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop>>      outer_loop:none
64dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get1:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
65dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get2:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
66dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Sub:i\d+>>    Sub [<<Get1>>,<<Get2>>]        loop:<<Loop>>      outer_loop:none
67dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Intrin:i\d+>> InvokeStaticOrDirect [<<Sub>>] intrinsic:MathAbsInt loop:<<Loop>> outer_loop:none
68dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi2>>,<<Intrin>>]      loop:<<Loop>>      outer_loop:none
69dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi1>>,<<Cons1>>]       loop:<<Loop>>      outer_loop:none
70dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  //
7138e380b3c5139c0993495a7a0f040bfe8aa1e9e9Lena Djokic  /// CHECK-START: int Main.sadChar2Int(char[], char[]) loop_optimization (after)
72dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-NOT: VecSADAccumulate
7368ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static int sadChar2Int(char[] s1, char[] s2) {
74dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
75dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int sad = 0;
76dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
77dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += Math.abs(s1[i] - s2[i]);
78dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
79dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
80dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
81dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
8268ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  /// CHECK-START: int Main.sadChar2IntAlt(char[], char[]) loop_optimization (before)
83dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons0:i\d+>>  IntConstant 0                  loop:none
84dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons1:i\d+>>  IntConstant 1                  loop:none
85dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi1:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop:B\d+>> outer_loop:none
86dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi2:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop>>      outer_loop:none
87dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get1:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
88dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get2:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
89dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Sub:i\d+>>    Sub [<<Get2>>,<<Get1>>]        loop:<<Loop>>      outer_loop:none
90dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Intrin:i\d+>> InvokeStaticOrDirect [<<Sub>>] intrinsic:MathAbsInt loop:<<Loop>> outer_loop:none
91dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi2>>,<<Intrin>>]      loop:<<Loop>>      outer_loop:none
92dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi1>>,<<Cons1>>]       loop:<<Loop>>      outer_loop:none
93dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  //
9438e380b3c5139c0993495a7a0f040bfe8aa1e9e9Lena Djokic  /// CHECK-START: int Main.sadChar2IntAlt(char[], char[]) loop_optimization (after)
95dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-NOT: VecSADAccumulate
9668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static int sadChar2IntAlt(char[] s1, char[] s2) {
97dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
98dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int sad = 0;
99dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
100dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char s = s1[i];
101dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char p = s2[i];
102dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += s >= p ? s - p : p - s;
103dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
104dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
105dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
106dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
10768ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  /// CHECK-START: int Main.sadChar2IntAlt2(char[], char[]) loop_optimization (before)
108dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons0:i\d+>>  IntConstant 0                  loop:none
109dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons1:i\d+>>  IntConstant 1                  loop:none
110dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi1:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop:B\d+>> outer_loop:none
111dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi2:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop>>      outer_loop:none
112dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get1:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
113dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get2:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
114dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Sub:i\d+>>    Sub [<<Get1>>,<<Get2>>]        loop:<<Loop>>      outer_loop:none
115dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Intrin:i\d+>> InvokeStaticOrDirect [<<Sub>>] intrinsic:MathAbsInt loop:<<Loop>> outer_loop:none
116dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi2>>,<<Intrin>>]      loop:<<Loop>>      outer_loop:none
117dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi1>>,<<Cons1>>]       loop:<<Loop>>      outer_loop:none
118dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  //
11938e380b3c5139c0993495a7a0f040bfe8aa1e9e9Lena Djokic  /// CHECK-START: int Main.sadChar2IntAlt2(char[], char[]) loop_optimization (after)
120dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-NOT: VecSADAccumulate
12168ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static int sadChar2IntAlt2(char[] s1, char[] s2) {
122dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
123dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int sad = 0;
124dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
125dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char s = s1[i];
126dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      char p = s2[i];
127dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      int x = s - p;
128dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      if (x < 0) x = -x;
129dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += x;
130dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
131dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
132dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
133dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
13468ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  /// CHECK-START: long Main.sadChar2Long(char[], char[]) loop_optimization (before)
135dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons0:i\d+>>  IntConstant 0                  loop:none
136dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons1:i\d+>>  IntConstant 1                  loop:none
137dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<ConsL:j\d+>>  LongConstant 0                 loop:none
138dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi1:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop:B\d+>> outer_loop:none
139dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi2:j\d+>>   Phi [<<ConsL>>,{{j\d+}}]       loop:<<Loop>>      outer_loop:none
140dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get1:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
141dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get2:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
142dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cnv1:j\d+>>   TypeConversion [<<Get1>>]      loop:<<Loop>>      outer_loop:none
143dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cnv2:j\d+>>   TypeConversion [<<Get2>>]      loop:<<Loop>>      outer_loop:none
144dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Sub:j\d+>>    Sub [<<Cnv1>>,<<Cnv2>>]        loop:<<Loop>>      outer_loop:none
145dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Intrin:j\d+>> InvokeStaticOrDirect [<<Sub>>] intrinsic:MathAbsLong loop:<<Loop>> outer_loop:none
146dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi2>>,<<Intrin>>]      loop:<<Loop>>      outer_loop:none
147dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi1>>,<<Cons1>>]       loop:<<Loop>>      outer_loop:none
148dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  //
14938e380b3c5139c0993495a7a0f040bfe8aa1e9e9Lena Djokic  /// CHECK-START: long Main.sadChar2Long(char[], char[]) loop_optimization (after)
150dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-NOT: VecSADAccumulate
15168ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static long sadChar2Long(char[] s1, char[] s2) {
152dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
153dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    long sad = 0;
154dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
155dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      long x = s1[i];
156dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      long y = s2[i];
157dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += Math.abs(x - y);
158dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
159dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
160dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
161dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
16268ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  /// CHECK-START: long Main.sadChar2LongAt1(char[], char[]) loop_optimization (before)
163dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons0:i\d+>>  IntConstant 0                  loop:none
164dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cons1:i\d+>>  IntConstant 1                  loop:none
165dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<ConsL:j\d+>>  LongConstant 1                 loop:none
166dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi1:i\d+>>   Phi [<<Cons0>>,{{i\d+}}]       loop:<<Loop:B\d+>> outer_loop:none
167dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Phi2:j\d+>>   Phi [<<ConsL>>,{{j\d+}}]       loop:<<Loop>>      outer_loop:none
168dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get1:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
169dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Get2:c\d+>>   ArrayGet [{{l\d+}},<<Phi1>>]   loop:<<Loop>>      outer_loop:none
170dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cnv1:j\d+>>   TypeConversion [<<Get1>>]      loop:<<Loop>>      outer_loop:none
171dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Cnv2:j\d+>>   TypeConversion [<<Get2>>]      loop:<<Loop>>      outer_loop:none
172dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Sub:j\d+>>    Sub [<<Cnv1>>,<<Cnv2>>]        loop:<<Loop>>      outer_loop:none
173dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG: <<Intrin:j\d+>> InvokeStaticOrDirect [<<Sub>>] intrinsic:MathAbsLong loop:<<Loop>> outer_loop:none
174dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi2>>,<<Intrin>>]      loop:<<Loop>>      outer_loop:none
175dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-DAG:                 Add [<<Phi1>>,<<Cons1>>]       loop:<<Loop>>      outer_loop:none
176dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  //
17738e380b3c5139c0993495a7a0f040bfe8aa1e9e9Lena Djokic  /// CHECK-START: long Main.sadChar2LongAt1(char[], char[]) loop_optimization (after)
178dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  /// CHECK-NOT: VecSADAccumulate
17968ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik  private static long sadChar2LongAt1(char[] s1, char[] s2) {
180dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int min_length = Math.min(s1.length, s2.length);
181dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    long sad = 1;  // starts at 1
182dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < min_length; i++) {
183dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      long x = s1[i];
184dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      long y = s2[i];
185dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      sad += Math.abs(x - y);
186dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
187dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    return sad;
188dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
189dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
190dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  public static void main(String[] args) {
191dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    // Cross-test the two most extreme values individually.
192dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char[] s1 = { 0, 0x8000, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
193dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char[] s2 = { 0, 0x7fff, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
19468ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2Char(s1, s2));
19568ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2Char(s2, s1));
19668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2CharAlt(s1, s2));
19768ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2CharAlt(s2, s1));
19868ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2CharAlt2(s1, s2));
19968ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2CharAlt2(s2, s1));
20068ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2Int(s1, s2));
20168ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2Int(s2, s1));
20268ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2IntAlt(s1, s2));
20368ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2IntAlt(s2, s1));
20468ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2IntAlt2(s1, s2));
20568ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1, sadChar2IntAlt2(s2, s1));
20668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1L, sadChar2Long(s1, s2));
20768ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1L, sadChar2Long(s2, s1));
20868ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(2L, sadChar2LongAt1(s1, s2));
20968ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(2L, sadChar2LongAt1(s2, s1));
210dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
211dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    // Use cross-values to test all cases.
212dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    char[] interesting = {
213dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x0000,
214dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x0001,
215dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x0002,
216dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x1234,
217dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x8000,
218dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x8001,
219dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0x7fff,
220dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      (char) 0xffff
221dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    };
222dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int n = interesting.length;
223dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int m = n * n + 1;
224dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    s1 = new char[m];
225dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    s2 = new char[m];
226dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    int k = 0;
227dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    for (int i = 0; i < n; i++) {
228dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      for (int j = 0; j < n; j++) {
229dbbac8f812a866b1b53f3007721f66038d208549Aart Bik        s1[k] = interesting[i];
230dbbac8f812a866b1b53f3007721f66038d208549Aart Bik        s2[k] = interesting[j];
231dbbac8f812a866b1b53f3007721f66038d208549Aart Bik        k++;
232dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      }
233dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
234dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    s1[k] = 10;
235dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    s2[k] = 2;
23668ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(56196, sadChar2Char(s1, s2));
23768ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(56196, sadChar2CharAlt(s1, s2));
23868ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(56196, sadChar2CharAlt2(s1, s2));
23968ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1497988, sadChar2Int(s1, s2));
24068ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1497988, sadChar2IntAlt(s1, s2));
24168ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1497988, sadChar2IntAlt2(s1, s2));
24268ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1497988L, sadChar2Long(s1, s2));
24368ca702c800d40b3e1f9aecdb6d5385b3492fda1Aart Bik    expectEquals(1497989L, sadChar2LongAt1(s1, s2));
244dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
245dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    System.out.println("passed");
246dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
247dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
248dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  private static void expectEquals(int expected, int result) {
249dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    if (expected != result) {
250dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      throw new Error("Expected: " + expected + ", found: " + result);
251dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
252dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
253dbbac8f812a866b1b53f3007721f66038d208549Aart Bik
254dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  private static void expectEquals(long expected, long result) {
255dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    if (expected != result) {
256dbbac8f812a866b1b53f3007721f66038d208549Aart Bik      throw new Error("Expected: " + expected + ", found: " + result);
257dbbac8f812a866b1b53f3007721f66038d208549Aart Bik    }
258dbbac8f812a866b1b53f3007721f66038d208549Aart Bik  }
259dbbac8f812a866b1b53f3007721f66038d208549Aart Bik}
260