src/share/vm/c1/c1_GraphBuilder.cpp
Index
Unified diffs
Context diffs
Sdiffs
Patch
New
Old
Previous File
Next File
hotspot Cdiff src/share/vm/c1/c1_GraphBuilder.cpp
src/share/vm/c1/c1_GraphBuilder.cpp
Print this page
rev 5468 : 8026251: New type profiling points: parameters to methods
Summary: x86 interpreter and c1 type profiling for parameters on method entries
Reviewed-by:
*** 1468,1478 ****
// return value, if any, of the inlined method on operand stack.
int invoke_bci = state()->caller_state()->bci();
set_state(state()->caller_state()->copy_for_parsing());
if (x != NULL) {
state()->push(x->type(), x);
! if (profile_calls() && MethodData::profile_return() && x->type()->is_object_kind()) {
ciMethod* caller = state()->scope()->method();
ciMethodData* md = caller->method_data_or_null();
ciProfileData* data = md->bci_to_data(invoke_bci);
if (data->is_CallTypeData() || data->is_VirtualCallTypeData()) {
bool has_return = data->is_CallTypeData() ? ((ciCallTypeData*)data)->has_return() : ((ciVirtualCallTypeData*)data)->has_return();
--- 1468,1478 ----
// return value, if any, of the inlined method on operand stack.
int invoke_bci = state()->caller_state()->bci();
set_state(state()->caller_state()->copy_for_parsing());
if (x != NULL) {
state()->push(x->type(), x);
! if (profile_return() && x->type()->is_object_kind()) {
ciMethod* caller = state()->scope()->method();
ciMethodData* md = caller->method_data_or_null();
ciProfileData* data = md->bci_to_data(invoke_bci);
if (data->is_CallTypeData() || data->is_VirtualCallTypeData()) {
bool has_return = data->is_CallTypeData() ? ((ciCallTypeData*)data)->has_return() : ((ciVirtualCallTypeData*)data)->has_return();
*** 1670,1700 ****
assert(DeoptC1, "need debug information");
return compilation()->dependency_recorder();
}
// How many arguments do we want to profile?
! Values* GraphBuilder::args_list_for_profiling(int& start, bool may_have_receiver) {
int n = 0;
! assert(start == 0, "should be initialized");
! if (MethodData::profile_arguments()) {
ciProfileData* data = method()->method_data()->bci_to_data(bci());
if (data->is_CallTypeData() || data->is_VirtualCallTypeData()) {
n = data->is_CallTypeData() ? data->as_CallTypeData()->number_of_arguments() : data->as_VirtualCallTypeData()->number_of_arguments();
! bool has_receiver = may_have_receiver && Bytecodes::has_receiver(method()->java_code_at_bci(bci()));
! start = has_receiver ? 1 : 0;
}
}
if (n > 0) {
return new Values(n);
}
return NULL;
}
// Collect arguments that we want to profile in a list
! Values* GraphBuilder::collect_args_for_profiling(Values* args, bool may_have_receiver) {
int start = 0;
! Values* obj_args = args_list_for_profiling(start, may_have_receiver);
if (obj_args == NULL) {
return NULL;
}
int s = obj_args->size();
for (int i = start, j = 0; j < s; i++) {
--- 1670,1708 ----
assert(DeoptC1, "need debug information");
return compilation()->dependency_recorder();
}
// How many arguments do we want to profile?
! Values* GraphBuilder::args_list_for_profiling(ciMethod* target, int& start, bool may_have_receiver) {
int n = 0;
! bool has_receiver = may_have_receiver && Bytecodes::has_receiver(method()->java_code_at_bci(bci()));
! start = has_receiver ? 1 : 0;
! if (profile_arguments()) {
ciProfileData* data = method()->method_data()->bci_to_data(bci());
if (data->is_CallTypeData() || data->is_VirtualCallTypeData()) {
n = data->is_CallTypeData() ? data->as_CallTypeData()->number_of_arguments() : data->as_VirtualCallTypeData()->number_of_arguments();
! }
! }
! // If we are inlining then we need to collect arguments to profile parameters for the target
! if (profile_parameters() && target != NULL) {
! if (target->method_data() != NULL && target->method_data()->parameters_type_data() != NULL) {
! // The receiver is profiled on method entry so it's included in
! // the number of parameters but here we're only interested in
! // actual arguments.
! n = MAX2(n, target->method_data()->parameters_type_data()->number_of_parameters() - start);
}
}
if (n > 0) {
return new Values(n);
}
return NULL;
}
// Collect arguments that we want to profile in a list
! Values* GraphBuilder::collect_args_for_profiling(Values* args, ciMethod* target, bool may_have_receiver) {
int start = 0;
! Values* obj_args = args_list_for_profiling(target, start, may_have_receiver);
if (obj_args == NULL) {
return NULL;
}
int s = obj_args->size();
for (int i = start, j = 0; j < s; i++) {
*** 2004,2014 ****
if (cha_monomorphic_target != NULL) {
target_klass = cha_monomorphic_target->holder();
} else if (exact_target != NULL) {
target_klass = exact_target->holder();
}
! profile_call(target, recv, target_klass, collect_args_for_profiling(args, false), false);
}
}
Invoke* result = new Invoke(code, result_type, recv, args, vtable_index, target, state_before);
// push result
--- 2012,2022 ----
if (cha_monomorphic_target != NULL) {
target_klass = cha_monomorphic_target->holder();
} else if (exact_target != NULL) {
target_klass = exact_target->holder();
}
! profile_call(target, recv, target_klass, collect_args_for_profiling(args, NULL, false), false);
}
}
Invoke* result = new Invoke(code, result_type, recv, args, vtable_index, target, state_before);
// push result
*** 2019,2029 ****
push(result_type, round_fp(result));
} else {
push(result_type, result);
}
}
! if (profile_calls() && MethodData::profile_return() && result_type->is_object_kind()) {
profile_return_type(result, target);
}
}
--- 2027,2037 ----
push(result_type, round_fp(result));
} else {
push(result_type, result);
}
}
! if (profile_return() && result_type->is_object_kind()) {
profile_return_type(result, target);
}
}
*** 3559,3580 ****
Value recv = NULL;
if (has_receiver) {
recv = args->at(0);
null_check(recv);
}
! profile_call(callee, recv, NULL, collect_args_for_profiling(args, true), true);
}
}
}
Intrinsic* result = new Intrinsic(result_type, id, args, has_receiver, state_before,
preserves_state, cantrap);
// append instruction & push result
Value value = append_split(result);
if (result_type != voidType) push(result_type, value);
! if (callee != method() && profile_calls() && MethodData::profile_return() && result_type->is_object_kind()) {
profile_return_type(result, callee);
}
// done
return true;
--- 3567,3588 ----
Value recv = NULL;
if (has_receiver) {
recv = args->at(0);
null_check(recv);
}
! profile_call(callee, recv, NULL, collect_args_for_profiling(args, callee, true), true);
}
}
}
Intrinsic* result = new Intrinsic(result_type, id, args, has_receiver, state_before,
preserves_state, cantrap);
// append instruction & push result
Value value = append_split(result);
if (result_type != voidType) push(result_type, value);
! if (callee != method() && profile_return() && result_type->is_object_kind()) {
profile_return_type(result, callee);
}
// done
return true;
*** 3818,3828 ****
// this may be redundant here...
compilation()->set_would_profile(true);
if (profile_calls()) {
int start = 0;
! Values* obj_args = args_list_for_profiling(start, has_receiver);
if (obj_args != NULL) {
int s = obj_args->size();
// if called through method handle invoke, some arguments may have been popped
for (int i = args_base+start, j = 0; j < obj_args->size() && i < state()->stack_size(); ) {
Value v = state()->stack_at_inc(i);
--- 3826,3836 ----
// this may be redundant here...
compilation()->set_would_profile(true);
if (profile_calls()) {
int start = 0;
! Values* obj_args = args_list_for_profiling(callee, start, has_receiver);
if (obj_args != NULL) {
int s = obj_args->size();
// if called through method handle invoke, some arguments may have been popped
for (int i = args_base+start, j = 0; j < obj_args->size() && i < state()->stack_size(); ) {
Value v = state()->stack_at_inc(i);
src/share/vm/c1/c1_GraphBuilder.cpp
Index
Unified diffs
Context diffs
Sdiffs
Patch
New
Old
Previous File
Next File