| OLD | NEW |
| 1 // Copyright 2010 the V8 project authors. All rights reserved. | 1 // Copyright 2010 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 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 71 | 71 |
| 72 Handle<Object> TypeFeedbackOracle::GetInfo(int pos) { | 72 Handle<Object> TypeFeedbackOracle::GetInfo(int pos) { |
| 73 int entry = dictionary_->FindEntry(pos); | 73 int entry = dictionary_->FindEntry(pos); |
| 74 return entry != NumberDictionary::kNotFound | 74 return entry != NumberDictionary::kNotFound |
| 75 ? Handle<Object>(dictionary_->ValueAt(entry)) | 75 ? Handle<Object>(dictionary_->ValueAt(entry)) |
| 76 : Factory::undefined_value(); | 76 : Factory::undefined_value(); |
| 77 } | 77 } |
| 78 | 78 |
| 79 | 79 |
| 80 bool TypeFeedbackOracle::LoadIsMonomorphic(Property* expr) { | 80 bool TypeFeedbackOracle::LoadIsMonomorphic(Property* expr) { |
| 81 return GetInfo(expr->position())->IsMap(); | 81 Handle<Object> map_or_code(GetInfo( expr->position())); |
| 82 if (map_or_code->IsMap()) return true; |
| 83 if (map_or_code->IsCode()) { |
| 84 Handle<Code> code(Code::cast(*map_or_code)); |
| 85 return code->kind() == Code::KEYED_EXTERNAL_ARRAY_LOAD_IC && |
| 86 code->FindFirstMap() != NULL; |
| 87 } |
| 88 return false; |
| 82 } | 89 } |
| 83 | 90 |
| 84 | 91 |
| 85 bool TypeFeedbackOracle:: StoreIsMonomorphic(Assignment* expr) { | 92 bool TypeFeedbackOracle::StoreIsMonomorphic(Assignment* expr) { |
| 86 return GetInfo(expr->position())->IsMap(); | 93 Handle<Object> map_or_code(GetInfo(expr->position())); |
| 94 if (map_or_code->IsMap()) return true; |
| 95 if (map_or_code->IsCode()) { |
| 96 Handle<Code> code(Code::cast(*map_or_code)); |
| 97 return code->kind() == Code::KEYED_EXTERNAL_ARRAY_STORE_IC && |
| 98 code->FindFirstMap() != NULL; |
| 99 } |
| 100 return false; |
| 87 } | 101 } |
| 88 | 102 |
| 89 | 103 |
| 90 bool TypeFeedbackOracle::CallIsMonomorphic(Call* expr) { | 104 bool TypeFeedbackOracle::CallIsMonomorphic(Call* expr) { |
| 91 Handle<Object> value = GetInfo(expr->position()); | 105 Handle<Object> value = GetInfo(expr->position()); |
| 92 return value->IsMap() || value->IsSmi(); | 106 return value->IsMap() || value->IsSmi(); |
| 93 } | 107 } |
| 94 | 108 |
| 95 | 109 |
| 96 Handle<Map> TypeFeedbackOracle::LoadMonomorphicReceiverType(Property* expr) { | 110 Handle<Map> TypeFeedbackOracle::LoadMonomorphicReceiverType(Property* expr) { |
| 97 ASSERT(LoadIsMonomorphic(expr)); | 111 ASSERT(LoadIsMonomorphic(expr)); |
| 98 return Handle<Map>::cast(GetInfo(expr->position())); | 112 Handle<Object> map_or_code( |
| 113 Handle<HeapObject>::cast(GetInfo(expr->position()))); |
| 114 if (map_or_code->IsCode()) { |
| 115 Handle<Code> code(Code::cast(*map_or_code)); |
| 116 return Handle<Map>(code->FindFirstMap()); |
| 117 } |
| 118 return Handle<Map>(Map::cast(*map_or_code)); |
| 99 } | 119 } |
| 100 | 120 |
| 101 | 121 |
| 102 Handle<Map> TypeFeedbackOracle::StoreMonomorphicReceiverType(Assignment* expr) { | 122 Handle<Map> TypeFeedbackOracle::StoreMonomorphicReceiverType(Assignment* expr) { |
| 103 ASSERT(StoreIsMonomorphic(expr)); | 123 ASSERT(StoreIsMonomorphic(expr)); |
| 104 return Handle<Map>::cast(GetInfo(expr->position())); | 124 Handle<HeapObject> map_or_code( |
| 125 Handle<HeapObject>::cast(GetInfo(expr->position()))); |
| 126 if (map_or_code->IsCode()) { |
| 127 Handle<Code> code(Code::cast(*map_or_code)); |
| 128 return Handle<Map>(code->FindFirstMap()); |
| 129 } |
| 130 return Handle<Map>(Map::cast(*map_or_code)); |
| 105 } | 131 } |
| 106 | 132 |
| 107 | 133 |
| 108 ZoneMapList* TypeFeedbackOracle::LoadReceiverTypes(Property* expr, | 134 ZoneMapList* TypeFeedbackOracle::LoadReceiverTypes(Property* expr, |
| 109 Handle<String> name) { | 135 Handle<String> name) { |
| 110 Code::Flags flags = Code::ComputeMonomorphicFlags(Code::LOAD_IC, NORMAL); | 136 Code::Flags flags = Code::ComputeMonomorphicFlags(Code::LOAD_IC, NORMAL); |
| 111 return CollectReceiverTypes(expr->position(), name, flags); | 137 return CollectReceiverTypes(expr->position(), name, flags); |
| 112 } | 138 } |
| 113 | 139 |
| 114 | 140 |
| (...skipping 22 matching lines...) Expand all Loading... |
| 137 | 163 |
| 138 | 164 |
| 139 CheckType TypeFeedbackOracle::GetCallCheckType(Call* expr) { | 165 CheckType TypeFeedbackOracle::GetCallCheckType(Call* expr) { |
| 140 Handle<Object> value = GetInfo(expr->position()); | 166 Handle<Object> value = GetInfo(expr->position()); |
| 141 if (!value->IsSmi()) return RECEIVER_MAP_CHECK; | 167 if (!value->IsSmi()) return RECEIVER_MAP_CHECK; |
| 142 CheckType check = static_cast<CheckType>(Smi::cast(*value)->value()); | 168 CheckType check = static_cast<CheckType>(Smi::cast(*value)->value()); |
| 143 ASSERT(check != RECEIVER_MAP_CHECK); | 169 ASSERT(check != RECEIVER_MAP_CHECK); |
| 144 return check; | 170 return check; |
| 145 } | 171 } |
| 146 | 172 |
| 173 ExternalArrayType TypeFeedbackOracle::GetKeyedLoadExternalArrayType( |
| 174 Property* expr) { |
| 175 Handle<Object> stub = GetInfo(expr->position()); |
| 176 ASSERT(stub->IsCode()); |
| 177 return Code::cast(*stub)->external_array_type(); |
| 178 } |
| 179 |
| 180 ExternalArrayType TypeFeedbackOracle::GetKeyedStoreExternalArrayType( |
| 181 Assignment* expr) { |
| 182 Handle<Object> stub = GetInfo(expr->position()); |
| 183 ASSERT(stub->IsCode()); |
| 184 return Code::cast(*stub)->external_array_type(); |
| 185 } |
| 147 | 186 |
| 148 Handle<JSObject> TypeFeedbackOracle::GetPrototypeForPrimitiveCheck( | 187 Handle<JSObject> TypeFeedbackOracle::GetPrototypeForPrimitiveCheck( |
| 149 CheckType check) { | 188 CheckType check) { |
| 150 JSFunction* function = NULL; | 189 JSFunction* function = NULL; |
| 151 switch (check) { | 190 switch (check) { |
| 152 case RECEIVER_MAP_CHECK: | 191 case RECEIVER_MAP_CHECK: |
| 153 UNREACHABLE(); | 192 UNREACHABLE(); |
| 154 break; | 193 break; |
| 155 case STRING_CHECK: | 194 case STRING_CHECK: |
| 156 function = global_context_->string_function(); | 195 function = global_context_->string_function(); |
| (...skipping 183 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 340 kind == Code::TYPE_RECORDING_BINARY_OP_IC || | 379 kind == Code::TYPE_RECORDING_BINARY_OP_IC || |
| 341 kind == Code::COMPARE_IC) { | 380 kind == Code::COMPARE_IC) { |
| 342 // TODO(kasperl): Avoid having multiple ICs with the same | 381 // TODO(kasperl): Avoid having multiple ICs with the same |
| 343 // position by making sure that we have position information | 382 // position by making sure that we have position information |
| 344 // recorded for all binary ICs. | 383 // recorded for all binary ICs. |
| 345 int entry = dictionary_->FindEntry(position); | 384 int entry = dictionary_->FindEntry(position); |
| 346 if (entry == NumberDictionary::kNotFound) { | 385 if (entry == NumberDictionary::kNotFound) { |
| 347 value = target; | 386 value = target; |
| 348 } | 387 } |
| 349 } else if (state == MONOMORPHIC) { | 388 } else if (state == MONOMORPHIC) { |
| 350 if (target->kind() != Code::CALL_IC || | 389 if (kind == Code::KEYED_EXTERNAL_ARRAY_LOAD_IC || |
| 351 target->check_type() == RECEIVER_MAP_CHECK) { | 390 kind == Code::KEYED_EXTERNAL_ARRAY_STORE_IC) { |
| 391 value = target; |
| 392 } else if (kind != Code::CALL_IC || |
| 393 target->check_type() == RECEIVER_MAP_CHECK) { |
| 352 Handle<Map> map = Handle<Map>(target->FindFirstMap()); | 394 Handle<Map> map = Handle<Map>(target->FindFirstMap()); |
| 353 if (*map == NULL) { | 395 if (*map == NULL) { |
| 354 value = target; | 396 value = target; |
| 355 } else { | 397 } else { |
| 356 value = map; | 398 value = map; |
| 357 } | 399 } |
| 358 } else { | 400 } else { |
| 359 ASSERT(target->kind() == Code::CALL_IC); | 401 ASSERT(target->kind() == Code::CALL_IC); |
| 360 CheckType check = target->check_type(); | 402 CheckType check = target->check_type(); |
| 361 ASSERT(check != RECEIVER_MAP_CHECK); | 403 ASSERT(check != RECEIVER_MAP_CHECK); |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 411 source_positions->Add(position); | 453 source_positions->Add(position); |
| 412 } | 454 } |
| 413 } else { | 455 } else { |
| 414 ASSERT(RelocInfo::IsPosition(mode)); | 456 ASSERT(RelocInfo::IsPosition(mode)); |
| 415 position = static_cast<int>(info->data()); | 457 position = static_cast<int>(info->data()); |
| 416 } | 458 } |
| 417 } | 459 } |
| 418 } | 460 } |
| 419 | 461 |
| 420 } } // namespace v8::internal | 462 } } // namespace v8::internal |
| OLD | NEW |