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 #ifndef V8_HYDROGEN_INSTRUCTIONS_H_ | 5 #ifndef V8_HYDROGEN_INSTRUCTIONS_H_ |
6 #define V8_HYDROGEN_INSTRUCTIONS_H_ | 6 #define V8_HYDROGEN_INSTRUCTIONS_H_ |
7 | 7 |
8 #include "v8.h" | 8 #include "v8.h" |
9 | 9 |
10 #include "allocation.h" | 10 #include "allocation.h" |
(...skipping 6194 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6205 friend class SideEffectsTracker; | 6205 friend class SideEffectsTracker; |
6206 | 6206 |
6207 inline Portion portion() const { | 6207 inline Portion portion() const { |
6208 return PortionField::decode(value_); | 6208 return PortionField::decode(value_); |
6209 } | 6209 } |
6210 }; | 6210 }; |
6211 | 6211 |
6212 | 6212 |
6213 class HLoadNamedField V8_FINAL : public HTemplateInstruction<2> { | 6213 class HLoadNamedField V8_FINAL : public HTemplateInstruction<2> { |
6214 public: | 6214 public: |
6215 static HLoadNamedField* New(Zone* zone, HValue* context, | 6215 DECLARE_INSTRUCTION_FACTORY_P3(HLoadNamedField, HValue*, |
6216 HValue* object, HValue* dependency, | 6216 HValue*, HObjectAccess); |
6217 HObjectAccess access) { | 6217 DECLARE_INSTRUCTION_FACTORY_P5(HLoadNamedField, HValue*, HValue*, |
6218 return new(zone) HLoadNamedField( | 6218 HObjectAccess, const UniqueSet<Map>*, HType); |
6219 object, dependency, access, new(zone) UniqueSet<Map>()); | |
6220 } | |
6221 static HLoadNamedField* New(Zone* zone, HValue* context, | |
6222 HValue* object, HValue* dependency, | |
6223 HObjectAccess access, SmallMapList* map_list, | |
6224 CompilationInfo* info) { | |
6225 UniqueSet<Map>* maps = new(zone) UniqueSet<Map>(map_list->length(), zone); | |
6226 for (int i = 0; i < map_list->length(); ++i) { | |
6227 Handle<Map> map = map_list->at(i); | |
6228 maps->Add(Unique<Map>::CreateImmovable(map), zone); | |
6229 // TODO(bmeurer): Get rid of this shit! | |
6230 if (map->CanTransition()) { | |
6231 Map::AddDependentCompilationInfo( | |
6232 map, DependentCode::kPrototypeCheckGroup, info); | |
6233 } | |
6234 } | |
6235 return new(zone) HLoadNamedField(object, dependency, access, maps); | |
6236 } | |
6237 | 6219 |
6238 HValue* object() { return OperandAt(0); } | 6220 HValue* object() { return OperandAt(0); } |
6239 HValue* dependency() { | 6221 HValue* dependency() { |
6240 ASSERT(HasDependency()); | 6222 ASSERT(HasDependency()); |
6241 return OperandAt(1); | 6223 return OperandAt(1); |
6242 } | 6224 } |
6243 bool HasDependency() const { return OperandAt(0) != OperandAt(1); } | 6225 bool HasDependency() const { return OperandAt(0) != OperandAt(1); } |
6244 HObjectAccess access() const { return access_; } | 6226 HObjectAccess access() const { return access_; } |
6245 Representation field_representation() const { | 6227 Representation field_representation() const { |
6246 return access_.representation(); | 6228 return access_.representation(); |
6247 } | 6229 } |
6248 | 6230 |
6249 const UniqueSet<Map>* maps() const { return maps_; } | 6231 const UniqueSet<Map>* maps() const { return maps_; } |
6250 | 6232 |
6251 virtual bool HasEscapingOperandAt(int index) V8_OVERRIDE { return false; } | 6233 virtual bool HasEscapingOperandAt(int index) V8_OVERRIDE { return false; } |
6252 virtual bool HasOutOfBoundsAccess(int size) V8_OVERRIDE { | 6234 virtual bool HasOutOfBoundsAccess(int size) V8_OVERRIDE { |
6253 return !access().IsInobject() || access().offset() >= size; | 6235 return !access().IsInobject() || access().offset() >= size; |
6254 } | 6236 } |
6255 virtual Representation RequiredInputRepresentation(int index) V8_OVERRIDE { | 6237 virtual Representation RequiredInputRepresentation(int index) V8_OVERRIDE { |
6256 if (index == 0 && access().IsExternalMemory()) { | 6238 if (index == 0 && access().IsExternalMemory()) { |
6257 // object must be external in case of external memory access | 6239 // object must be external in case of external memory access |
6258 return Representation::External(); | 6240 return Representation::External(); |
6259 } | 6241 } |
6260 return Representation::Tagged(); | 6242 return Representation::Tagged(); |
6261 } | 6243 } |
6262 virtual Range* InferRange(Zone* zone) V8_OVERRIDE; | 6244 virtual Range* InferRange(Zone* zone) V8_OVERRIDE; |
6263 virtual void PrintDataTo(StringStream* stream) V8_OVERRIDE; | 6245 virtual void PrintDataTo(StringStream* stream) V8_OVERRIDE; |
6264 | 6246 |
| 6247 bool CanBeReplacedWith(HLoadNamedField* that) const { |
| 6248 if (this->maps_ == that->maps_) return true; |
| 6249 if (this->maps_ == NULL || that->maps_ == NULL) return false; |
| 6250 return this->maps_->IsSubset(that->maps_); |
| 6251 } |
| 6252 |
6265 DECLARE_CONCRETE_INSTRUCTION(LoadNamedField) | 6253 DECLARE_CONCRETE_INSTRUCTION(LoadNamedField) |
6266 | 6254 |
6267 protected: | 6255 protected: |
6268 virtual bool DataEquals(HValue* other) V8_OVERRIDE { | 6256 virtual bool DataEquals(HValue* other) V8_OVERRIDE { |
6269 HLoadNamedField* b = HLoadNamedField::cast(other); | 6257 HLoadNamedField* that = HLoadNamedField::cast(other); |
6270 return access_.Equals(b->access_) && this->maps()->Equals(b->maps()); | 6258 if (!this->access_.Equals(that->access_)) return false; |
| 6259 if (this->maps_ == that->maps_) return true; |
| 6260 return (this->maps_ != NULL && |
| 6261 that->maps_ != NULL && |
| 6262 this->maps_->Equals(that->maps_)); |
6271 } | 6263 } |
6272 | 6264 |
6273 private: | 6265 private: |
6274 HLoadNamedField(HValue* object, | 6266 HLoadNamedField(HValue* object, |
6275 HValue* dependency, | 6267 HValue* dependency, |
6276 HObjectAccess access, | 6268 HObjectAccess access) |
6277 const UniqueSet<Map>* maps) | 6269 : access_(access), maps_(NULL) { |
6278 : access_(access), maps_(maps) { | 6270 ASSERT_NOT_NULL(object); |
6279 ASSERT(object != NULL); | |
6280 SetOperandAt(0, object); | 6271 SetOperandAt(0, object); |
6281 SetOperandAt(1, dependency != NULL ? dependency : object); | 6272 SetOperandAt(1, dependency ? dependency : object); |
6282 | 6273 |
6283 Representation representation = access.representation(); | 6274 Representation representation = access.representation(); |
6284 if (representation.IsInteger8() || | 6275 if (representation.IsInteger8() || |
6285 representation.IsUInteger8() || | 6276 representation.IsUInteger8() || |
6286 representation.IsInteger16() || | 6277 representation.IsInteger16() || |
6287 representation.IsUInteger16()) { | 6278 representation.IsUInteger16()) { |
6288 set_representation(Representation::Integer32()); | 6279 set_representation(Representation::Integer32()); |
6289 } else if (representation.IsSmi()) { | 6280 } else if (representation.IsSmi()) { |
6290 set_type(HType::Smi()); | 6281 set_type(HType::Smi()); |
6291 if (SmiValuesAre32Bits()) { | 6282 if (SmiValuesAre32Bits()) { |
6292 set_representation(Representation::Integer32()); | 6283 set_representation(Representation::Integer32()); |
6293 } else { | 6284 } else { |
6294 set_representation(representation); | 6285 set_representation(representation); |
6295 } | 6286 } |
6296 } else if (representation.IsDouble() || | 6287 } else if (representation.IsDouble() || |
6297 representation.IsExternal() || | 6288 representation.IsExternal() || |
6298 representation.IsInteger32()) { | 6289 representation.IsInteger32()) { |
6299 set_representation(representation); | 6290 set_representation(representation); |
6300 } else if (representation.IsHeapObject()) { | 6291 } else if (representation.IsHeapObject()) { |
| 6292 // TODO(bmeurer): This is probably broken. What we actually want to to |
| 6293 // instead is set_representation(Representation::HeapObject()). |
6301 set_type(HType::NonPrimitive()); | 6294 set_type(HType::NonPrimitive()); |
6302 set_representation(Representation::Tagged()); | 6295 set_representation(Representation::Tagged()); |
6303 } else { | 6296 } else { |
6304 set_representation(Representation::Tagged()); | 6297 set_representation(Representation::Tagged()); |
6305 } | 6298 } |
6306 access.SetGVNFlags(this, LOAD); | 6299 access.SetGVNFlags(this, LOAD); |
6307 } | 6300 } |
6308 | 6301 |
| 6302 HLoadNamedField(HValue* object, |
| 6303 HValue* dependency, |
| 6304 HObjectAccess access, |
| 6305 const UniqueSet<Map>* maps, |
| 6306 HType type) |
| 6307 : HTemplateInstruction<2>(type), access_(access), maps_(maps) { |
| 6308 ASSERT_NOT_NULL(maps); |
| 6309 ASSERT_NE(0, maps->size()); |
| 6310 |
| 6311 ASSERT_NOT_NULL(object); |
| 6312 SetOperandAt(0, object); |
| 6313 SetOperandAt(1, dependency ? dependency : object); |
| 6314 |
| 6315 ASSERT(access.representation().IsHeapObject()); |
| 6316 // TODO(bmeurer): This is probably broken. What we actually want to to |
| 6317 // instead is set_representation(Representation::HeapObject()). |
| 6318 if (!type.IsHeapObject()) set_type(HType::NonPrimitive()); |
| 6319 set_representation(Representation::Tagged()); |
| 6320 |
| 6321 access.SetGVNFlags(this, LOAD); |
| 6322 } |
| 6323 |
6309 virtual bool IsDeletable() const V8_OVERRIDE { return true; } | 6324 virtual bool IsDeletable() const V8_OVERRIDE { return true; } |
6310 | 6325 |
6311 HObjectAccess access_; | 6326 HObjectAccess access_; |
6312 const UniqueSet<Map>* maps_; | 6327 const UniqueSet<Map>* maps_; |
6313 }; | 6328 }; |
6314 | 6329 |
6315 | 6330 |
6316 class HLoadNamedGeneric V8_FINAL : public HTemplateInstruction<2> { | 6331 class HLoadNamedGeneric V8_FINAL : public HTemplateInstruction<2> { |
6317 public: | 6332 public: |
6318 DECLARE_INSTRUCTION_WITH_CONTEXT_FACTORY_P2(HLoadNamedGeneric, HValue*, | 6333 DECLARE_INSTRUCTION_WITH_CONTEXT_FACTORY_P2(HLoadNamedGeneric, HValue*, |
(...skipping 1313 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7632 virtual bool IsDeletable() const V8_OVERRIDE { return true; } | 7647 virtual bool IsDeletable() const V8_OVERRIDE { return true; } |
7633 }; | 7648 }; |
7634 | 7649 |
7635 | 7650 |
7636 #undef DECLARE_INSTRUCTION | 7651 #undef DECLARE_INSTRUCTION |
7637 #undef DECLARE_CONCRETE_INSTRUCTION | 7652 #undef DECLARE_CONCRETE_INSTRUCTION |
7638 | 7653 |
7639 } } // namespace v8::internal | 7654 } } // namespace v8::internal |
7640 | 7655 |
7641 #endif // V8_HYDROGEN_INSTRUCTIONS_H_ | 7656 #endif // V8_HYDROGEN_INSTRUCTIONS_H_ |
OLD | NEW |