OLD | NEW |
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/base/bits.h" | 10 #include "src/base/bits.h" |
(...skipping 1093 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1104 } else if (!lookup->IsFound()) { | 1104 } else if (!lookup->IsFound()) { |
1105 if (kind() == Code::LOAD_IC) { | 1105 if (kind() == Code::LOAD_IC) { |
1106 code = NamedLoadHandlerCompiler::ComputeLoadNonexistent(lookup->name(), | 1106 code = NamedLoadHandlerCompiler::ComputeLoadNonexistent(lookup->name(), |
1107 receiver_map()); | 1107 receiver_map()); |
1108 // TODO(jkummerow/verwaest): Introduce a builtin that handles this case. | 1108 // TODO(jkummerow/verwaest): Introduce a builtin that handles this case. |
1109 if (code.is_null()) code = slow_stub(); | 1109 if (code.is_null()) code = slow_stub(); |
1110 } else { | 1110 } else { |
1111 code = slow_stub(); | 1111 code = slow_stub(); |
1112 } | 1112 } |
1113 } else { | 1113 } else { |
1114 code = ComputeHandler(lookup); | 1114 if (lookup->state() == LookupIterator::ACCESSOR) { |
| 1115 Handle<Object> accessors = lookup->GetAccessors(); |
| 1116 Handle<Map> map = receiver_map(); |
| 1117 if (accessors->IsExecutableAccessorInfo()) { |
| 1118 Handle<ExecutableAccessorInfo> info = |
| 1119 Handle<ExecutableAccessorInfo>::cast(accessors); |
| 1120 if ((v8::ToCData<Address>(info->getter()) != 0) && |
| 1121 !ExecutableAccessorInfo::IsCompatibleReceiverMap(isolate(), info, |
| 1122 map)) { |
| 1123 TRACE_GENERIC_IC(isolate(), "LoadIC", "incompatible receiver type"); |
| 1124 code = slow_stub(); |
| 1125 } |
| 1126 } else if (accessors->IsAccessorPair()) { |
| 1127 Handle<Object> getter(Handle<AccessorPair>::cast(accessors)->getter(), |
| 1128 isolate()); |
| 1129 Handle<JSObject> holder = lookup->GetHolder<JSObject>(); |
| 1130 Handle<Object> receiver = lookup->GetReceiver(); |
| 1131 if (getter->IsJSFunction() && holder->HasFastProperties()) { |
| 1132 Handle<JSFunction> function = Handle<JSFunction>::cast(getter); |
| 1133 if (receiver->IsJSObject() || function->IsBuiltin() || |
| 1134 !is_sloppy(function->shared()->language_mode())) { |
| 1135 CallOptimization call_optimization(function); |
| 1136 if (call_optimization.is_simple_api_call() && |
| 1137 !call_optimization.IsCompatibleReceiver(receiver, holder)) { |
| 1138 TRACE_GENERIC_IC(isolate(), "LoadIC", |
| 1139 "incompatible receiver type"); |
| 1140 code = slow_stub(); |
| 1141 } |
| 1142 } |
| 1143 } |
| 1144 } |
| 1145 } |
| 1146 if (code.is_null()) code = ComputeHandler(lookup); |
1115 } | 1147 } |
1116 | 1148 |
1117 PatchCache(lookup->name(), code); | 1149 PatchCache(lookup->name(), code); |
1118 TRACE_IC("LoadIC", lookup->name()); | 1150 TRACE_IC("LoadIC", lookup->name()); |
1119 } | 1151 } |
1120 | 1152 |
1121 | 1153 |
1122 void IC::UpdateMegamorphicCache(Map* map, Name* name, Code* code) { | 1154 void IC::UpdateMegamorphicCache(Map* map, Name* name, Code* code) { |
1123 isolate()->stub_cache()->Set(name, map, code); | 1155 isolate()->stub_cache()->Set(name, map, code); |
1124 } | 1156 } |
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1231 } | 1263 } |
1232 } | 1264 } |
1233 | 1265 |
1234 Handle<Object> accessors = lookup->GetAccessors(); | 1266 Handle<Object> accessors = lookup->GetAccessors(); |
1235 if (accessors->IsExecutableAccessorInfo()) { | 1267 if (accessors->IsExecutableAccessorInfo()) { |
1236 Handle<ExecutableAccessorInfo> info = | 1268 Handle<ExecutableAccessorInfo> info = |
1237 Handle<ExecutableAccessorInfo>::cast(accessors); | 1269 Handle<ExecutableAccessorInfo>::cast(accessors); |
1238 if (v8::ToCData<Address>(info->getter()) == 0) break; | 1270 if (v8::ToCData<Address>(info->getter()) == 0) break; |
1239 if (!ExecutableAccessorInfo::IsCompatibleReceiverMap(isolate(), info, | 1271 if (!ExecutableAccessorInfo::IsCompatibleReceiverMap(isolate(), info, |
1240 map)) { | 1272 map)) { |
| 1273 // This case should be already handled in LoadIC::UpdateCaches. |
| 1274 UNREACHABLE(); |
1241 break; | 1275 break; |
1242 } | 1276 } |
1243 if (!holder->HasFastProperties()) break; | 1277 if (!holder->HasFastProperties()) break; |
1244 NamedLoadHandlerCompiler compiler(isolate(), map, holder, cache_holder); | 1278 NamedLoadHandlerCompiler compiler(isolate(), map, holder, cache_holder); |
1245 return compiler.CompileLoadCallback(lookup->name(), info); | 1279 return compiler.CompileLoadCallback(lookup->name(), info); |
1246 } | 1280 } |
1247 if (accessors->IsAccessorPair()) { | 1281 if (accessors->IsAccessorPair()) { |
1248 Handle<Object> getter(Handle<AccessorPair>::cast(accessors)->getter(), | 1282 Handle<Object> getter(Handle<AccessorPair>::cast(accessors)->getter(), |
1249 isolate()); | 1283 isolate()); |
1250 if (!getter->IsJSFunction()) break; | 1284 if (!getter->IsJSFunction()) break; |
1251 if (!holder->HasFastProperties()) break; | 1285 if (!holder->HasFastProperties()) break; |
1252 Handle<JSFunction> function = Handle<JSFunction>::cast(getter); | 1286 Handle<JSFunction> function = Handle<JSFunction>::cast(getter); |
1253 if (!receiver->IsJSObject() && !function->IsBuiltin() && | 1287 if (!receiver->IsJSObject() && !function->IsBuiltin() && |
1254 is_sloppy(function->shared()->language_mode())) { | 1288 is_sloppy(function->shared()->language_mode())) { |
1255 // Calling sloppy non-builtins with a value as the receiver | 1289 // Calling sloppy non-builtins with a value as the receiver |
1256 // requires boxing. | 1290 // requires boxing. |
1257 break; | 1291 break; |
1258 } | 1292 } |
1259 CallOptimization call_optimization(function); | 1293 CallOptimization call_optimization(function); |
1260 NamedLoadHandlerCompiler compiler(isolate(), map, holder, cache_holder); | 1294 NamedLoadHandlerCompiler compiler(isolate(), map, holder, cache_holder); |
1261 if (call_optimization.is_simple_api_call() && | 1295 if (call_optimization.is_simple_api_call()) { |
1262 call_optimization.IsCompatibleReceiver(receiver, holder)) { | 1296 if (call_optimization.IsCompatibleReceiver(receiver, holder)) { |
1263 return compiler.CompileLoadCallback(lookup->name(), call_optimization, | 1297 return compiler.CompileLoadCallback( |
1264 lookup->GetAccessorIndex()); | 1298 lookup->name(), call_optimization, lookup->GetAccessorIndex()); |
| 1299 } else { |
| 1300 // This case should be already handled in LoadIC::UpdateCaches. |
| 1301 UNREACHABLE(); |
| 1302 } |
1265 } | 1303 } |
1266 int expected_arguments = | 1304 int expected_arguments = |
1267 function->shared()->internal_formal_parameter_count(); | 1305 function->shared()->internal_formal_parameter_count(); |
1268 return compiler.CompileLoadViaGetter( | 1306 return compiler.CompileLoadViaGetter( |
1269 lookup->name(), lookup->GetAccessorIndex(), expected_arguments); | 1307 lookup->name(), lookup->GetAccessorIndex(), expected_arguments); |
1270 } | 1308 } |
1271 break; | 1309 break; |
1272 } | 1310 } |
1273 | 1311 |
1274 case LookupIterator::DATA: { | 1312 case LookupIterator::DATA: { |
(...skipping 1773 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3048 static const Address IC_utilities[] = { | 3086 static const Address IC_utilities[] = { |
3049 #define ADDR(name) FUNCTION_ADDR(name), | 3087 #define ADDR(name) FUNCTION_ADDR(name), |
3050 IC_UTIL_LIST(ADDR) NULL | 3088 IC_UTIL_LIST(ADDR) NULL |
3051 #undef ADDR | 3089 #undef ADDR |
3052 }; | 3090 }; |
3053 | 3091 |
3054 | 3092 |
3055 Address IC::AddressFromUtilityId(IC::UtilityId id) { return IC_utilities[id]; } | 3093 Address IC::AddressFromUtilityId(IC::UtilityId id) { return IC_utilities[id]; } |
3056 } | 3094 } |
3057 } // namespace v8::internal | 3095 } // namespace v8::internal |
OLD | NEW |