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

Side by Side Diff: src/ic.cc

Issue 426633002: Encapsulate type in the PropertyHandlerCompiler (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 6 years, 4 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 | Annotate | Revision Log
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/v8.h" 5 #include "src/v8.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/codegen.h" 10 #include "src/codegen.h"
(...skipping 924 matching lines...) Expand 10 before | Expand all | Expand 10 after
935 Handle<JSFunction>::cast(object)->should_have_prototype() && 935 Handle<JSFunction>::cast(object)->should_have_prototype() &&
936 !Handle<JSFunction>::cast(object)->map()->has_non_instance_prototype()) { 936 !Handle<JSFunction>::cast(object)->map()->has_non_instance_prototype()) {
937 Handle<Code> stub; 937 Handle<Code> stub;
938 FunctionPrototypeStub function_prototype_stub(isolate()); 938 FunctionPrototypeStub function_prototype_stub(isolate());
939 return function_prototype_stub.GetCode(); 939 return function_prototype_stub.GetCode();
940 } 940 }
941 941
942 Handle<HeapType> type = receiver_type(); 942 Handle<HeapType> type = receiver_type();
943 Handle<JSObject> holder(lookup->holder()); 943 Handle<JSObject> holder(lookup->holder());
944 bool receiver_is_holder = object.is_identical_to(holder); 944 bool receiver_is_holder = object.is_identical_to(holder);
945 NamedLoadHandlerCompiler compiler(isolate(), cache_holder); 945 NamedLoadHandlerCompiler compiler(isolate(), receiver_type(), cache_holder);
946 946
947 switch (lookup->type()) { 947 switch (lookup->type()) {
948 case FIELD: { 948 case FIELD: {
949 FieldIndex field = lookup->GetFieldIndex(); 949 FieldIndex field = lookup->GetFieldIndex();
950 if (receiver_is_holder) { 950 if (receiver_is_holder) {
951 return SimpleFieldLoad(field); 951 return SimpleFieldLoad(field);
952 } 952 }
953 return compiler.CompileLoadField( 953 return compiler.CompileLoadField(holder, name, field,
954 type, holder, name, field, lookup->representation()); 954 lookup->representation());
955 } 955 }
956 case CONSTANT: { 956 case CONSTANT: {
957 Handle<Object> constant(lookup->GetConstant(), isolate()); 957 Handle<Object> constant(lookup->GetConstant(), isolate());
958 return compiler.CompileLoadConstant(type, holder, name, constant); 958 return compiler.CompileLoadConstant(holder, name, constant);
959 } 959 }
960 case NORMAL: 960 case NORMAL:
961 if (kind() != Code::LOAD_IC) break; 961 if (kind() != Code::LOAD_IC) break;
962 if (holder->IsGlobalObject()) { 962 if (holder->IsGlobalObject()) {
963 Handle<GlobalObject> global = Handle<GlobalObject>::cast(holder); 963 Handle<GlobalObject> global = Handle<GlobalObject>::cast(holder);
964 Handle<PropertyCell> cell( 964 Handle<PropertyCell> cell(
965 global->GetPropertyCell(lookup), isolate()); 965 global->GetPropertyCell(lookup), isolate());
966 Handle<Code> code = compiler.CompileLoadGlobal( 966 Handle<Code> code = compiler.CompileLoadGlobal(global, cell, name,
967 type, global, cell, name, lookup->IsDontDelete()); 967 lookup->IsDontDelete());
968 // TODO(verwaest): Move caching of these NORMAL stubs outside as well. 968 // TODO(verwaest): Move caching of these NORMAL stubs outside as well.
969 CacheHolderFlag flag; 969 CacheHolderFlag flag;
970 Handle<Map> stub_holder_map = 970 Handle<Map> stub_holder_map =
971 GetHandlerCacheHolder(*type, receiver_is_holder, isolate(), &flag); 971 GetHandlerCacheHolder(*type, receiver_is_holder, isolate(), &flag);
972 Map::UpdateCodeCache(stub_holder_map, name, code); 972 Map::UpdateCodeCache(stub_holder_map, name, code);
973 return code; 973 return code;
974 } 974 }
975 // There is only one shared stub for loading normalized 975 // There is only one shared stub for loading normalized
976 // properties. It does not traverse the prototype chain, so the 976 // properties. It does not traverse the prototype chain, so the
977 // property must be found in the object for the stub to be 977 // property must be found in the object for the stub to be
(...skipping 12 matching lines...) Expand all
990 object_offset, receiver->map()); 990 object_offset, receiver->map());
991 return SimpleFieldLoad(index); 991 return SimpleFieldLoad(index);
992 } 992 }
993 } 993 }
994 994
995 Handle<Object> callback(lookup->GetCallbackObject(), isolate()); 995 Handle<Object> callback(lookup->GetCallbackObject(), isolate());
996 if (callback->IsExecutableAccessorInfo()) { 996 if (callback->IsExecutableAccessorInfo()) {
997 Handle<ExecutableAccessorInfo> info = 997 Handle<ExecutableAccessorInfo> info =
998 Handle<ExecutableAccessorInfo>::cast(callback); 998 Handle<ExecutableAccessorInfo>::cast(callback);
999 if (v8::ToCData<Address>(info->getter()) == 0) break; 999 if (v8::ToCData<Address>(info->getter()) == 0) break;
1000 if (!info->IsCompatibleReceiver(*object)) break; 1000 if (!ExecutableAccessorInfo::IsCompatibleReceiverType(isolate(), info,
1001 return compiler.CompileLoadCallback(type, holder, name, info); 1001 type)) {
1002 break;
1003 }
1004 return compiler.CompileLoadCallback(holder, name, info);
1002 } else if (callback->IsAccessorPair()) { 1005 } else if (callback->IsAccessorPair()) {
1003 Handle<Object> getter(Handle<AccessorPair>::cast(callback)->getter(), 1006 Handle<Object> getter(Handle<AccessorPair>::cast(callback)->getter(),
1004 isolate()); 1007 isolate());
1005 if (!getter->IsJSFunction()) break; 1008 if (!getter->IsJSFunction()) break;
1006 if (holder->IsGlobalObject()) break; 1009 if (holder->IsGlobalObject()) break;
1007 if (!holder->HasFastProperties()) break; 1010 if (!holder->HasFastProperties()) break;
1008 Handle<JSFunction> function = Handle<JSFunction>::cast(getter); 1011 Handle<JSFunction> function = Handle<JSFunction>::cast(getter);
1009 if (!object->IsJSObject() && 1012 if (!object->IsJSObject() &&
1010 !function->IsBuiltin() && 1013 !function->IsBuiltin() &&
1011 function->shared()->strict_mode() == SLOPPY) { 1014 function->shared()->strict_mode() == SLOPPY) {
1012 // Calling sloppy non-builtins with a value as the receiver 1015 // Calling sloppy non-builtins with a value as the receiver
1013 // requires boxing. 1016 // requires boxing.
1014 break; 1017 break;
1015 } 1018 }
1016 CallOptimization call_optimization(function); 1019 CallOptimization call_optimization(function);
1017 if (call_optimization.is_simple_api_call() && 1020 if (call_optimization.is_simple_api_call() &&
1018 call_optimization.IsCompatibleReceiver(object, holder)) { 1021 call_optimization.IsCompatibleReceiver(object, holder)) {
1019 return compiler.CompileLoadCallback( 1022 return compiler.CompileLoadCallback(holder, name, call_optimization);
1020 type, holder, name, call_optimization);
1021 } 1023 }
1022 return compiler.CompileLoadViaGetter(type, holder, name, function); 1024 return compiler.CompileLoadViaGetter(holder, name, function);
1023 } 1025 }
1024 // TODO(dcarney): Handle correctly. 1026 // TODO(dcarney): Handle correctly.
1025 ASSERT(callback->IsDeclaredAccessorInfo()); 1027 ASSERT(callback->IsDeclaredAccessorInfo());
1026 break; 1028 break;
1027 } 1029 }
1028 case INTERCEPTOR: 1030 case INTERCEPTOR:
1029 ASSERT(HasInterceptorGetter(*holder)); 1031 ASSERT(HasInterceptorGetter(*holder));
1030 return compiler.CompileLoadInterceptor(type, holder, name); 1032 return compiler.CompileLoadInterceptor(holder, name);
1031 default: 1033 default:
1032 break; 1034 break;
1033 } 1035 }
1034 1036
1035 return slow_stub(); 1037 return slow_stub();
1036 } 1038 }
1037 1039
1038 1040
1039 static Handle<Object> TryConvertKey(Handle<Object> key, Isolate* isolate) { 1041 static Handle<Object> TryConvertKey(Handle<Object> key, Isolate* isolate) {
1040 // This helper implements a few common fast cases for converting 1042 // This helper implements a few common fast cases for converting
(...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after
1385 Handle<Object> object, Handle<String> name, 1387 Handle<Object> object, Handle<String> name,
1386 Handle<Object> value, 1388 Handle<Object> value,
1387 CacheHolderFlag cache_holder) { 1389 CacheHolderFlag cache_holder) {
1388 if (object->IsAccessCheckNeeded()) return slow_stub(); 1390 if (object->IsAccessCheckNeeded()) return slow_stub();
1389 ASSERT(cache_holder == kCacheOnReceiver || lookup->type() == CALLBACKS || 1391 ASSERT(cache_holder == kCacheOnReceiver || lookup->type() == CALLBACKS ||
1390 (object->IsJSGlobalProxy() && lookup->holder()->IsJSGlobalObject())); 1392 (object->IsJSGlobalProxy() && lookup->holder()->IsJSGlobalObject()));
1391 // This is currently guaranteed by checks in StoreIC::Store. 1393 // This is currently guaranteed by checks in StoreIC::Store.
1392 Handle<JSObject> receiver = Handle<JSObject>::cast(object); 1394 Handle<JSObject> receiver = Handle<JSObject>::cast(object);
1393 1395
1394 Handle<JSObject> holder(lookup->holder()); 1396 Handle<JSObject> holder(lookup->holder());
1395 NamedStoreHandlerCompiler compiler(isolate()); 1397 NamedStoreHandlerCompiler compiler(isolate(), receiver_type());
1396 1398
1397 if (lookup->IsTransition()) { 1399 if (lookup->IsTransition()) {
1398 // Explicitly pass in the receiver map since LookupForWrite may have 1400 // Explicitly pass in the receiver map since LookupForWrite may have
1399 // stored something else than the receiver in the holder. 1401 // stored something else than the receiver in the holder.
1400 Handle<Map> transition(lookup->GetTransitionTarget()); 1402 Handle<Map> transition(lookup->GetTransitionTarget());
1401 PropertyDetails details = lookup->GetPropertyDetails(); 1403 PropertyDetails details = lookup->GetPropertyDetails();
1402 1404
1403 if (details.type() != CALLBACKS && details.attributes() == NONE) { 1405 if (details.type() != CALLBACKS && details.attributes() == NONE) {
1404 return compiler.CompileStoreTransition( 1406 return compiler.CompileStoreTransition(
1405 receiver, lookup, transition, name); 1407 receiver, lookup, transition, name);
(...skipping 25 matching lines...) Expand all
1431 } 1433 }
1432 ASSERT(holder.is_identical_to(receiver)); 1434 ASSERT(holder.is_identical_to(receiver));
1433 return isolate()->builtins()->StoreIC_Normal(); 1435 return isolate()->builtins()->StoreIC_Normal();
1434 case CALLBACKS: { 1436 case CALLBACKS: {
1435 Handle<Object> callback(lookup->GetCallbackObject(), isolate()); 1437 Handle<Object> callback(lookup->GetCallbackObject(), isolate());
1436 if (callback->IsExecutableAccessorInfo()) { 1438 if (callback->IsExecutableAccessorInfo()) {
1437 Handle<ExecutableAccessorInfo> info = 1439 Handle<ExecutableAccessorInfo> info =
1438 Handle<ExecutableAccessorInfo>::cast(callback); 1440 Handle<ExecutableAccessorInfo>::cast(callback);
1439 if (v8::ToCData<Address>(info->setter()) == 0) break; 1441 if (v8::ToCData<Address>(info->setter()) == 0) break;
1440 if (!holder->HasFastProperties()) break; 1442 if (!holder->HasFastProperties()) break;
1441 if (!info->IsCompatibleReceiver(*receiver)) break; 1443 if (!ExecutableAccessorInfo::IsCompatibleReceiverType(
1444 isolate(), info, receiver_type())) {
1445 break;
1446 }
1442 return compiler.CompileStoreCallback(receiver, holder, name, info); 1447 return compiler.CompileStoreCallback(receiver, holder, name, info);
1443 } else if (callback->IsAccessorPair()) { 1448 } else if (callback->IsAccessorPair()) {
1444 Handle<Object> setter( 1449 Handle<Object> setter(
1445 Handle<AccessorPair>::cast(callback)->setter(), isolate()); 1450 Handle<AccessorPair>::cast(callback)->setter(), isolate());
1446 if (!setter->IsJSFunction()) break; 1451 if (!setter->IsJSFunction()) break;
1447 if (holder->IsGlobalObject()) break; 1452 if (holder->IsGlobalObject()) break;
1448 if (!holder->HasFastProperties()) break; 1453 if (!holder->HasFastProperties()) break;
1449 Handle<JSFunction> function = Handle<JSFunction>::cast(setter); 1454 Handle<JSFunction> function = Handle<JSFunction>::cast(setter);
1450 CallOptimization call_optimization(function); 1455 CallOptimization call_optimization(function);
1451 if (call_optimization.is_simple_api_call() && 1456 if (call_optimization.is_simple_api_call() &&
(...skipping 1583 matching lines...) Expand 10 before | Expand all | Expand 10 after
3035 #undef ADDR 3040 #undef ADDR
3036 }; 3041 };
3037 3042
3038 3043
3039 Address IC::AddressFromUtilityId(IC::UtilityId id) { 3044 Address IC::AddressFromUtilityId(IC::UtilityId id) {
3040 return IC_utilities[id]; 3045 return IC_utilities[id];
3041 } 3046 }
3042 3047
3043 3048
3044 } } // namespace v8::internal 3049 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/ia32/stub-cache-ia32.cc ('k') | src/objects.h » ('j') | src/objects.cc » ('J')

Powered by Google App Engine
This is Rietveld 408576698