Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(3)

Side by Side Diff: src/register-allocator.h

Issue 146077: Removed static type inference and add a dynamic test for string addition. (Closed)
Patch Set: And it lints too. Created 11 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2008 the V8 project authors. All rights reserved. 1 // Copyright 2008 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 27 matching lines...) Expand all
38 #include "arm/register-allocator-arm.h" 38 #include "arm/register-allocator-arm.h"
39 #else 39 #else
40 #error Unsupported target architecture. 40 #error Unsupported target architecture.
41 #endif 41 #endif
42 42
43 namespace v8 { 43 namespace v8 {
44 namespace internal { 44 namespace internal {
45 45
46 46
47 // ------------------------------------------------------------------------- 47 // -------------------------------------------------------------------------
48 // StaticType
49 //
50 // StaticType represent the type of an expression or a word at runtime.
51 // The types are ordered by knowledge, so that if a value can come about
52 // in more than one way, and there are different static types inferred
53 // for the different ways, the types can be combined to a type that we
54 // are still certain of (possibly just "unknown").
55
56 class StaticType BASE_EMBEDDED {
57 public:
58 StaticType() : static_type_(UNKNOWN_TYPE) {}
59
60 static StaticType unknown() { return StaticType(); }
61 static StaticType smi() { return StaticType(SMI_TYPE); }
62 static StaticType jsstring() { return StaticType(STRING_TYPE); }
63 static StaticType heap_object() { return StaticType(HEAP_OBJECT_TYPE); }
64
65 // Accessors
66 bool is_unknown() { return static_type_ == UNKNOWN_TYPE; }
67 bool is_smi() { return static_type_ == SMI_TYPE; }
68 bool is_heap_object() { return (static_type_ & HEAP_OBJECT_TYPE) != 0; }
69 bool is_jsstring() { return static_type_ == STRING_TYPE; }
70
71 bool operator==(StaticType other) const {
72 return static_type_ == other.static_type_;
73 }
74
75 // Find the best approximating type for a value.
76 // The argument must not be NULL.
77 static StaticType TypeOf(Object* object) {
78 // Remember to make the most specific tests first. A string is also a heap
79 // object, so test for string-ness first.
80 if (object->IsSmi()) return smi();
81 if (object->IsString()) return jsstring();
82 if (object->IsHeapObject()) return heap_object();
83 return unknown();
84 }
85
86 // Merges two static types to a type that combines the knowledge
87 // of both. If there is no way to combine (e.g., being a string *and*
88 // being a smi), the resulting type is unknown.
89 StaticType merge(StaticType other) {
90 StaticType x(
91 static_cast<StaticTypeEnum>(static_type_ & other.static_type_));
92 return x;
93 }
94
95 private:
96 enum StaticTypeEnum {
97 // Numbers are chosen so that least upper bound of the following
98 // partial order is implemented by bitwise "and":
99 //
100 // string
101 // |
102 // heap-object smi
103 // \ /
104 // unknown
105 //
106 UNKNOWN_TYPE = 0x00,
107 SMI_TYPE = 0x01,
108 HEAP_OBJECT_TYPE = 0x02,
109 STRING_TYPE = 0x04 | HEAP_OBJECT_TYPE
110 };
111 explicit StaticType(StaticTypeEnum static_type) : static_type_(static_type) {}
112
113 // StaticTypeEnum static_type_;
114 StaticTypeEnum static_type_;
115
116 friend class FrameElement;
117 friend class Result;
118 };
119
120
121 // -------------------------------------------------------------------------
122 // Results 48 // Results
123 // 49 //
124 // Results encapsulate the compile-time values manipulated by the code 50 // Results encapsulate the compile-time values manipulated by the code
125 // generator. They can represent registers or constants. 51 // generator. They can represent registers or constants.
126 52
127 class Result BASE_EMBEDDED { 53 class Result BASE_EMBEDDED {
128 public: 54 public:
129 enum Type { 55 enum Type {
130 INVALID, 56 INVALID,
131 REGISTER, 57 REGISTER,
132 CONSTANT 58 CONSTANT
133 }; 59 };
134 60
135 // Construct an invalid result. 61 // Construct an invalid result.
136 Result() { invalidate(); } 62 Result() { invalidate(); }
137 63
138 // Construct a register Result. 64 // Construct a register Result.
139 explicit Result(Register reg); 65 explicit Result(Register reg);
140 66
141 // Construct a register Result with a known static type.
142 Result(Register reg, StaticType static_type);
143
144 // Construct a Result whose value is a compile-time constant. 67 // Construct a Result whose value is a compile-time constant.
145 explicit Result(Handle<Object> value) { 68 explicit Result(Handle<Object> value) {
146 value_ = StaticTypeField::encode(StaticType::TypeOf(*value).static_type_) 69 value_ = TypeField::encode(CONSTANT)
147 | TypeField::encode(CONSTANT)
148 | DataField::encode(ConstantList()->length()); 70 | DataField::encode(ConstantList()->length());
149 ConstantList()->Add(value); 71 ConstantList()->Add(value);
150 } 72 }
151 73
152 // The copy constructor and assignment operators could each create a new 74 // The copy constructor and assignment operators could each create a new
153 // register reference. 75 // register reference.
154 Result(const Result& other) { 76 Result(const Result& other) {
155 other.CopyTo(this); 77 other.CopyTo(this);
156 } 78 }
157 79
(...skipping 17 matching lines...) Expand all
175 return &list; 97 return &list;
176 } 98 }
177 99
178 // Clear the constants indirection table. 100 // Clear the constants indirection table.
179 static void ClearConstantList() { 101 static void ClearConstantList() {
180 ConstantList()->Clear(); 102 ConstantList()->Clear();
181 } 103 }
182 104
183 inline void Unuse(); 105 inline void Unuse();
184 106
185 StaticType static_type() const {
186 return StaticType(StaticTypeField::decode(value_));
187 }
188
189 void set_static_type(StaticType type) {
190 value_ = value_ & ~StaticTypeField::mask();
191 value_ = value_ | StaticTypeField::encode(type.static_type_);
192 }
193
194 Type type() const { return TypeField::decode(value_); } 107 Type type() const { return TypeField::decode(value_); }
195 108
196 void invalidate() { value_ = TypeField::encode(INVALID); } 109 void invalidate() { value_ = TypeField::encode(INVALID); }
197 110
198 bool is_valid() const { return type() != INVALID; } 111 bool is_valid() const { return type() != INVALID; }
199 bool is_register() const { return type() == REGISTER; } 112 bool is_register() const { return type() == REGISTER; }
200 bool is_constant() const { return type() == CONSTANT; } 113 bool is_constant() const { return type() == CONSTANT; }
201 114
202 Register reg() const { 115 Register reg() const {
203 ASSERT(is_register()); 116 ASSERT(is_register());
(...skipping 14 matching lines...) Expand all
218 void ToRegister(); 131 void ToRegister();
219 132
220 // Move this result to a specified register. The register is spilled from 133 // Move this result to a specified register. The register is spilled from
221 // the frame, and the register is singly-referenced (by this result) 134 // the frame, and the register is singly-referenced (by this result)
222 // outside the frame. 135 // outside the frame.
223 void ToRegister(Register reg); 136 void ToRegister(Register reg);
224 137
225 private: 138 private:
226 uint32_t value_; 139 uint32_t value_;
227 140
228 class StaticTypeField: public BitField<StaticType::StaticTypeEnum, 0, 3> {}; 141 class TypeField: public BitField<Type, 0, 2> {};
229 class TypeField: public BitField<Type, 3, 2> {}; 142 class DataField: public BitField<uint32_t, 2, 32 - 3> {};
230 class DataField: public BitField<uint32_t, 5, 32 - 6> {};
231 143
232 inline void CopyTo(Result* destination) const; 144 inline void CopyTo(Result* destination) const;
233 145
234 friend class CodeGeneratorScope; 146 friend class CodeGeneratorScope;
235 }; 147 };
236 148
237 149
238 // ------------------------------------------------------------------------- 150 // -------------------------------------------------------------------------
239 // Register file 151 // Register file
240 // 152 //
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after
377 } 289 }
378 290
379 private: 291 private:
380 CodeGenerator* cgen_; 292 CodeGenerator* cgen_;
381 RegisterFile registers_; 293 RegisterFile registers_;
382 }; 294 };
383 295
384 } } // namespace v8::internal 296 } } // namespace v8::internal
385 297
386 #endif // V8_REGISTER_ALLOCATOR_H_ 298 #endif // V8_REGISTER_ALLOCATOR_H_
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698