| 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/ast.h" | 5 #include "src/ast.h" |
| 6 | 6 |
| 7 #include <cmath> // For isfinite. | 7 #include <cmath> // For isfinite. |
| 8 #include "src/builtins.h" | 8 #include "src/builtins.h" |
| 9 #include "src/code-stubs.h" | 9 #include "src/code-stubs.h" |
| 10 #include "src/contexts.h" | 10 #include "src/contexts.h" |
| (...skipping 163 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 174 if (shared->start_position() == start_position()) { | 174 if (shared->start_position() == start_position()) { |
| 175 shared_info_ = Handle<SharedFunctionInfo>(shared); | 175 shared_info_ = Handle<SharedFunctionInfo>(shared); |
| 176 break; | 176 break; |
| 177 } | 177 } |
| 178 } | 178 } |
| 179 } | 179 } |
| 180 } | 180 } |
| 181 | 181 |
| 182 | 182 |
| 183 ObjectLiteralProperty::ObjectLiteralProperty( | 183 ObjectLiteralProperty::ObjectLiteralProperty( |
| 184 Zone* zone, Literal* key, Expression* value) { | 184 Zone* zone, Expression* key, Expression* value, bool is_computed_name) { |
| 185 emit_store_ = true; | 185 emit_store_ = true; |
| 186 key_ = key; | 186 key_ = key; |
| 187 value_ = value; | 187 value_ = value; |
| 188 Handle<Object> k = key->value(); | 188 if (is_computed_name) { |
| 189 if (k->IsInternalizedString() && | 189 kind_ = COMPUTED_NAME; |
| 190 String::Equals(Handle<String>::cast(k), | |
| 191 zone->isolate()->factory()->proto_string())) { | |
| 192 kind_ = PROTOTYPE; | |
| 193 } else if (value_->AsMaterializedLiteral() != NULL) { | |
| 194 kind_ = MATERIALIZED_LITERAL; | |
| 195 } else if (value_->IsLiteral()) { | |
| 196 kind_ = CONSTANT; | |
| 197 } else { | 190 } else { |
| 198 kind_ = COMPUTED; | 191 Handle<Object> k = key->AsLiteral()->value(); |
| 192 if (k->IsInternalizedString() && |
| 193 String::Equals(Handle<String>::cast(k), |
| 194 zone->isolate()->factory()->proto_string())) { |
| 195 kind_ = PROTOTYPE; |
| 196 } else if (value_->AsMaterializedLiteral() != NULL) { |
| 197 kind_ = MATERIALIZED_LITERAL; |
| 198 } else if (value_->IsLiteral()) { |
| 199 kind_ = CONSTANT; |
| 200 } else { |
| 201 kind_ = COMPUTED; |
| 202 } |
| 199 } | 203 } |
| 200 } | 204 } |
| 201 | 205 |
| 202 | 206 |
| 203 ObjectLiteralProperty::ObjectLiteralProperty( | 207 ObjectLiteralProperty::ObjectLiteralProperty( |
| 204 Zone* zone, bool is_getter, FunctionLiteral* value) { | 208 Zone* zone, bool is_getter, FunctionLiteral* value) { |
| 205 emit_store_ = true; | 209 emit_store_ = true; |
| 206 value_ = value; | 210 value_ = value; |
| 207 kind_ = is_getter ? GETTER : SETTER; | 211 kind_ = is_getter ? GETTER : SETTER; |
| 208 } | 212 } |
| (...skipping 16 matching lines...) Expand all Loading... |
| 225 } | 229 } |
| 226 | 230 |
| 227 | 231 |
| 228 void ObjectLiteral::CalculateEmitStore(Zone* zone) { | 232 void ObjectLiteral::CalculateEmitStore(Zone* zone) { |
| 229 ZoneAllocationPolicy allocator(zone); | 233 ZoneAllocationPolicy allocator(zone); |
| 230 | 234 |
| 231 ZoneHashMap table(Literal::Match, ZoneHashMap::kDefaultHashMapCapacity, | 235 ZoneHashMap table(Literal::Match, ZoneHashMap::kDefaultHashMapCapacity, |
| 232 allocator); | 236 allocator); |
| 233 for (int i = properties()->length() - 1; i >= 0; i--) { | 237 for (int i = properties()->length() - 1; i >= 0; i--) { |
| 234 ObjectLiteral::Property* property = properties()->at(i); | 238 ObjectLiteral::Property* property = properties()->at(i); |
| 235 Literal* literal = property->key(); | 239 if (property->kind() == ObjectLiteral::Property::COMPUTED_NAME) continue; |
| 240 Literal* literal = property->key()->AsLiteral(); |
| 236 if (literal->value()->IsNull()) continue; | 241 if (literal->value()->IsNull()) continue; |
| 237 uint32_t hash = literal->Hash(); | 242 uint32_t hash = literal->Hash(); |
| 238 // If the key of a computed property is in the table, do not emit | 243 // If the key of a computed property is in the table, do not emit |
| 239 // a store for the property later. | 244 // a store for the property later. |
| 240 if ((property->kind() == ObjectLiteral::Property::MATERIALIZED_LITERAL || | 245 if ((property->kind() == ObjectLiteral::Property::MATERIALIZED_LITERAL || |
| 241 property->kind() == ObjectLiteral::Property::COMPUTED) && | 246 property->kind() == ObjectLiteral::Property::COMPUTED) && |
| 242 table.Lookup(literal, hash, false, allocator) != NULL) { | 247 table.Lookup(literal, hash, false, allocator) != NULL) { |
| 243 property->set_emit_store(false); | 248 property->set_emit_store(false); |
| 244 } else { | 249 } else { |
| 245 // Add key to the table. | 250 // Add key to the table. |
| (...skipping 21 matching lines...) Expand all Loading... |
| 267 bool is_simple = true; | 272 bool is_simple = true; |
| 268 int depth_acc = 1; | 273 int depth_acc = 1; |
| 269 uint32_t max_element_index = 0; | 274 uint32_t max_element_index = 0; |
| 270 uint32_t elements = 0; | 275 uint32_t elements = 0; |
| 271 for (int i = 0; i < properties()->length(); i++) { | 276 for (int i = 0; i < properties()->length(); i++) { |
| 272 ObjectLiteral::Property* property = properties()->at(i); | 277 ObjectLiteral::Property* property = properties()->at(i); |
| 273 if (!IsBoilerplateProperty(property)) { | 278 if (!IsBoilerplateProperty(property)) { |
| 274 is_simple = false; | 279 is_simple = false; |
| 275 continue; | 280 continue; |
| 276 } | 281 } |
| 282 |
| 283 if (position == boilerplate_properties_ * 2) { |
| 284 // Constant properties stop at the first computed name. |
| 285 ASSERT(property->kind() == ObjectLiteral::Property::COMPUTED_NAME); |
| 286 break; |
| 287 } |
| 288 ASSERT(property->kind() != ObjectLiteral::Property::COMPUTED_NAME); |
| 289 |
| 277 MaterializedLiteral* m_literal = property->value()->AsMaterializedLiteral(); | 290 MaterializedLiteral* m_literal = property->value()->AsMaterializedLiteral(); |
| 278 if (m_literal != NULL) { | 291 if (m_literal != NULL) { |
| 279 m_literal->BuildConstants(isolate); | 292 m_literal->BuildConstants(isolate); |
| 280 if (m_literal->depth() >= depth_acc) depth_acc = m_literal->depth() + 1; | 293 if (m_literal->depth() >= depth_acc) depth_acc = m_literal->depth() + 1; |
| 281 } | 294 } |
| 282 | 295 |
| 283 // Add CONSTANT and COMPUTED properties to boilerplate. Use undefined | 296 // Add CONSTANT and COMPUTED properties to boilerplate. Use undefined |
| 284 // value for COMPUTED properties, the real value is filled in at | 297 // value for COMPUTED properties, the real value is filled in at |
| 285 // runtime. The enumeration order is maintained. | 298 // runtime. The enumeration order is maintained. |
| 286 Handle<Object> key = property->key()->value(); | 299 Handle<Object> key = property->key()->AsLiteral()->value(); |
| 287 Handle<Object> value = GetBoilerplateValue(property->value(), isolate); | 300 Handle<Object> value = GetBoilerplateValue(property->value(), isolate); |
| 288 | 301 |
| 289 // Ensure objects that may, at any point in time, contain fields with double | 302 // Ensure objects that may, at any point in time, contain fields with double |
| 290 // representation are always treated as nested objects. This is true for | 303 // representation are always treated as nested objects. This is true for |
| 291 // computed fields (value is undefined), and smi and double literals | 304 // computed fields (value is undefined), and smi and double literals |
| 292 // (value->IsNumber()). | 305 // (value->IsNumber()). |
| 293 // TODO(verwaest): Remove once we can store them inline. | 306 // TODO(verwaest): Remove once we can store them inline. |
| 294 if (FLAG_track_double_fields && | 307 if (FLAG_track_double_fields && |
| 295 (value->IsNumber() || value->IsUninitialized())) { | 308 (value->IsNumber() || value->IsUninitialized())) { |
| 296 may_store_doubles_ = true; | 309 may_store_doubles_ = true; |
| (...skipping 328 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 625 if (is_monomorphic_) { | 638 if (is_monomorphic_) { |
| 626 target_ = oracle->GetCallNewTarget(CallNewFeedbackSlot()); | 639 target_ = oracle->GetCallNewTarget(CallNewFeedbackSlot()); |
| 627 if (!allocation_site_.is_null()) { | 640 if (!allocation_site_.is_null()) { |
| 628 elements_kind_ = allocation_site_->GetElementsKind(); | 641 elements_kind_ = allocation_site_->GetElementsKind(); |
| 629 } | 642 } |
| 630 } | 643 } |
| 631 } | 644 } |
| 632 | 645 |
| 633 | 646 |
| 634 void ObjectLiteral::Property::RecordTypeFeedback(TypeFeedbackOracle* oracle) { | 647 void ObjectLiteral::Property::RecordTypeFeedback(TypeFeedbackOracle* oracle) { |
| 635 TypeFeedbackId id = key()->LiteralFeedbackId(); | 648 ASSERT(key()->IsLiteral()); |
| 649 TypeFeedbackId id = key()->AsLiteral()->LiteralFeedbackId(); |
| 636 SmallMapList maps; | 650 SmallMapList maps; |
| 637 oracle->CollectReceiverTypes(id, &maps); | 651 oracle->CollectReceiverTypes(id, &maps); |
| 638 receiver_type_ = maps.length() == 1 ? maps.at(0) | 652 receiver_type_ = maps.length() == 1 ? maps.at(0) |
| 639 : Handle<Map>::null(); | 653 : Handle<Map>::null(); |
| 640 } | 654 } |
| 641 | 655 |
| 642 | 656 |
| 643 // ---------------------------------------------------------------------------- | 657 // ---------------------------------------------------------------------------- |
| 644 // Implementation of AstVisitor | 658 // Implementation of AstVisitor |
| 645 | 659 |
| (...skipping 503 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1149 OS::SNPrintF(buffer, "%d", Smi::cast(*value_)->value()); | 1163 OS::SNPrintF(buffer, "%d", Smi::cast(*value_)->value()); |
| 1150 str = arr; | 1164 str = arr; |
| 1151 } else { | 1165 } else { |
| 1152 str = DoubleToCString(value_->Number(), buffer); | 1166 str = DoubleToCString(value_->Number(), buffer); |
| 1153 } | 1167 } |
| 1154 return isolate_->factory()->NewStringFromAsciiChecked(str); | 1168 return isolate_->factory()->NewStringFromAsciiChecked(str); |
| 1155 } | 1169 } |
| 1156 | 1170 |
| 1157 | 1171 |
| 1158 } } // namespace v8::internal | 1172 } } // namespace v8::internal |
| OLD | NEW |