Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2)

Side by Side Diff: src/ic/ic.cc

Issue 1332563003: Vector ICs: No more patching for call ics. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Fix x64 build break. Created 5 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/ic/ic.h ('k') | src/ic/ic-inl.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/ic/ic.h" 5 #include "src/ic/ic.h"
6 6
7 #include "src/accessors.h" 7 #include "src/accessors.h"
8 #include "src/api.h" 8 #include "src/api.h"
9 #include "src/arguments.h" 9 #include "src/arguments.h"
10 #include "src/base/bits.h" 10 #include "src/base/bits.h"
(...skipping 2279 matching lines...) Expand 10 before | Expand all | Expand 10 after
2290 if (!AddressIsDeoptimizedCode()) { 2290 if (!AddressIsDeoptimizedCode()) {
2291 set_target(*stub); 2291 set_target(*stub);
2292 } 2292 }
2293 } 2293 }
2294 TRACE_IC("StoreIC", key); 2294 TRACE_IC("StoreIC", key);
2295 2295
2296 return store_handle; 2296 return store_handle;
2297 } 2297 }
2298 2298
2299 2299
2300 bool CallIC::DoCustomHandler(Handle<Object> function,
2301 const CallICState& callic_state) {
2302 DCHECK(FLAG_use_ic && function->IsJSFunction());
2303
2304 // Are we the array function?
2305 Handle<JSFunction> array_function =
2306 Handle<JSFunction>(isolate()->native_context()->array_function());
2307 if (array_function.is_identical_to(Handle<JSFunction>::cast(function))) {
2308 // Alter the slot.
2309 CallICNexus* nexus = casted_nexus<CallICNexus>();
2310 nexus->ConfigureMonomorphicArray();
2311
2312 // Vector-based ICs have a different calling convention in optimized code
2313 // than full code so the correct stub has to be chosen.
2314 if (AddressIsOptimizedCode()) {
2315 CallIC_ArrayStub stub(isolate(), callic_state);
2316 set_target(*stub.GetCode());
2317 } else {
2318 CallIC_ArrayTrampolineStub stub(isolate(), callic_state);
2319 set_target(*stub.GetCode());
2320 }
2321
2322 Handle<String> name;
2323 if (array_function->shared()->name()->IsString()) {
2324 name = Handle<String>(String::cast(array_function->shared()->name()),
2325 isolate());
2326 }
2327 TRACE_IC("CallIC", name);
2328 OnTypeFeedbackChanged(isolate(), get_host(), nexus->vector(), state(),
2329 MONOMORPHIC);
2330 return true;
2331 }
2332 return false;
2333 }
2334
2335
2336 void CallIC::PatchMegamorphic(Handle<Object> function) {
2337 CallICState callic_state(target()->extra_ic_state());
2338
2339 // We are going generic.
2340 CallICNexus* nexus = casted_nexus<CallICNexus>();
2341 nexus->ConfigureMegamorphic();
2342
2343 // Vector-based ICs have a different calling convention in optimized code
2344 // than full code so the correct stub has to be chosen.
2345 if (AddressIsOptimizedCode()) {
2346 CallICStub stub(isolate(), callic_state);
2347 set_target(*stub.GetCode());
2348 } else {
2349 CallICTrampolineStub stub(isolate(), callic_state);
2350 set_target(*stub.GetCode());
2351 }
2352
2353 Handle<Object> name = isolate()->factory()->empty_string();
2354 if (function->IsJSFunction()) {
2355 Handle<JSFunction> js_function = Handle<JSFunction>::cast(function);
2356 name = handle(js_function->shared()->name(), isolate());
2357 }
2358
2359 TRACE_IC("CallIC", name);
2360 OnTypeFeedbackChanged(isolate(), get_host(), nexus->vector(), state(),
2361 GENERIC);
2362 }
2363
2364
2365 void CallIC::HandleMiss(Handle<Object> function) { 2300 void CallIC::HandleMiss(Handle<Object> function) {
2366 CallICState callic_state(target()->extra_ic_state());
2367 Handle<Object> name = isolate()->factory()->empty_string(); 2301 Handle<Object> name = isolate()->factory()->empty_string();
2368 CallICNexus* nexus = casted_nexus<CallICNexus>(); 2302 CallICNexus* nexus = casted_nexus<CallICNexus>();
2369 Object* feedback = nexus->GetFeedback(); 2303 Object* feedback = nexus->GetFeedback();
2370 2304
2371 // Hand-coded MISS handling is easier if CallIC slots don't contain smis. 2305 // Hand-coded MISS handling is easier if CallIC slots don't contain smis.
2372 DCHECK(!feedback->IsSmi()); 2306 DCHECK(!feedback->IsSmi());
2373 2307
2374 if (feedback->IsWeakCell() || !function->IsJSFunction()) { 2308 if (feedback->IsWeakCell() || !function->IsJSFunction() ||
2309 feedback->IsAllocationSite()) {
2375 // We are going generic. 2310 // We are going generic.
2376 nexus->ConfigureMegamorphic(); 2311 nexus->ConfigureMegamorphic();
2377 } else { 2312 } else {
2378 // The feedback is either uninitialized or an allocation site. 2313 DCHECK(feedback == *TypeFeedbackVector::UninitializedSentinel(isolate()));
2379 // It might be an allocation site because if we re-compile the full code 2314 Handle<JSFunction> js_function = Handle<JSFunction>::cast(function);
2380 // to add deoptimization support, we call with the default call-ic, and
2381 // merely need to patch the target to match the feedback.
2382 // TODO(mvstanton): the better approach is to dispense with patching
2383 // altogether, which is in progress.
2384 DCHECK(feedback == *TypeFeedbackVector::UninitializedSentinel(isolate()) ||
2385 feedback->IsAllocationSite());
2386 2315
2387 // Do we want to install a custom handler? 2316 Handle<JSFunction> array_function =
2388 if (FLAG_use_ic && DoCustomHandler(function, callic_state)) { 2317 Handle<JSFunction>(isolate()->native_context()->array_function());
2389 return; 2318 if (array_function.is_identical_to(js_function)) {
2319 // Alter the slot.
2320 nexus->ConfigureMonomorphicArray();
2321 } else {
2322 nexus->ConfigureMonomorphic(js_function);
2390 } 2323 }
2391
2392 nexus->ConfigureMonomorphic(Handle<JSFunction>::cast(function));
2393 } 2324 }
2394 2325
2395 if (function->IsJSFunction()) { 2326 if (function->IsJSFunction()) {
2396 Handle<JSFunction> js_function = Handle<JSFunction>::cast(function); 2327 Handle<JSFunction> js_function = Handle<JSFunction>::cast(function);
2397 name = handle(js_function->shared()->name(), isolate()); 2328 name = handle(js_function->shared()->name(), isolate());
2398 } 2329 }
2399 2330
2400 IC::State new_state = nexus->StateFromFeedback(); 2331 IC::State new_state = nexus->StateFromFeedback();
2401 OnTypeFeedbackChanged(isolate(), get_host(), *vector(), state(), new_state); 2332 OnTypeFeedbackChanged(isolate(), get_host(), *vector(), state(), new_state);
2402 TRACE_IC("CallIC", name); 2333 TRACE_IC("CallIC", name);
(...skipping 16 matching lines...) Expand all
2419 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(1); 2350 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(1);
2420 Handle<Smi> slot = args.at<Smi>(2); 2351 Handle<Smi> slot = args.at<Smi>(2);
2421 FeedbackVectorICSlot vector_slot = vector->ToICSlot(slot->value()); 2352 FeedbackVectorICSlot vector_slot = vector->ToICSlot(slot->value());
2422 CallICNexus nexus(vector, vector_slot); 2353 CallICNexus nexus(vector, vector_slot);
2423 CallIC ic(isolate, &nexus); 2354 CallIC ic(isolate, &nexus);
2424 ic.HandleMiss(function); 2355 ic.HandleMiss(function);
2425 return *function; 2356 return *function;
2426 } 2357 }
2427 2358
2428 2359
2429 RUNTIME_FUNCTION(Runtime_CallIC_Customization_Miss) {
2430 TimerEventScope<TimerEventIcMiss> timer(isolate);
2431 HandleScope scope(isolate);
2432 DCHECK(args.length() == 3);
2433 Handle<Object> function = args.at<Object>(0);
2434 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(1);
2435 Handle<Smi> slot = args.at<Smi>(2);
2436 FeedbackVectorICSlot vector_slot = vector->ToICSlot(slot->value());
2437 CallICNexus nexus(vector, vector_slot);
2438 // A miss on a custom call ic always results in going megamorphic.
2439 CallIC ic(isolate, &nexus);
2440 ic.PatchMegamorphic(function);
2441 return *function;
2442 }
2443
2444
2445 // Used from ic-<arch>.cc. 2360 // Used from ic-<arch>.cc.
2446 RUNTIME_FUNCTION(Runtime_LoadIC_Miss) { 2361 RUNTIME_FUNCTION(Runtime_LoadIC_Miss) {
2447 TimerEventScope<TimerEventIcMiss> timer(isolate); 2362 TimerEventScope<TimerEventIcMiss> timer(isolate);
2448 HandleScope scope(isolate); 2363 HandleScope scope(isolate);
2449 Handle<Object> receiver = args.at<Object>(0); 2364 Handle<Object> receiver = args.at<Object>(0);
2450 Handle<Name> key = args.at<Name>(1); 2365 Handle<Name> key = args.at<Name>(1);
2451 Handle<Object> result; 2366 Handle<Object> result;
2452 2367
2453 DCHECK(args.length() == 4); 2368 DCHECK(args.length() == 4);
2454 Handle<Smi> slot = args.at<Smi>(2); 2369 Handle<Smi> slot = args.at<Smi>(2);
(...skipping 753 matching lines...) Expand 10 before | Expand all | Expand 10 after
3208 KeyedLoadICNexus nexus(vector, vector_slot); 3123 KeyedLoadICNexus nexus(vector, vector_slot);
3209 KeyedLoadIC ic(IC::EXTRA_CALL_FRAME, isolate, &nexus); 3124 KeyedLoadIC ic(IC::EXTRA_CALL_FRAME, isolate, &nexus);
3210 ic.UpdateState(receiver, key); 3125 ic.UpdateState(receiver, key);
3211 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, ic.Load(receiver, key)); 3126 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, ic.Load(receiver, key));
3212 } 3127 }
3213 3128
3214 return *result; 3129 return *result;
3215 } 3130 }
3216 } // namespace internal 3131 } // namespace internal
3217 } // namespace v8 3132 } // namespace v8
OLDNEW
« no previous file with comments | « src/ic/ic.h ('k') | src/ic/ic-inl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698