| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 95 primary->value = code; | 95 primary->value = code; |
| 96 primary->map = map; | 96 primary->map = map; |
| 97 isolate()->counters()->megamorphic_stub_cache_updates()->Increment(); | 97 isolate()->counters()->megamorphic_stub_cache_updates()->Increment(); |
| 98 return code; | 98 return code; |
| 99 } | 99 } |
| 100 | 100 |
| 101 | 101 |
| 102 Handle<Code> StubCache::FindIC(Handle<Name> name, | 102 Handle<Code> StubCache::FindIC(Handle<Name> name, |
| 103 Handle<Map> stub_holder_map, | 103 Handle<Map> stub_holder_map, |
| 104 Code::Kind kind, | 104 Code::Kind kind, |
| 105 Code::StubType type, | |
| 106 Code::ExtraICState extra_state) { | 105 Code::ExtraICState extra_state) { |
| 107 Code::Flags flags = Code::ComputeMonomorphicFlags(kind, extra_state, type); | 106 Code::Flags flags = Code::ComputeMonomorphicFlags(kind, extra_state); |
| 108 Handle<Object> probe(stub_holder_map->FindInCodeCache(*name, flags), | 107 Handle<Object> probe(stub_holder_map->FindInCodeCache(*name, flags), |
| 109 isolate_); | 108 isolate_); |
| 110 if (probe->IsCode()) return Handle<Code>::cast(probe); | 109 if (probe->IsCode()) return Handle<Code>::cast(probe); |
| 111 return Handle<Code>::null(); | 110 return Handle<Code>::null(); |
| 112 } | 111 } |
| 113 | 112 |
| 114 | 113 |
| 115 Handle<Code> StubCache::FindIC(Handle<Name> name, | 114 Handle<Code> StubCache::FindIC(Handle<Name> name, |
| 116 Handle<JSObject> stub_holder, | 115 Handle<JSObject> stub_holder, |
| 117 Code::Kind kind, | 116 Code::Kind kind, |
| 118 Code::StubType type, | |
| 119 Code::ExtraICState extra_ic_state) { | 117 Code::ExtraICState extra_ic_state) { |
| 120 return FindIC(name, Handle<Map>(stub_holder->map()), kind, | 118 return FindIC(name, Handle<Map>(stub_holder->map()), kind, extra_ic_state); |
| 121 type, extra_ic_state); | |
| 122 } | 119 } |
| 123 | 120 |
| 124 | 121 |
| 125 Handle<Code> StubCache::FindLoadHandler(Handle<Name> name, | 122 Handle<Code> StubCache::FindLoadHandler(Handle<Name> name, |
| 126 Handle<JSObject> receiver, | 123 Handle<JSObject> receiver, |
| 127 Code::Kind kind, | 124 Code::Kind kind) { |
| 128 Code::StubType type) { | |
| 129 ASSERT(type != Code::NORMAL); | |
| 130 Code::Flags flags = Code::ComputeMonomorphicFlags( | 125 Code::Flags flags = Code::ComputeMonomorphicFlags( |
| 131 Code::HANDLER, Code::kNoExtraICState, type, kind); | 126 Code::HANDLER, Code::kNoExtraICState, Code::NORMAL, kind); |
| 132 Handle<Object> probe(receiver->map()->FindInCodeCache(*name, flags), | 127 Handle<Object> probe(receiver->map()->FindInCodeCache(*name, flags), |
| 133 isolate_); | 128 isolate_); |
| 134 if (probe->IsCode()) return Handle<Code>::cast(probe); | 129 if (probe->IsCode()) return Handle<Code>::cast(probe); |
| 135 return Handle<Code>::null(); | 130 return Handle<Code>::null(); |
| 136 } | 131 } |
| 137 | 132 |
| 138 | 133 |
| 139 Handle<Code> StubCache::FindStoreHandler(Handle<Name> name, | 134 Handle<Code> StubCache::FindStoreHandler(Handle<Name> name, |
| 140 Handle<JSObject> receiver, | 135 Handle<JSObject> receiver, |
| 141 Code::Kind kind, | 136 Code::Kind kind, |
| 142 Code::StubType type, | |
| 143 StrictModeFlag strict_mode) { | 137 StrictModeFlag strict_mode) { |
| 144 Code::ExtraICState extra_ic_state = Code::ComputeExtraICState( | 138 Code::ExtraICState extra_ic_state = Code::ComputeExtraICState( |
| 145 STANDARD_STORE, strict_mode); | 139 STANDARD_STORE, strict_mode); |
| 146 ASSERT(type != Code::NORMAL); | |
| 147 Code::Flags flags = Code::ComputeMonomorphicFlags( | 140 Code::Flags flags = Code::ComputeMonomorphicFlags( |
| 148 Code::HANDLER, extra_ic_state, type, kind); | 141 Code::HANDLER, extra_ic_state, Code::NORMAL, kind); |
| 149 Handle<Object> probe(receiver->map()->FindInCodeCache(*name, flags), | 142 Handle<Object> probe(receiver->map()->FindInCodeCache(*name, flags), |
| 150 isolate_); | 143 isolate_); |
| 151 if (probe->IsCode()) return Handle<Code>::cast(probe); | 144 if (probe->IsCode()) return Handle<Code>::cast(probe); |
| 152 return Handle<Code>::null(); | 145 return Handle<Code>::null(); |
| 153 } | 146 } |
| 154 | 147 |
| 155 | 148 |
| 156 Handle<Code> StubCache::ComputeMonomorphicIC(Handle<HeapObject> receiver, | 149 Handle<Code> StubCache::ComputeMonomorphicIC(Handle<HeapObject> receiver, |
| 157 Handle<Code> handler, | 150 Handle<Code> handler, |
| 158 Handle<Name> name, | 151 Handle<Name> name, |
| 159 StrictModeFlag strict_mode) { | 152 StrictModeFlag strict_mode) { |
| 160 Code::Kind kind = handler->handler_kind(); | 153 Code::Kind kind = handler->handler_kind(); |
| 161 Handle<Map> map(receiver->map()); | 154 Handle<Map> map(receiver->map()); |
| 162 Handle<Code> ic = FindIC(name, map, kind, handler->type(), strict_mode); | 155 Handle<Code> ic = FindIC(name, map, kind, strict_mode); |
| 163 if (!ic.is_null()) return ic; | 156 if (!ic.is_null()) return ic; |
| 164 | 157 |
| 165 if (kind == Code::LOAD_IC) { | 158 if (kind == Code::LOAD_IC) { |
| 166 LoadStubCompiler ic_compiler(isolate()); | 159 LoadStubCompiler ic_compiler(isolate()); |
| 167 ic = ic_compiler.CompileMonomorphicIC(map, handler, name); | 160 ic = ic_compiler.CompileMonomorphicIC(map, handler, name); |
| 168 } else if (kind == Code::KEYED_LOAD_IC) { | 161 } else if (kind == Code::KEYED_LOAD_IC) { |
| 169 KeyedLoadStubCompiler ic_compiler(isolate()); | 162 KeyedLoadStubCompiler ic_compiler(isolate()); |
| 170 ic = ic_compiler.CompileMonomorphicIC(map, handler, name); | 163 ic = ic_compiler.CompileMonomorphicIC(map, handler, name); |
| 171 } else if (kind == Code::STORE_IC) { | 164 } else if (kind == Code::STORE_IC) { |
| 172 StoreStubCompiler ic_compiler(isolate(), strict_mode); | 165 StoreStubCompiler ic_compiler(isolate(), strict_mode); |
| (...skipping 27 matching lines...) Expand all Loading... |
| 200 if (current->IsGlobalObject()) { | 193 if (current->IsGlobalObject()) { |
| 201 global = Handle<GlobalObject>::cast(current); | 194 global = Handle<GlobalObject>::cast(current); |
| 202 cache_name = name; | 195 cache_name = name; |
| 203 } else if (!current->HasFastProperties()) { | 196 } else if (!current->HasFastProperties()) { |
| 204 cache_name = name; | 197 cache_name = name; |
| 205 } | 198 } |
| 206 } while (!next->IsNull()); | 199 } while (!next->IsNull()); |
| 207 | 200 |
| 208 // Compile the stub that is either shared for all names or | 201 // Compile the stub that is either shared for all names or |
| 209 // name specific if there are global objects involved. | 202 // name specific if there are global objects involved. |
| 210 Handle<Code> handler = FindLoadHandler( | 203 Handle<Code> handler = FindLoadHandler(cache_name, receiver, Code::LOAD_IC); |
| 211 cache_name, receiver, Code::LOAD_IC, Code::NONEXISTENT); | |
| 212 if (!handler.is_null()) return handler; | 204 if (!handler.is_null()) return handler; |
| 213 | 205 |
| 214 LoadStubCompiler compiler(isolate_); | 206 LoadStubCompiler compiler(isolate_); |
| 215 handler = | 207 handler = |
| 216 compiler.CompileLoadNonexistent(receiver, current, cache_name, global); | 208 compiler.CompileLoadNonexistent(receiver, current, cache_name, global); |
| 217 HeapObject::UpdateMapCodeCache(receiver, cache_name, handler); | 209 HeapObject::UpdateMapCodeCache(receiver, cache_name, handler); |
| 218 return handler; | 210 return handler; |
| 219 } | 211 } |
| 220 | 212 |
| 221 | 213 |
| 222 Handle<Code> StubCache::ComputeLoadField(Handle<Name> name, | 214 Handle<Code> StubCache::ComputeLoadField(Handle<Name> name, |
| 223 Handle<JSObject> receiver, | 215 Handle<JSObject> receiver, |
| 224 Handle<JSObject> holder, | 216 Handle<JSObject> holder, |
| 225 PropertyIndex field, | 217 PropertyIndex field, |
| 226 Representation representation) { | 218 Representation representation) { |
| 227 if (receiver.is_identical_to(holder)) { | 219 if (receiver.is_identical_to(holder)) { |
| 228 LoadFieldStub stub(field.is_inobject(holder), | 220 LoadFieldStub stub(field.is_inobject(holder), |
| 229 field.translate(holder), | 221 field.translate(holder), |
| 230 representation); | 222 representation); |
| 231 return stub.GetCode(isolate()); | 223 return stub.GetCode(isolate()); |
| 232 } | 224 } |
| 233 | 225 |
| 234 Handle<Code> stub = FindLoadHandler( | 226 Handle<Code> stub = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 235 name, receiver, Code::LOAD_IC, Code::FIELD); | |
| 236 if (!stub.is_null()) return stub; | 227 if (!stub.is_null()) return stub; |
| 237 | 228 |
| 238 LoadStubCompiler compiler(isolate_); | 229 LoadStubCompiler compiler(isolate_); |
| 239 Handle<Code> handler = | 230 Handle<Code> handler = |
| 240 compiler.CompileLoadField(receiver, holder, name, field, representation); | 231 compiler.CompileLoadField(receiver, holder, name, field, representation); |
| 241 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 232 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 242 return handler; | 233 return handler; |
| 243 } | 234 } |
| 244 | 235 |
| 245 | 236 |
| 246 Handle<Code> StubCache::ComputeLoadCallback( | 237 Handle<Code> StubCache::ComputeLoadCallback( |
| 247 Handle<Name> name, | 238 Handle<Name> name, |
| 248 Handle<JSObject> receiver, | 239 Handle<JSObject> receiver, |
| 249 Handle<JSObject> holder, | 240 Handle<JSObject> holder, |
| 250 Handle<ExecutableAccessorInfo> callback) { | 241 Handle<ExecutableAccessorInfo> callback) { |
| 251 ASSERT(v8::ToCData<Address>(callback->getter()) != 0); | 242 ASSERT(v8::ToCData<Address>(callback->getter()) != 0); |
| 252 Handle<Code> stub = FindLoadHandler( | 243 Handle<Code> stub = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 253 name, receiver, Code::LOAD_IC, Code::CALLBACKS); | |
| 254 if (!stub.is_null()) return stub; | 244 if (!stub.is_null()) return stub; |
| 255 | 245 |
| 256 LoadStubCompiler compiler(isolate_); | 246 LoadStubCompiler compiler(isolate_); |
| 257 Handle<Code> handler = | 247 Handle<Code> handler = |
| 258 compiler.CompileLoadCallback(receiver, holder, name, callback); | 248 compiler.CompileLoadCallback(receiver, holder, name, callback); |
| 259 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 249 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 260 return handler; | 250 return handler; |
| 261 } | 251 } |
| 262 | 252 |
| 263 | 253 |
| 264 Handle<Code> StubCache::ComputeLoadCallback( | 254 Handle<Code> StubCache::ComputeLoadCallback( |
| 265 Handle<Name> name, | 255 Handle<Name> name, |
| 266 Handle<JSObject> receiver, | 256 Handle<JSObject> receiver, |
| 267 Handle<JSObject> holder, | 257 Handle<JSObject> holder, |
| 268 const CallOptimization& call_optimization) { | 258 const CallOptimization& call_optimization) { |
| 269 Handle<Code> stub = FindLoadHandler( | 259 Handle<Code> stub = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 270 name, receiver, Code::LOAD_IC, Code::CALLBACKS); | |
| 271 if (!stub.is_null()) return stub; | 260 if (!stub.is_null()) return stub; |
| 272 | 261 |
| 273 LoadStubCompiler compiler(isolate_); | 262 LoadStubCompiler compiler(isolate_); |
| 274 Handle<Code> handler = | 263 Handle<Code> handler = |
| 275 compiler.CompileLoadCallback(receiver, holder, name, call_optimization); | 264 compiler.CompileLoadCallback(receiver, holder, name, call_optimization); |
| 276 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 265 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 277 return handler; | 266 return handler; |
| 278 } | 267 } |
| 279 | 268 |
| 280 | 269 |
| 281 Handle<Code> StubCache::ComputeLoadViaGetter(Handle<Name> name, | 270 Handle<Code> StubCache::ComputeLoadViaGetter(Handle<Name> name, |
| 282 Handle<JSObject> receiver, | 271 Handle<JSObject> receiver, |
| 283 Handle<JSObject> holder, | 272 Handle<JSObject> holder, |
| 284 Handle<JSFunction> getter) { | 273 Handle<JSFunction> getter) { |
| 285 Handle<Code> stub = FindLoadHandler( | 274 Handle<Code> stub = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 286 name, receiver, Code::LOAD_IC, Code::CALLBACKS); | |
| 287 if (!stub.is_null()) return stub; | 275 if (!stub.is_null()) return stub; |
| 288 | 276 |
| 289 LoadStubCompiler compiler(isolate_); | 277 LoadStubCompiler compiler(isolate_); |
| 290 Handle<Code> handler = | 278 Handle<Code> handler = |
| 291 compiler.CompileLoadViaGetter(receiver, holder, name, getter); | 279 compiler.CompileLoadViaGetter(receiver, holder, name, getter); |
| 292 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 280 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 293 return handler; | 281 return handler; |
| 294 } | 282 } |
| 295 | 283 |
| 296 | 284 |
| 297 Handle<Code> StubCache::ComputeLoadConstant(Handle<Name> name, | 285 Handle<Code> StubCache::ComputeLoadConstant(Handle<Name> name, |
| 298 Handle<JSObject> receiver, | 286 Handle<JSObject> receiver, |
| 299 Handle<JSObject> holder, | 287 Handle<JSObject> holder, |
| 300 Handle<Object> value) { | 288 Handle<Object> value) { |
| 301 Handle<Code> handler = FindLoadHandler( | 289 Handle<Code> handler = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 302 name, receiver, Code::LOAD_IC, Code::CONSTANT); | |
| 303 if (!handler.is_null()) return handler; | 290 if (!handler.is_null()) return handler; |
| 304 | 291 |
| 305 LoadStubCompiler compiler(isolate_); | 292 LoadStubCompiler compiler(isolate_); |
| 306 handler = compiler.CompileLoadConstant(receiver, holder, name, value); | 293 handler = compiler.CompileLoadConstant(receiver, holder, name, value); |
| 307 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 294 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 308 | 295 |
| 309 return handler; | 296 return handler; |
| 310 } | 297 } |
| 311 | 298 |
| 312 | 299 |
| 313 Handle<Code> StubCache::ComputeLoadInterceptor(Handle<Name> name, | 300 Handle<Code> StubCache::ComputeLoadInterceptor(Handle<Name> name, |
| 314 Handle<JSObject> receiver, | 301 Handle<JSObject> receiver, |
| 315 Handle<JSObject> holder) { | 302 Handle<JSObject> holder) { |
| 316 Handle<Code> stub = FindLoadHandler( | 303 Handle<Code> stub = FindLoadHandler(name, receiver, Code::LOAD_IC); |
| 317 name, receiver, Code::LOAD_IC, Code::INTERCEPTOR); | |
| 318 if (!stub.is_null()) return stub; | 304 if (!stub.is_null()) return stub; |
| 319 | 305 |
| 320 LoadStubCompiler compiler(isolate_); | 306 LoadStubCompiler compiler(isolate_); |
| 321 Handle<Code> handler = | 307 Handle<Code> handler = |
| 322 compiler.CompileLoadInterceptor(receiver, holder, name); | 308 compiler.CompileLoadInterceptor(receiver, holder, name); |
| 323 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 309 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 324 return handler; | 310 return handler; |
| 325 } | 311 } |
| 326 | 312 |
| 327 | 313 |
| 328 Handle<Code> StubCache::ComputeLoadNormal(Handle<Name> name, | 314 Handle<Code> StubCache::ComputeLoadNormal(Handle<Name> name, |
| 329 Handle<JSObject> receiver) { | 315 Handle<JSObject> receiver) { |
| 330 return isolate_->builtins()->LoadIC_Normal(); | 316 return isolate_->builtins()->LoadIC_Normal(); |
| 331 } | 317 } |
| 332 | 318 |
| 333 | 319 |
| 334 Handle<Code> StubCache::ComputeLoadGlobal(Handle<Name> name, | 320 Handle<Code> StubCache::ComputeLoadGlobal(Handle<Name> name, |
| 335 Handle<JSObject> receiver, | 321 Handle<JSObject> receiver, |
| 336 Handle<GlobalObject> holder, | 322 Handle<GlobalObject> holder, |
| 337 Handle<PropertyCell> cell, | 323 Handle<PropertyCell> cell, |
| 338 bool is_dont_delete) { | 324 bool is_dont_delete) { |
| 339 Handle<Code> stub = FindIC(name, receiver, Code::LOAD_IC, Code::NORMAL); | 325 Handle<Code> stub = FindIC(name, receiver, Code::LOAD_IC); |
| 340 if (!stub.is_null()) return stub; | 326 if (!stub.is_null()) return stub; |
| 341 | 327 |
| 342 LoadStubCompiler compiler(isolate_); | 328 LoadStubCompiler compiler(isolate_); |
| 343 Handle<Code> ic = | 329 Handle<Code> ic = |
| 344 compiler.CompileLoadGlobal(receiver, holder, cell, name, is_dont_delete); | 330 compiler.CompileLoadGlobal(receiver, holder, cell, name, is_dont_delete); |
| 345 HeapObject::UpdateMapCodeCache(receiver, name, ic); | 331 HeapObject::UpdateMapCodeCache(receiver, name, ic); |
| 346 return ic; | 332 return ic; |
| 347 } | 333 } |
| 348 | 334 |
| 349 | 335 |
| 350 Handle<Code> StubCache::ComputeKeyedLoadField(Handle<Name> name, | 336 Handle<Code> StubCache::ComputeKeyedLoadField(Handle<Name> name, |
| 351 Handle<JSObject> receiver, | 337 Handle<JSObject> receiver, |
| 352 Handle<JSObject> holder, | 338 Handle<JSObject> holder, |
| 353 PropertyIndex field, | 339 PropertyIndex field, |
| 354 Representation representation) { | 340 Representation representation) { |
| 355 if (receiver.is_identical_to(holder)) { | 341 if (receiver.is_identical_to(holder)) { |
| 356 // TODO(titzer): this should use an HObjectAccess | 342 // TODO(titzer): this should use an HObjectAccess |
| 357 KeyedLoadFieldStub stub(field.is_inobject(holder), | 343 KeyedLoadFieldStub stub(field.is_inobject(holder), |
| 358 field.translate(holder), | 344 field.translate(holder), |
| 359 representation); | 345 representation); |
| 360 return stub.GetCode(isolate()); | 346 return stub.GetCode(isolate()); |
| 361 } | 347 } |
| 362 | 348 |
| 363 Handle<Code> stub = FindLoadHandler( | 349 Handle<Code> stub = FindLoadHandler(name, receiver, Code::KEYED_LOAD_IC); |
| 364 name, receiver, Code::KEYED_LOAD_IC, Code::FIELD); | |
| 365 if (!stub.is_null()) return stub; | 350 if (!stub.is_null()) return stub; |
| 366 | 351 |
| 367 KeyedLoadStubCompiler compiler(isolate_); | 352 KeyedLoadStubCompiler compiler(isolate_); |
| 368 Handle<Code> handler = | 353 Handle<Code> handler = |
| 369 compiler.CompileLoadField(receiver, holder, name, field, representation); | 354 compiler.CompileLoadField(receiver, holder, name, field, representation); |
| 370 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 355 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 371 return handler; | 356 return handler; |
| 372 } | 357 } |
| 373 | 358 |
| 374 | 359 |
| 375 Handle<Code> StubCache::ComputeKeyedLoadConstant(Handle<Name> name, | 360 Handle<Code> StubCache::ComputeKeyedLoadConstant(Handle<Name> name, |
| 376 Handle<JSObject> receiver, | 361 Handle<JSObject> receiver, |
| 377 Handle<JSObject> holder, | 362 Handle<JSObject> holder, |
| 378 Handle<Object> value) { | 363 Handle<Object> value) { |
| 379 Handle<Code> handler = FindLoadHandler( | 364 Handle<Code> handler = FindLoadHandler(name, receiver, Code::KEYED_LOAD_IC); |
| 380 name, receiver, Code::KEYED_LOAD_IC, Code::CONSTANT); | |
| 381 if (!handler.is_null()) return handler; | 365 if (!handler.is_null()) return handler; |
| 382 | 366 |
| 383 KeyedLoadStubCompiler compiler(isolate_); | 367 KeyedLoadStubCompiler compiler(isolate_); |
| 384 handler = compiler.CompileLoadConstant(receiver, holder, name, value); | 368 handler = compiler.CompileLoadConstant(receiver, holder, name, value); |
| 385 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 369 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 386 return handler; | 370 return handler; |
| 387 } | 371 } |
| 388 | 372 |
| 389 | 373 |
| 390 Handle<Code> StubCache::ComputeKeyedLoadInterceptor(Handle<Name> name, | 374 Handle<Code> StubCache::ComputeKeyedLoadInterceptor(Handle<Name> name, |
| 391 Handle<JSObject> receiver, | 375 Handle<JSObject> receiver, |
| 392 Handle<JSObject> holder) { | 376 Handle<JSObject> holder) { |
| 393 Handle<Code> stub = FindLoadHandler( | 377 Handle<Code> stub = FindLoadHandler(name, receiver, Code::KEYED_LOAD_IC); |
| 394 name, receiver, Code::KEYED_LOAD_IC, Code::INTERCEPTOR); | |
| 395 if (!stub.is_null()) return stub; | 378 if (!stub.is_null()) return stub; |
| 396 | 379 |
| 397 KeyedLoadStubCompiler compiler(isolate_); | 380 KeyedLoadStubCompiler compiler(isolate_); |
| 398 Handle<Code> handler = | 381 Handle<Code> handler = |
| 399 compiler.CompileLoadInterceptor(receiver, holder, name); | 382 compiler.CompileLoadInterceptor(receiver, holder, name); |
| 400 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 383 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 401 return handler; | 384 return handler; |
| 402 } | 385 } |
| 403 | 386 |
| 404 | 387 |
| 405 Handle<Code> StubCache::ComputeKeyedLoadCallback( | 388 Handle<Code> StubCache::ComputeKeyedLoadCallback( |
| 406 Handle<Name> name, | 389 Handle<Name> name, |
| 407 Handle<JSObject> receiver, | 390 Handle<JSObject> receiver, |
| 408 Handle<JSObject> holder, | 391 Handle<JSObject> holder, |
| 409 Handle<ExecutableAccessorInfo> callback) { | 392 Handle<ExecutableAccessorInfo> callback) { |
| 410 Handle<Code> stub = FindLoadHandler( | 393 Handle<Code> stub = FindLoadHandler(name, receiver, Code::KEYED_LOAD_IC); |
| 411 name, receiver, Code::KEYED_LOAD_IC, Code::CALLBACKS); | |
| 412 if (!stub.is_null()) return stub; | 394 if (!stub.is_null()) return stub; |
| 413 | 395 |
| 414 KeyedLoadStubCompiler compiler(isolate_); | 396 KeyedLoadStubCompiler compiler(isolate_); |
| 415 Handle<Code> handler = | 397 Handle<Code> handler = |
| 416 compiler.CompileLoadCallback(receiver, holder, name, callback); | 398 compiler.CompileLoadCallback(receiver, holder, name, callback); |
| 417 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 399 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 418 return handler; | 400 return handler; |
| 419 } | 401 } |
| 420 | 402 |
| 421 | 403 |
| 422 Handle<Code> StubCache::ComputeKeyedLoadCallback( | 404 Handle<Code> StubCache::ComputeKeyedLoadCallback( |
| 423 Handle<Name> name, | 405 Handle<Name> name, |
| 424 Handle<JSObject> receiver, | 406 Handle<JSObject> receiver, |
| 425 Handle<JSObject> holder, | 407 Handle<JSObject> holder, |
| 426 const CallOptimization& call_optimization) { | 408 const CallOptimization& call_optimization) { |
| 427 Handle<Code> stub = FindLoadHandler( | 409 Handle<Code> stub = FindLoadHandler(name, receiver, Code::KEYED_LOAD_IC); |
| 428 name, receiver, Code::KEYED_LOAD_IC, Code::CALLBACKS); | |
| 429 if (!stub.is_null()) return stub; | 410 if (!stub.is_null()) return stub; |
| 430 | 411 |
| 431 KeyedLoadStubCompiler compiler(isolate_); | 412 KeyedLoadStubCompiler compiler(isolate_); |
| 432 Handle<Code> handler = | 413 Handle<Code> handler = |
| 433 compiler.CompileLoadCallback(receiver, holder, name, call_optimization); | 414 compiler.CompileLoadCallback(receiver, holder, name, call_optimization); |
| 434 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 415 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 435 return handler; | 416 return handler; |
| 436 } | 417 } |
| 437 | 418 |
| 438 | 419 |
| 439 Handle<Code> StubCache::ComputeStoreField(Handle<Name> name, | 420 Handle<Code> StubCache::ComputeStoreField(Handle<Name> name, |
| 440 Handle<JSObject> receiver, | 421 Handle<JSObject> receiver, |
| 441 LookupResult* lookup, | 422 LookupResult* lookup, |
| 442 StrictModeFlag strict_mode) { | 423 StrictModeFlag strict_mode) { |
| 443 Handle<Code> stub = FindStoreHandler( | 424 Handle<Code> stub = FindStoreHandler( |
| 444 name, receiver, Code::STORE_IC, Code::FIELD, strict_mode); | 425 name, receiver, Code::STORE_IC, strict_mode); |
| 445 if (!stub.is_null()) return stub; | 426 if (!stub.is_null()) return stub; |
| 446 | 427 |
| 447 StoreStubCompiler compiler(isolate_, strict_mode); | 428 StoreStubCompiler compiler(isolate_, strict_mode); |
| 448 Handle<Code> handler = compiler.CompileStoreField(receiver, lookup, name); | 429 Handle<Code> handler = compiler.CompileStoreField(receiver, lookup, name); |
| 449 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 430 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 450 return handler; | 431 return handler; |
| 451 } | 432 } |
| 452 | 433 |
| 453 | 434 |
| 454 Handle<Code> StubCache::ComputeStoreTransition(Handle<Name> name, | 435 Handle<Code> StubCache::ComputeStoreTransition(Handle<Name> name, |
| 455 Handle<JSObject> receiver, | 436 Handle<JSObject> receiver, |
| 456 LookupResult* lookup, | 437 LookupResult* lookup, |
| 457 Handle<Map> transition, | 438 Handle<Map> transition, |
| 458 StrictModeFlag strict_mode) { | 439 StrictModeFlag strict_mode) { |
| 459 Handle<Code> stub = FindStoreHandler( | 440 Handle<Code> stub = FindStoreHandler( |
| 460 name, receiver, Code::STORE_IC, Code::TRANSITION, strict_mode); | 441 name, receiver, Code::STORE_IC, strict_mode); |
| 461 if (!stub.is_null()) return stub; | 442 if (!stub.is_null()) return stub; |
| 462 | 443 |
| 463 StoreStubCompiler compiler(isolate_, strict_mode); | 444 StoreStubCompiler compiler(isolate_, strict_mode); |
| 464 Handle<Code> handler = | 445 Handle<Code> handler = |
| 465 compiler.CompileStoreTransition(receiver, lookup, transition, name); | 446 compiler.CompileStoreTransition(receiver, lookup, transition, name); |
| 466 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 447 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 467 return handler; | 448 return handler; |
| 468 } | 449 } |
| 469 | 450 |
| 470 | 451 |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 524 Handle<PropertyCell> cell, | 505 Handle<PropertyCell> cell, |
| 525 Handle<Object> value, | 506 Handle<Object> value, |
| 526 StrictModeFlag strict_mode) { | 507 StrictModeFlag strict_mode) { |
| 527 Isolate* isolate = cell->GetIsolate(); | 508 Isolate* isolate = cell->GetIsolate(); |
| 528 Handle<Type> union_type(PropertyCell::UpdateType(cell, value), isolate); | 509 Handle<Type> union_type(PropertyCell::UpdateType(cell, value), isolate); |
| 529 bool is_constant = union_type->IsConstant(); | 510 bool is_constant = union_type->IsConstant(); |
| 530 StoreGlobalStub stub(strict_mode, is_constant); | 511 StoreGlobalStub stub(strict_mode, is_constant); |
| 531 | 512 |
| 532 Handle<Code> code = FindIC( | 513 Handle<Code> code = FindIC( |
| 533 name, Handle<JSObject>::cast(receiver), | 514 name, Handle<JSObject>::cast(receiver), |
| 534 Code::STORE_IC, Code::NORMAL, stub.GetExtraICState()); | 515 Code::STORE_IC, stub.GetExtraICState()); |
| 535 if (!code.is_null()) return code; | 516 if (!code.is_null()) return code; |
| 536 | 517 |
| 537 // Replace the placeholder cell and global object map with the actual global | 518 // Replace the placeholder cell and global object map with the actual global |
| 538 // cell and receiver map. | 519 // cell and receiver map. |
| 539 Handle<Map> meta_map(isolate_->heap()->meta_map()); | 520 Handle<Map> meta_map(isolate_->heap()->meta_map()); |
| 540 Handle<Object> receiver_map(receiver->map(), isolate_); | 521 Handle<Object> receiver_map(receiver->map(), isolate_); |
| 541 code = stub.GetCodeCopyFromTemplate(isolate_); | 522 code = stub.GetCodeCopyFromTemplate(isolate_); |
| 542 code->ReplaceNthObject(1, *meta_map, *receiver_map); | 523 code->ReplaceNthObject(1, *meta_map, *receiver_map); |
| 543 Handle<Map> cell_map(isolate_->heap()->global_property_cell_map()); | 524 Handle<Map> cell_map(isolate_->heap()->global_property_cell_map()); |
| 544 code->ReplaceNthObject(1, *cell_map, *cell); | 525 code->ReplaceNthObject(1, *cell_map, *cell); |
| 545 | 526 |
| 546 HeapObject::UpdateMapCodeCache(receiver, name, code); | 527 HeapObject::UpdateMapCodeCache(receiver, name, code); |
| 547 | 528 |
| 548 return code; | 529 return code; |
| 549 } | 530 } |
| 550 | 531 |
| 551 | 532 |
| 552 Handle<Code> StubCache::ComputeStoreCallback( | 533 Handle<Code> StubCache::ComputeStoreCallback( |
| 553 Handle<Name> name, | 534 Handle<Name> name, |
| 554 Handle<JSObject> receiver, | 535 Handle<JSObject> receiver, |
| 555 Handle<JSObject> holder, | 536 Handle<JSObject> holder, |
| 556 Handle<ExecutableAccessorInfo> callback, | 537 Handle<ExecutableAccessorInfo> callback, |
| 557 StrictModeFlag strict_mode) { | 538 StrictModeFlag strict_mode) { |
| 558 ASSERT(v8::ToCData<Address>(callback->setter()) != 0); | 539 ASSERT(v8::ToCData<Address>(callback->setter()) != 0); |
| 559 Handle<Code> stub = FindStoreHandler( | 540 Handle<Code> stub = FindStoreHandler( |
| 560 name, receiver, Code::STORE_IC, Code::CALLBACKS, strict_mode); | 541 name, receiver, Code::STORE_IC, strict_mode); |
| 561 if (!stub.is_null()) return stub; | 542 if (!stub.is_null()) return stub; |
| 562 | 543 |
| 563 StoreStubCompiler compiler(isolate_, strict_mode); | 544 StoreStubCompiler compiler(isolate_, strict_mode); |
| 564 Handle<Code> handler = compiler.CompileStoreCallback( | 545 Handle<Code> handler = compiler.CompileStoreCallback( |
| 565 receiver, holder, name, callback); | 546 receiver, holder, name, callback); |
| 566 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 547 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 567 return handler; | 548 return handler; |
| 568 } | 549 } |
| 569 | 550 |
| 570 | 551 |
| 571 Handle<Code> StubCache::ComputeStoreCallback( | 552 Handle<Code> StubCache::ComputeStoreCallback( |
| 572 Handle<Name> name, | 553 Handle<Name> name, |
| 573 Handle<JSObject> receiver, | 554 Handle<JSObject> receiver, |
| 574 Handle<JSObject> holder, | 555 Handle<JSObject> holder, |
| 575 const CallOptimization& call_optimization, | 556 const CallOptimization& call_optimization, |
| 576 StrictModeFlag strict_mode) { | 557 StrictModeFlag strict_mode) { |
| 577 Handle<Code> stub = FindStoreHandler( | 558 Handle<Code> stub = FindStoreHandler( |
| 578 name, receiver, Code::STORE_IC, Code::CALLBACKS, strict_mode); | 559 name, receiver, Code::STORE_IC, strict_mode); |
| 579 if (!stub.is_null()) return stub; | 560 if (!stub.is_null()) return stub; |
| 580 | 561 |
| 581 StoreStubCompiler compiler(isolate_, strict_mode); | 562 StoreStubCompiler compiler(isolate_, strict_mode); |
| 582 Handle<Code> handler = compiler.CompileStoreCallback( | 563 Handle<Code> handler = compiler.CompileStoreCallback( |
| 583 receiver, holder, name, call_optimization); | 564 receiver, holder, name, call_optimization); |
| 584 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 565 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 585 return handler; | 566 return handler; |
| 586 } | 567 } |
| 587 | 568 |
| 588 | 569 |
| 589 Handle<Code> StubCache::ComputeStoreViaSetter(Handle<Name> name, | 570 Handle<Code> StubCache::ComputeStoreViaSetter(Handle<Name> name, |
| 590 Handle<JSObject> receiver, | 571 Handle<JSObject> receiver, |
| 591 Handle<JSObject> holder, | 572 Handle<JSObject> holder, |
| 592 Handle<JSFunction> setter, | 573 Handle<JSFunction> setter, |
| 593 StrictModeFlag strict_mode) { | 574 StrictModeFlag strict_mode) { |
| 594 Handle<Code> stub = FindStoreHandler( | 575 Handle<Code> stub = FindStoreHandler( |
| 595 name, receiver, Code::STORE_IC, Code::CALLBACKS, strict_mode); | 576 name, receiver, Code::STORE_IC, strict_mode); |
| 596 if (!stub.is_null()) return stub; | 577 if (!stub.is_null()) return stub; |
| 597 | 578 |
| 598 StoreStubCompiler compiler(isolate_, strict_mode); | 579 StoreStubCompiler compiler(isolate_, strict_mode); |
| 599 Handle<Code> handler = compiler.CompileStoreViaSetter( | 580 Handle<Code> handler = compiler.CompileStoreViaSetter( |
| 600 receiver, holder, name, setter); | 581 receiver, holder, name, setter); |
| 601 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 582 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 602 return handler; | 583 return handler; |
| 603 } | 584 } |
| 604 | 585 |
| 605 | 586 |
| 606 Handle<Code> StubCache::ComputeStoreInterceptor(Handle<Name> name, | 587 Handle<Code> StubCache::ComputeStoreInterceptor(Handle<Name> name, |
| 607 Handle<JSObject> receiver, | 588 Handle<JSObject> receiver, |
| 608 StrictModeFlag strict_mode) { | 589 StrictModeFlag strict_mode) { |
| 609 Handle<Code> stub = FindStoreHandler( | 590 Handle<Code> stub = FindStoreHandler( |
| 610 name, receiver, Code::STORE_IC, Code::INTERCEPTOR, strict_mode); | 591 name, receiver, Code::STORE_IC, strict_mode); |
| 611 if (!stub.is_null()) return stub; | 592 if (!stub.is_null()) return stub; |
| 612 | 593 |
| 613 StoreStubCompiler compiler(isolate_, strict_mode); | 594 StoreStubCompiler compiler(isolate_, strict_mode); |
| 614 Handle<Code> handler = compiler.CompileStoreInterceptor(receiver, name); | 595 Handle<Code> handler = compiler.CompileStoreInterceptor(receiver, name); |
| 615 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 596 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 616 return handler; | 597 return handler; |
| 617 } | 598 } |
| 618 | 599 |
| 619 | 600 |
| 620 Handle<Code> StubCache::ComputeKeyedStoreField(Handle<Name> name, | 601 Handle<Code> StubCache::ComputeKeyedStoreField(Handle<Name> name, |
| 621 Handle<JSObject> receiver, | 602 Handle<JSObject> receiver, |
| 622 LookupResult* lookup, | 603 LookupResult* lookup, |
| 623 StrictModeFlag strict_mode) { | 604 StrictModeFlag strict_mode) { |
| 624 Handle<Code> stub = FindStoreHandler( | 605 Handle<Code> stub = FindStoreHandler( |
| 625 name, receiver, Code::KEYED_STORE_IC, Code::FIELD, strict_mode); | 606 name, receiver, Code::KEYED_STORE_IC, strict_mode); |
| 626 if (!stub.is_null()) return stub; | 607 if (!stub.is_null()) return stub; |
| 627 | 608 |
| 628 KeyedStoreStubCompiler compiler(isolate(), strict_mode, STANDARD_STORE); | 609 KeyedStoreStubCompiler compiler(isolate(), strict_mode, STANDARD_STORE); |
| 629 Handle<Code> handler = compiler.CompileStoreField(receiver, lookup, name); | 610 Handle<Code> handler = compiler.CompileStoreField(receiver, lookup, name); |
| 630 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 611 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 631 return handler; | 612 return handler; |
| 632 } | 613 } |
| 633 | 614 |
| 634 | 615 |
| 635 Handle<Code> StubCache::ComputeKeyedStoreTransition( | 616 Handle<Code> StubCache::ComputeKeyedStoreTransition( |
| 636 Handle<Name> name, | 617 Handle<Name> name, |
| 637 Handle<JSObject> receiver, | 618 Handle<JSObject> receiver, |
| 638 LookupResult* lookup, | 619 LookupResult* lookup, |
| 639 Handle<Map> transition, | 620 Handle<Map> transition, |
| 640 StrictModeFlag strict_mode) { | 621 StrictModeFlag strict_mode) { |
| 641 Handle<Code> stub = FindStoreHandler( | 622 Handle<Code> stub = FindStoreHandler( |
| 642 name, receiver, Code::KEYED_STORE_IC, Code::TRANSITION, strict_mode); | 623 name, receiver, Code::KEYED_STORE_IC, strict_mode); |
| 643 if (!stub.is_null()) return stub; | 624 if (!stub.is_null()) return stub; |
| 644 | 625 |
| 645 KeyedStoreStubCompiler compiler(isolate(), strict_mode, STANDARD_STORE); | 626 KeyedStoreStubCompiler compiler(isolate(), strict_mode, STANDARD_STORE); |
| 646 Handle<Code> handler = | 627 Handle<Code> handler = |
| 647 compiler.CompileStoreTransition(receiver, lookup, transition, name); | 628 compiler.CompileStoreTransition(receiver, lookup, transition, name); |
| 648 HeapObject::UpdateMapCodeCache(receiver, name, handler); | 629 HeapObject::UpdateMapCodeCache(receiver, name, handler); |
| 649 return handler; | 630 return handler; |
| 650 } | 631 } |
| 651 | 632 |
| 652 | 633 |
| (...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 962 FillCache(isolate_, code); | 943 FillCache(isolate_, code); |
| 963 return code; | 944 return code; |
| 964 } | 945 } |
| 965 | 946 |
| 966 | 947 |
| 967 Handle<Code> StubCache::ComputeCompareNil(Handle<Map> receiver_map, | 948 Handle<Code> StubCache::ComputeCompareNil(Handle<Map> receiver_map, |
| 968 CompareNilICStub& stub) { | 949 CompareNilICStub& stub) { |
| 969 Handle<String> name(isolate_->heap()->empty_string()); | 950 Handle<String> name(isolate_->heap()->empty_string()); |
| 970 if (!receiver_map->is_shared()) { | 951 if (!receiver_map->is_shared()) { |
| 971 Handle<Code> cached_ic = FindIC(name, receiver_map, Code::COMPARE_NIL_IC, | 952 Handle<Code> cached_ic = FindIC(name, receiver_map, Code::COMPARE_NIL_IC, |
| 972 Code::NORMAL, stub.GetExtraICState()); | 953 stub.GetExtraICState()); |
| 973 if (!cached_ic.is_null()) return cached_ic; | 954 if (!cached_ic.is_null()) return cached_ic; |
| 974 } | 955 } |
| 975 | 956 |
| 976 Handle<Code> ic = stub.GetCodeCopyFromTemplate(isolate_); | 957 Handle<Code> ic = stub.GetCodeCopyFromTemplate(isolate_); |
| 977 ic->ReplaceNthObject(1, isolate_->heap()->meta_map(), *receiver_map); | 958 ic->ReplaceNthObject(1, isolate_->heap()->meta_map(), *receiver_map); |
| 978 | 959 |
| 979 if (!receiver_map->is_shared()) { | 960 if (!receiver_map->is_shared()) { |
| 980 Map::UpdateCodeCache(receiver_map, name, ic); | 961 Map::UpdateCodeCache(receiver_map, name, ic); |
| 981 } | 962 } |
| 982 | 963 |
| (...skipping 1185 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2168 Handle<FunctionTemplateInfo>( | 2149 Handle<FunctionTemplateInfo>( |
| 2169 FunctionTemplateInfo::cast(signature->receiver())); | 2150 FunctionTemplateInfo::cast(signature->receiver())); |
| 2170 } | 2151 } |
| 2171 } | 2152 } |
| 2172 | 2153 |
| 2173 is_simple_api_call_ = true; | 2154 is_simple_api_call_ = true; |
| 2174 } | 2155 } |
| 2175 | 2156 |
| 2176 | 2157 |
| 2177 } } // namespace v8::internal | 2158 } } // namespace v8::internal |
| OLD | NEW |