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 |