OLD | NEW |
---|---|
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/code_generator.h" | 5 #include "vm/code_generator.h" |
6 | 6 |
7 #include "vm/assembler.h" | 7 #include "vm/assembler.h" |
8 #include "vm/ast.h" | 8 #include "vm/ast.h" |
9 #include "vm/bigint_operations.h" | 9 #include "vm/bigint_operations.h" |
10 #include "vm/code_patcher.h" | 10 #include "vm/code_patcher.h" |
(...skipping 1048 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1059 // time. | 1059 // time. |
1060 if (stack_pos < isolate->saved_stack_limit()) { | 1060 if (stack_pos < isolate->saved_stack_limit()) { |
1061 // Use the preallocated stack overflow exception to avoid calling | 1061 // Use the preallocated stack overflow exception to avoid calling |
1062 // into dart code. | 1062 // into dart code. |
1063 const Instance& exception = | 1063 const Instance& exception = |
1064 Instance::Handle(isolate->object_store()->stack_overflow()); | 1064 Instance::Handle(isolate->object_store()->stack_overflow()); |
1065 Exceptions::Throw(exception); | 1065 Exceptions::Throw(exception); |
1066 UNREACHABLE(); | 1066 UNREACHABLE(); |
1067 } | 1067 } |
1068 | 1068 |
1069 // The following code is used to stress test deoptimization and | |
1070 // debugger stack tracing. | |
1071 bool do_deopt = false; | |
1072 bool do_stacktrace = false; | |
1073 if (FLAG_deoptimize_every > 0 || | |
1074 FLAG_stacktrace_every > 0) { | |
srdjan
2014/05/20 18:13:32
This fits in one line, and add parentheses please.
Florian Schneider
2014/05/21 09:28:59
Done.
| |
1075 // TODO(turnidge): To make --deoptimize_every and | |
1076 // --stacktrace-every faster we could move this increment/test to | |
1077 // the generated code. | |
1078 int32_t count = isolate->IncrementAndGetStackOverflowCount(); | |
1079 if (FLAG_deoptimize_every > 0 && | |
1080 (count % FLAG_deoptimize_every) == 0) { | |
srdjan
2014/05/20 18:13:32
Add parantheses
| |
1081 do_deopt = true; | |
1082 } | |
1083 if (FLAG_stacktrace_every > 0 && | |
1084 (count % FLAG_stacktrace_every) == 0) { | |
srdjan
2014/05/20 18:13:32
ditto
| |
1085 do_stacktrace = true; | |
1086 } | |
1087 } | |
1088 if (FLAG_deoptimize_filter != NULL || | |
1089 FLAG_stacktrace_filter != NULL) { | |
srdjan
2014/05/20 18:13:32
ditto
| |
1090 DartFrameIterator iterator; | |
1091 StackFrame* frame = iterator.NextFrame(); | |
1092 ASSERT(frame != NULL); | |
1093 const Code& code = Code::Handle(frame->LookupDartCode()); | |
1094 ASSERT(!code.IsNull()); | |
1095 const Function& function = Function::Handle(code.function()); | |
1096 ASSERT(!function.IsNull()); | |
1097 const char* function_name = function.ToFullyQualifiedCString(); | |
1098 ASSERT(function_name != NULL); | |
1099 if (code.is_optimized() && | |
1100 FLAG_deoptimize_filter != NULL && | |
1101 strstr(function_name, FLAG_deoptimize_filter) != NULL) { | |
srdjan
2014/05/20 18:13:32
ditto
| |
1102 OS::PrintErr("*** Forcing deoptimization (%s)\n", | |
1103 function.ToFullyQualifiedCString()); | |
1104 do_deopt = true; | |
1105 } | |
1106 if (FLAG_stacktrace_filter != NULL && | |
1107 strstr(function_name, FLAG_stacktrace_filter) != NULL) { | |
srdjan
2014/05/20 18:13:32
ditto
| |
1108 OS::PrintErr("*** Computing stacktrace (%s)\n", | |
1109 function.ToFullyQualifiedCString()); | |
1110 do_stacktrace = true; | |
1111 } | |
1112 } | |
1113 if (do_deopt) { | |
1114 // TODO(turnidge): Consider using DeoptimizeAt instead. | |
1115 DeoptimizeAll(); | |
turnidge
2014/05/20 16:52:25
If I deoptimize here and then attempt to osr below
Florian Schneider
2014/05/21 09:28:59
Yes, I think so. The function triggering OSR is un
| |
1116 } | |
1117 if (do_stacktrace) { | |
1118 String& var_name = String::Handle(); | |
1119 Instance& var_value = Instance::Handle(); | |
1120 DebuggerStackTrace* stack = isolate->debugger()->StackTrace(); | |
1121 intptr_t num_frames = stack->Length(); | |
1122 for (intptr_t i = 0; i < num_frames; i++) { | |
1123 ActivationFrame* frame = stack->FrameAt(i); | |
1124 const int num_vars = frame->NumLocalVariables(); | |
1125 intptr_t unused; | |
1126 for (intptr_t v = 0; v < num_vars; v++) { | |
1127 frame->VariableAt(v, &var_name, &unused, &unused, &var_value); | |
1128 } | |
1129 } | |
1130 } | |
1131 | |
1069 uword interrupt_bits = isolate->GetAndClearInterrupts(); | 1132 uword interrupt_bits = isolate->GetAndClearInterrupts(); |
1070 if ((interrupt_bits & Isolate::kStoreBufferInterrupt) != 0) { | 1133 if ((interrupt_bits & Isolate::kStoreBufferInterrupt) != 0) { |
1071 if (FLAG_verbose_gc) { | 1134 if (FLAG_verbose_gc) { |
1072 OS::PrintErr("Scavenge scheduled by store buffer overflow.\n"); | 1135 OS::PrintErr("Scavenge scheduled by store buffer overflow.\n"); |
1073 } | 1136 } |
1074 isolate->heap()->CollectGarbage(Heap::kNew); | 1137 isolate->heap()->CollectGarbage(Heap::kNew); |
1075 } | 1138 } |
1076 if ((interrupt_bits & Isolate::kMessageInterrupt) != 0) { | 1139 if ((interrupt_bits & Isolate::kMessageInterrupt) != 0) { |
1077 isolate->message_handler()->HandleOOBMessages(); | 1140 isolate->message_handler()->HandleOOBMessages(); |
1078 } | 1141 } |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1137 if (optimized_code.raw() != original_code.raw()) { | 1200 if (optimized_code.raw() != original_code.raw()) { |
1138 // The OSR code does not work for calling the function, so restore the | 1201 // The OSR code does not work for calling the function, so restore the |
1139 // unoptimized code. Patch the stack frame to return into the OSR | 1202 // unoptimized code. Patch the stack frame to return into the OSR |
1140 // code. | 1203 // code. |
1141 uword optimized_entry = | 1204 uword optimized_entry = |
1142 Instructions::Handle(optimized_code.instructions()).EntryPoint(); | 1205 Instructions::Handle(optimized_code.instructions()).EntryPoint(); |
1143 function.AttachCode(original_code); | 1206 function.AttachCode(original_code); |
1144 frame->set_pc(optimized_entry); | 1207 frame->set_pc(optimized_entry); |
1145 } | 1208 } |
1146 } | 1209 } |
1147 | |
1148 // The following code is used to stress test deoptimization and | |
1149 // debugger stack tracing. | |
1150 bool do_deopt = false; | |
1151 bool do_stacktrace = false; | |
1152 if (FLAG_deoptimize_every > 0 || | |
1153 FLAG_stacktrace_every > 0) { | |
1154 // TODO(turnidge): To make --deoptimize_every and | |
1155 // --stacktrace-every faster we could move this increment/test to | |
1156 // the generated code. | |
1157 int32_t count = isolate->IncrementAndGetStackOverflowCount(); | |
1158 if (FLAG_deoptimize_every > 0 && | |
1159 (count % FLAG_deoptimize_every) == 0) { | |
1160 do_deopt = true; | |
1161 } | |
1162 if (FLAG_stacktrace_every > 0 && | |
1163 (count % FLAG_stacktrace_every) == 0) { | |
1164 do_stacktrace = true; | |
1165 } | |
1166 } | |
1167 if (FLAG_deoptimize_filter != NULL || | |
1168 FLAG_stacktrace_filter != NULL) { | |
1169 DartFrameIterator iterator; | |
1170 StackFrame* frame = iterator.NextFrame(); | |
1171 ASSERT(frame != NULL); | |
1172 const Code& code = Code::Handle(frame->LookupDartCode()); | |
1173 ASSERT(!code.IsNull()); | |
1174 const Function& function = Function::Handle(code.function()); | |
1175 ASSERT(!function.IsNull()); | |
1176 const char* function_name = function.ToFullyQualifiedCString(); | |
1177 ASSERT(function_name != NULL); | |
1178 if (code.is_optimized() && | |
1179 FLAG_deoptimize_filter != NULL && | |
1180 strstr(function_name, FLAG_deoptimize_filter) != NULL) { | |
1181 OS::PrintErr("*** Forcing deoptimization (%s)\n", | |
1182 function.ToFullyQualifiedCString()); | |
1183 do_deopt = true; | |
1184 } | |
1185 if (FLAG_stacktrace_filter != NULL && | |
1186 strstr(function_name, FLAG_stacktrace_filter) != NULL) { | |
1187 OS::PrintErr("*** Computing stacktrace (%s)\n", | |
1188 function.ToFullyQualifiedCString()); | |
1189 do_stacktrace = true; | |
1190 } | |
1191 } | |
1192 if (do_deopt) { | |
1193 // TODO(turnidge): Consider using DeoptimizeAt instead. | |
1194 DeoptimizeAll(); | |
1195 } | |
1196 if (do_stacktrace) { | |
1197 String& var_name = String::Handle(); | |
1198 Instance& var_value = Instance::Handle(); | |
1199 DebuggerStackTrace* stack = isolate->debugger()->StackTrace(); | |
1200 intptr_t num_frames = stack->Length(); | |
1201 for (intptr_t i = 0; i < num_frames; i++) { | |
1202 ActivationFrame* frame = stack->FrameAt(i); | |
1203 const int num_vars = frame->NumLocalVariables(); | |
1204 intptr_t unused; | |
1205 for (intptr_t v = 0; v < num_vars; v++) { | |
1206 frame->VariableAt(v, &var_name, &unused, &unused, &var_value); | |
1207 } | |
1208 } | |
1209 } | |
1210 } | 1210 } |
1211 | 1211 |
1212 | 1212 |
1213 DEFINE_RUNTIME_ENTRY(TraceICCall, 2) { | 1213 DEFINE_RUNTIME_ENTRY(TraceICCall, 2) { |
1214 const ICData& ic_data = ICData::CheckedHandle(arguments.ArgAt(0)); | 1214 const ICData& ic_data = ICData::CheckedHandle(arguments.ArgAt(0)); |
1215 const Function& function = Function::CheckedHandle(arguments.ArgAt(1)); | 1215 const Function& function = Function::CheckedHandle(arguments.ArgAt(1)); |
1216 DartFrameIterator iterator; | 1216 DartFrameIterator iterator; |
1217 StackFrame* frame = iterator.NextFrame(); | 1217 StackFrame* frame = iterator.NextFrame(); |
1218 ASSERT(frame != NULL); | 1218 ASSERT(frame != NULL); |
1219 OS::PrintErr("IC call @%#" Px ": ICData: %p cnt:%" Pd " nchecks: %" Pd | 1219 OS::PrintErr("IC call @%#" Px ": ICData: %p cnt:%" Pd " nchecks: %" Pd |
(...skipping 312 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1532 // of the given value. | 1532 // of the given value. |
1533 // Arg0: Field object; | 1533 // Arg0: Field object; |
1534 // Arg1: Value that is being stored. | 1534 // Arg1: Value that is being stored. |
1535 DEFINE_RUNTIME_ENTRY(UpdateFieldCid, 2) { | 1535 DEFINE_RUNTIME_ENTRY(UpdateFieldCid, 2) { |
1536 const Field& field = Field::CheckedHandle(arguments.ArgAt(0)); | 1536 const Field& field = Field::CheckedHandle(arguments.ArgAt(0)); |
1537 const Object& value = Object::Handle(arguments.ArgAt(1)); | 1537 const Object& value = Object::Handle(arguments.ArgAt(1)); |
1538 field.UpdateGuardedCidAndLength(value); | 1538 field.UpdateGuardedCidAndLength(value); |
1539 } | 1539 } |
1540 | 1540 |
1541 } // namespace dart | 1541 } // namespace dart |
OLD | NEW |