13cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray/*
23cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * Copyright (C) 2015 The Android Open Source Project
33cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray *
43cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * Licensed under the Apache License, Version 2.0 (the "License");
53cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * you may not use this file except in compliance with the License.
63cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * You may obtain a copy of the License at
73cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray *
83cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray *      http://www.apache.org/licenses/LICENSE-2.0
93cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray *
103cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * Unless required by applicable law or agreed to in writing, software
113cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * distributed under the License is distributed on an "AS IS" BASIS,
123cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
133cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * See the License for the specific language governing permissions and
143cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray * limitations under the License.
153cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray */
163cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray
173cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffraypublic class Main {
183cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray  public static int foo(int start, int[] array) {
193cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    int result = 0;
203cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    // We will create HDeoptimize nodes for this first loop, and a phi
213cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    // for the array length which will only be used within the loop.
223cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    for (int i = start; i < 3; i++) {
233cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray      result += array[i];
243cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray      for (int j = 0; j < 2; ++j) {
253cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray        // The HBoundsCheck for this array access will be updated to access
263cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray        // the array length phi created for the deoptimization checks of the
273cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray        // first loop. This crashed the compiler which used to DCHECK an array
283cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray        // length in a bounds check cannot be a phi.
293cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray        result += array[j];
303cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray      }
313cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    }
323cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    return result;
333cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray  }
343cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray
358df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray  public static int bar(int start, int[] array) {
368df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    int result = 0;
378df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    for (int i = start; i < 3; i++) {
388df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray      result += array[i];
398df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray      for (int j = 0; j < 2; ++j) {
408df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        result += array[j];
418df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        // The following operations would lead to BCE wanting to add another
428df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        // deoptimization, but it crashed assuming the input of a `HBoundsCheck`
438df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        // must be a `HArrayLength`.
448df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        result += array[0];
458df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        result += array[1];
468df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray        result += array[2];
478df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray      }
488df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    }
498df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    return result;
508df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray  }
518df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray
523cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray  public static void main(String[] args) {
533cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    int[] a = new int[] { 1, 2, 3, 4, 5 };
543cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    int result = foo(1, a);
553cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    if (result != 11) {
563cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray      throw new Error("Got " + result + ", expected " + 11);
573cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray    }
588df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray
598df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    result = bar(1, a);
608df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    if (result != 35) {
618df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray      throw new Error("Got " + result + ", expected " + 35);
628df886b9214802ad689316a1dedb00a6d102555cNicolas Geoffray    }
633cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray  }
643cde6227678cf62e06bca264671d1e957456ac3dNicolas Geoffray}
65