993 } 994 995 if (array->is_loaded_flattened_array()) { 996 ciType* array_type = array->declared_type(); 997 ciValueKlass* elem_klass = array_type->as_value_array_klass()->element_klass()->as_value_klass(); 998 NewValueTypeInstance* new_instance = new NewValueTypeInstance(elem_klass, state_before, false); 999 _memory->new_instance(new_instance); 1000 apush(append_split(new_instance)); 1001 LoadIndexed* load_indexed = new LoadIndexed(array, index, length, type, state_before); 1002 load_indexed->set_vt(new_instance); 1003 append(load_indexed); 1004 } else { 1005 push(as_ValueType(type), append(new LoadIndexed(array, index, length, type, state_before))); 1006 } 1007 } 1008 1009 1010 void GraphBuilder::store_indexed(BasicType type) { 1011 // In case of in block code motion in range check elimination 1012 ValueStack* state_before = copy_state_indexed_access(); 1013 ValueStack* deopt_state = copy_state_before(); 1014 compilation()->set_has_access_indexed(true); 1015 Value value = pop(as_ValueType(type)); 1016 Value index = ipop(); 1017 Value array = apop(); 1018 Value length = NULL; 1019 if (CSEArrayLength || 1020 (array->as_AccessField() && array->as_AccessField()->field()->is_constant()) || 1021 (array->as_NewArray() && array->as_NewArray()->length() && array->as_NewArray()->length()->type()->is_constant())) { 1022 length = append(new ArrayLength(array, state_before)); 1023 } 1024 ciType* array_type = array->declared_type(); 1025 bool check_boolean = false; 1026 if (array_type != NULL) { 1027 if (array_type->is_loaded() && 1028 array_type->as_array_klass()->element_type()->basic_type() == T_BOOLEAN) { 1029 assert(type == T_BYTE, "boolean store uses bastore"); 1030 Value mask = append(new Constant(new IntConstant(1))); 1031 value = append(new LogicOp(Bytecodes::_iand, value, mask)); 1032 } 1033 } else if (type == T_BYTE) { 1034 check_boolean = true; 1035 } 1036 1037 if (array->is_flattened_array() && !array_type->is_loaded()) { 1038 // Value array access may be deoptimized. Need full "before" states. 1039 state_before = deopt_state; 1040 } 1041 StoreIndexed* result = new StoreIndexed(array, index, length, type, value, state_before, check_boolean); 1042 append(result); 1043 _memory->store_value(value); 1044 1045 if (type == T_OBJECT && is_profiling()) { 1046 // Note that we'd collect profile data in this method if we wanted it. 1047 compilation()->set_would_profile(true); 1048 1049 if (profile_checkcasts()) { 1050 result->set_profiled_method(method()); 1051 result->set_profiled_bci(bci()); 1052 result->set_should_profile(true); 1053 } 1054 } 1055 } 1056 1057 1058 void GraphBuilder::stack_op(Bytecodes::Code code) { 1059 switch (code) { 1060 case Bytecodes::_pop: | 993 } 994 995 if (array->is_loaded_flattened_array()) { 996 ciType* array_type = array->declared_type(); 997 ciValueKlass* elem_klass = array_type->as_value_array_klass()->element_klass()->as_value_klass(); 998 NewValueTypeInstance* new_instance = new NewValueTypeInstance(elem_klass, state_before, false); 999 _memory->new_instance(new_instance); 1000 apush(append_split(new_instance)); 1001 LoadIndexed* load_indexed = new LoadIndexed(array, index, length, type, state_before); 1002 load_indexed->set_vt(new_instance); 1003 append(load_indexed); 1004 } else { 1005 push(as_ValueType(type), append(new LoadIndexed(array, index, length, type, state_before))); 1006 } 1007 } 1008 1009 1010 void GraphBuilder::store_indexed(BasicType type) { 1011 // In case of in block code motion in range check elimination 1012 ValueStack* state_before = copy_state_indexed_access(); 1013 compilation()->set_has_access_indexed(true); 1014 Value value = pop(as_ValueType(type)); 1015 Value index = ipop(); 1016 Value array = apop(); 1017 Value length = NULL; 1018 if (CSEArrayLength || 1019 (array->as_AccessField() && array->as_AccessField()->field()->is_constant()) || 1020 (array->as_NewArray() && array->as_NewArray()->length() && array->as_NewArray()->length()->type()->is_constant())) { 1021 length = append(new ArrayLength(array, state_before)); 1022 } 1023 ciType* array_type = array->declared_type(); 1024 bool check_boolean = false; 1025 if (array_type != NULL) { 1026 if (array_type->is_loaded() && 1027 array_type->as_array_klass()->element_type()->basic_type() == T_BOOLEAN) { 1028 assert(type == T_BYTE, "boolean store uses bastore"); 1029 Value mask = append(new Constant(new IntConstant(1))); 1030 value = append(new LogicOp(Bytecodes::_iand, value, mask)); 1031 } 1032 } else if (type == T_BYTE) { 1033 check_boolean = true; 1034 } 1035 1036 StoreIndexed* result = new StoreIndexed(array, index, length, type, value, state_before, check_boolean); 1037 append(result); 1038 _memory->store_value(value); 1039 1040 if (type == T_OBJECT && is_profiling()) { 1041 // Note that we'd collect profile data in this method if we wanted it. 1042 compilation()->set_would_profile(true); 1043 1044 if (profile_checkcasts()) { 1045 result->set_profiled_method(method()); 1046 result->set_profiled_bci(bci()); 1047 result->set_should_profile(true); 1048 } 1049 } 1050 } 1051 1052 1053 void GraphBuilder::stack_op(Bytecodes::Code code) { 1054 switch (code) { 1055 case Bytecodes::_pop: |