| 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 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 47 DEFINE_FLAG(charp, optimization_filter, NULL, "Optimize only named function"); | 47 DEFINE_FLAG(charp, optimization_filter, NULL, "Optimize only named function"); |
| 48 DEFINE_FLAG(bool, trace_failed_optimization_attempts, false, | 48 DEFINE_FLAG(bool, trace_failed_optimization_attempts, false, |
| 49 "Traces all failed optimization attempts"); | 49 "Traces all failed optimization attempts"); |
| 50 DEFINE_FLAG(bool, trace_optimized_ic_calls, false, | 50 DEFINE_FLAG(bool, trace_optimized_ic_calls, false, |
| 51 "Trace IC calls in optimized code."); | 51 "Trace IC calls in optimized code."); |
| 52 DEFINE_FLAG(int, reoptimization_counter_threshold, 2000, | 52 DEFINE_FLAG(int, reoptimization_counter_threshold, 2000, |
| 53 "Counter threshold before a function gets reoptimized."); | 53 "Counter threshold before a function gets reoptimized."); |
| 54 DEFINE_FLAG(int, max_subtype_cache_entries, 100, | 54 DEFINE_FLAG(int, max_subtype_cache_entries, 100, |
| 55 "Maximum number of subtype cache entries (number of checks cached)."); | 55 "Maximum number of subtype cache entries (number of checks cached)."); |
| 56 | 56 |
| 57 #if defined(TARGET_ARCH_IA32) || defined(TARGET_ARCH_X64) |
| 58 DEFINE_FLAG(bool, use_osr, true, "Use on-stack replacement."); |
| 59 #else |
| 60 DEFINE_FLAG(bool, use_osr, false, "Use on-stack replacement."); |
| 61 #endif |
| 62 DEFINE_FLAG(bool, trace_osr, false, "Trace attempts at on-stack replacement."); |
| 63 |
| 57 | 64 |
| 58 DEFINE_RUNTIME_ENTRY(TraceFunctionEntry, 1) { | 65 DEFINE_RUNTIME_ENTRY(TraceFunctionEntry, 1) { |
| 59 ASSERT(arguments.ArgCount() == | 66 ASSERT(arguments.ArgCount() == |
| 60 kTraceFunctionEntryRuntimeEntry.argument_count()); | 67 kTraceFunctionEntryRuntimeEntry.argument_count()); |
| 61 const Function& function = Function::CheckedHandle(arguments.ArgAt(0)); | 68 const Function& function = Function::CheckedHandle(arguments.ArgAt(0)); |
| 62 const String& function_name = String::Handle(function.name()); | 69 const String& function_name = String::Handle(function.name()); |
| 63 const String& class_name = | 70 const String& class_name = |
| 64 String::Handle(Class::Handle(function.Owner()).Name()); | 71 String::Handle(Class::Handle(function.Owner()).Name()); |
| 65 OS::PrintErr("> Entering '%s.%s'\n", | 72 OS::PrintErr("> Entering '%s.%s'\n", |
| 66 class_name.ToCString(), function_name.ToCString()); | 73 class_name.ToCString(), function_name.ToCString()); |
| (...skipping 1191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1258 UNIMPLEMENTED(); | 1265 UNIMPLEMENTED(); |
| 1259 } | 1266 } |
| 1260 } | 1267 } |
| 1261 } | 1268 } |
| 1262 if (interrupt_bits & Isolate::kVmStatusInterrupt) { | 1269 if (interrupt_bits & Isolate::kVmStatusInterrupt) { |
| 1263 Dart_IsolateInterruptCallback callback = isolate->VmStatsCallback(); | 1270 Dart_IsolateInterruptCallback callback = isolate->VmStatsCallback(); |
| 1264 if (callback) { | 1271 if (callback) { |
| 1265 (*callback)(); | 1272 (*callback)(); |
| 1266 } | 1273 } |
| 1267 } | 1274 } |
| 1275 |
| 1276 if (FLAG_use_osr && (interrupt_bits == 0)) { |
| 1277 DartFrameIterator iterator; |
| 1278 StackFrame* frame = iterator.NextFrame(); |
| 1279 const Function& function = Function::Handle(frame->LookupDartFunction()); |
| 1280 ASSERT(!function.IsNull()); |
| 1281 if (!function.is_optimizable()) return; |
| 1282 intptr_t osr_id = |
| 1283 Code::Handle(function.unoptimized_code()).GetDeoptIdForOsr(frame->pc()); |
| 1284 if (FLAG_trace_osr) { |
| 1285 OS::Print("Attempting OSR for %s at id=%"Pd"\n", |
| 1286 function.ToFullyQualifiedCString(), |
| 1287 osr_id); |
| 1288 } |
| 1289 |
| 1290 const Code& original_code = Code::Handle(function.CurrentCode()); |
| 1291 const Error& error = |
| 1292 Error::Handle(Compiler::CompileOptimizedFunction(function, osr_id)); |
| 1293 if (!error.IsNull()) Exceptions::PropagateError(error); |
| 1294 |
| 1295 const Code& optimized_code = Code::Handle(function.CurrentCode()); |
| 1296 // The current code will not be changed in the case that the compiler |
| 1297 // bailed out during OSR compilation. |
| 1298 if (optimized_code.raw() != original_code.raw()) { |
| 1299 // The OSR code does not work for calling the function, so restore the |
| 1300 // unoptimized code. Patch the stack frame to return into the OSR |
| 1301 // code. |
| 1302 uword optimized_entry = |
| 1303 Instructions::Handle(optimized_code.instructions()).EntryPoint(); |
| 1304 function.SetCode(original_code); |
| 1305 frame->set_pc(optimized_entry); |
| 1306 } |
| 1307 } |
| 1268 } | 1308 } |
| 1269 | 1309 |
| 1270 | 1310 |
| 1271 DEFINE_RUNTIME_ENTRY(TraceICCall, 2) { | 1311 DEFINE_RUNTIME_ENTRY(TraceICCall, 2) { |
| 1272 ASSERT(arguments.ArgCount() == | 1312 ASSERT(arguments.ArgCount() == |
| 1273 kTraceICCallRuntimeEntry.argument_count()); | 1313 kTraceICCallRuntimeEntry.argument_count()); |
| 1274 const ICData& ic_data = ICData::CheckedHandle(arguments.ArgAt(0)); | 1314 const ICData& ic_data = ICData::CheckedHandle(arguments.ArgAt(0)); |
| 1275 const Function& function = Function::CheckedHandle(arguments.ArgAt(1)); | 1315 const Function& function = Function::CheckedHandle(arguments.ArgAt(1)); |
| 1276 DartFrameIterator iterator; | 1316 DartFrameIterator iterator; |
| 1277 StackFrame* frame = iterator.NextFrame(); | 1317 StackFrame* frame = iterator.NextFrame(); |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1321 return; | 1361 return; |
| 1322 } | 1362 } |
| 1323 if (function.is_optimizable()) { | 1363 if (function.is_optimizable()) { |
| 1324 const Error& error = | 1364 const Error& error = |
| 1325 Error::Handle(Compiler::CompileOptimizedFunction(function)); | 1365 Error::Handle(Compiler::CompileOptimizedFunction(function)); |
| 1326 if (!error.IsNull()) { | 1366 if (!error.IsNull()) { |
| 1327 Exceptions::PropagateError(error); | 1367 Exceptions::PropagateError(error); |
| 1328 } | 1368 } |
| 1329 const Code& optimized_code = Code::Handle(function.CurrentCode()); | 1369 const Code& optimized_code = Code::Handle(function.CurrentCode()); |
| 1330 ASSERT(!optimized_code.IsNull()); | 1370 ASSERT(!optimized_code.IsNull()); |
| 1331 // Set usage counter for reoptimization. | 1371 // Reset usage counter for reoptimization. |
| 1332 function.set_usage_counter( | 1372 function.set_usage_counter(0); |
| 1333 function.usage_counter() - FLAG_reoptimization_counter_threshold); | |
| 1334 } else { | 1373 } else { |
| 1335 if (FLAG_trace_failed_optimization_attempts) { | 1374 if (FLAG_trace_failed_optimization_attempts) { |
| 1336 OS::PrintErr("Not Optimizable: %s\n", function.ToFullyQualifiedCString()); | 1375 OS::PrintErr("Not Optimizable: %s\n", function.ToFullyQualifiedCString()); |
| 1337 } | 1376 } |
| 1338 // TODO(5442338): Abort as this should not happen. | 1377 // TODO(5442338): Abort as this should not happen. |
| 1339 function.set_usage_counter(kLowInvocationCount); | 1378 function.set_usage_counter(kLowInvocationCount); |
| 1340 } | 1379 } |
| 1341 arguments.SetReturn(Code::Handle(function.CurrentCode())); | 1380 arguments.SetReturn(Code::Handle(function.CurrentCode())); |
| 1342 } | 1381 } |
| 1343 | 1382 |
| (...skipping 417 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1761 // Arg1: Value that is being stored. | 1800 // Arg1: Value that is being stored. |
| 1762 DEFINE_RUNTIME_ENTRY(UpdateFieldCid, 2) { | 1801 DEFINE_RUNTIME_ENTRY(UpdateFieldCid, 2) { |
| 1763 ASSERT(arguments.ArgCount() == kUpdateFieldCidRuntimeEntry.argument_count()); | 1802 ASSERT(arguments.ArgCount() == kUpdateFieldCidRuntimeEntry.argument_count()); |
| 1764 const Field& field = Field::CheckedHandle(arguments.ArgAt(0)); | 1803 const Field& field = Field::CheckedHandle(arguments.ArgAt(0)); |
| 1765 const Object& value = Object::Handle(arguments.ArgAt(1)); | 1804 const Object& value = Object::Handle(arguments.ArgAt(1)); |
| 1766 | 1805 |
| 1767 field.UpdateCid(value.GetClassId()); | 1806 field.UpdateCid(value.GetClassId()); |
| 1768 } | 1807 } |
| 1769 | 1808 |
| 1770 } // namespace dart | 1809 } // namespace dart |
| OLD | NEW |