OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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_COMPILER_REPRESENTATION_CHANGE_H_ | 5 #ifndef V8_COMPILER_REPRESENTATION_CHANGE_H_ |
6 #define V8_COMPILER_REPRESENTATION_CHANGE_H_ | 6 #define V8_COMPILER_REPRESENTATION_CHANGE_H_ |
7 | 7 |
8 #include <sstream> | 8 #include <sstream> |
9 | 9 |
10 #include "src/base/bits.h" | 10 #include "src/base/bits.h" |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
47 // Since loads of integers from memory implicitly sign or zero extend the | 47 // Since loads of integers from memory implicitly sign or zero extend the |
48 // value to the full machine word size and stores implicitly truncate, | 48 // value to the full machine word size and stores implicitly truncate, |
49 // no representation change is necessary. | 49 // no representation change is necessary. |
50 return node; | 50 return node; |
51 } | 51 } |
52 if (use_type & kRepTagged) { | 52 if (use_type & kRepTagged) { |
53 return GetTaggedRepresentationFor(node, output_type); | 53 return GetTaggedRepresentationFor(node, output_type); |
54 } else if (use_type & kRepFloat32) { | 54 } else if (use_type & kRepFloat32) { |
55 return GetFloat32RepresentationFor(node, output_type); | 55 return GetFloat32RepresentationFor(node, output_type); |
56 } else if (use_type & kRepFloat64) { | 56 } else if (use_type & kRepFloat64) { |
57 return GetFloat64RepresentationFor(node, output_type); | 57 return GetFloat64RepresentationFor(node, output_type, use_type); |
58 } else if (use_type & kRepBit) { | 58 } else if (use_type & kRepBit) { |
59 return GetBitRepresentationFor(node, output_type); | 59 return GetBitRepresentationFor(node, output_type); |
60 } else if (IsWord(use_type)) { | 60 } else if (IsWord(use_type)) { |
61 return GetWord32RepresentationFor(node, output_type); | 61 return GetWord32RepresentationFor(node, output_type); |
62 } else if (use_type & kRepWord64) { | 62 } else if (use_type & kRepWord64) { |
63 return GetWord64RepresentationFor(node, output_type); | 63 return GetWord64RepresentationFor(node, output_type); |
64 } else { | 64 } else { |
65 return node; | 65 return node; |
66 } | 66 } |
67 } | 67 } |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
154 node = jsgraph()->graph()->NewNode(op, node); | 154 node = jsgraph()->graph()->NewNode(op, node); |
155 op = machine()->TruncateFloat64ToFloat32(); | 155 op = machine()->TruncateFloat64ToFloat32(); |
156 } else if (output_type & kRepFloat64) { | 156 } else if (output_type & kRepFloat64) { |
157 op = machine()->TruncateFloat64ToFloat32(); | 157 op = machine()->TruncateFloat64ToFloat32(); |
158 } else { | 158 } else { |
159 return TypeError(node, output_type, kRepFloat32); | 159 return TypeError(node, output_type, kRepFloat32); |
160 } | 160 } |
161 return jsgraph()->graph()->NewNode(op, node); | 161 return jsgraph()->graph()->NewNode(op, node); |
162 } | 162 } |
163 | 163 |
164 Node* GetFloat64RepresentationFor(Node* node, MachineTypeUnion output_type) { | 164 Node* GetFloat64RepresentationFor(Node* node, MachineTypeUnion output_type, |
| 165 MachineTypeUnion use_type) { |
165 // Eagerly fold representation changes for constants. | 166 // Eagerly fold representation changes for constants. |
166 switch (node->opcode()) { | 167 switch (node->opcode()) { |
167 case IrOpcode::kNumberConstant: | 168 case IrOpcode::kNumberConstant: |
168 return jsgraph()->Float64Constant(OpParameter<double>(node)); | 169 return jsgraph()->Float64Constant(OpParameter<double>(node)); |
169 case IrOpcode::kInt32Constant: | 170 case IrOpcode::kInt32Constant: |
170 if (output_type & kTypeUint32) { | 171 if (output_type & kTypeUint32) { |
171 uint32_t value = static_cast<uint32_t>(OpParameter<int32_t>(node)); | 172 uint32_t value = static_cast<uint32_t>(OpParameter<int32_t>(node)); |
172 return jsgraph()->Float64Constant(static_cast<double>(value)); | 173 return jsgraph()->Float64Constant(static_cast<double>(value)); |
173 } else { | 174 } else { |
174 int32_t value = OpParameter<int32_t>(node); | 175 int32_t value = OpParameter<int32_t>(node); |
175 return jsgraph()->Float64Constant(value); | 176 return jsgraph()->Float64Constant(value); |
176 } | 177 } |
177 case IrOpcode::kFloat64Constant: | 178 case IrOpcode::kFloat64Constant: |
178 return node; // No change necessary. | 179 return node; // No change necessary. |
179 case IrOpcode::kFloat32Constant: | 180 case IrOpcode::kFloat32Constant: |
180 return jsgraph()->Float64Constant(OpParameter<float>(node)); | 181 return jsgraph()->Float64Constant(OpParameter<float>(node)); |
181 default: | 182 default: |
182 break; | 183 break; |
183 } | 184 } |
184 // Select the correct X -> Float64 operator. | 185 // Select the correct X -> Float64 operator. |
185 const Operator* op; | 186 const Operator* op; |
186 if (output_type & kRepBit) { | 187 if (output_type & kRepBit) { |
187 return TypeError(node, output_type, kRepFloat64); | 188 return TypeError(node, output_type, kRepFloat64); |
188 } else if (IsWord(output_type)) { | 189 } else if (IsWord(output_type)) { |
189 if (output_type & kTypeUint32) { | 190 if (output_type & kTypeUint32) { |
190 op = machine()->ChangeUint32ToFloat64(); | 191 op = machine()->ChangeUint32ToFloat64(); |
191 } else { | 192 } else { |
| 193 // Either the output is int32 or the uses only care about the |
| 194 // low 32 bits (so we can pick int32 safely). |
| 195 DCHECK(output_type & kTypeInt32 || |
| 196 !(use_type & ~(kTypeInt32 | kTypeUint32 | kRepMask))); |
192 op = machine()->ChangeInt32ToFloat64(); | 197 op = machine()->ChangeInt32ToFloat64(); |
193 } | 198 } |
194 } else if (output_type & kRepTagged) { | 199 } else if (output_type & kRepTagged) { |
195 op = simplified()->ChangeTaggedToFloat64(); | 200 op = simplified()->ChangeTaggedToFloat64(); |
196 } else if (output_type & kRepFloat32) { | 201 } else if (output_type & kRepFloat32) { |
197 op = machine()->ChangeFloat32ToFloat64(); | 202 op = machine()->ChangeFloat32ToFloat64(); |
198 } else { | 203 } else { |
199 return TypeError(node, output_type, kRepFloat64); | 204 return TypeError(node, output_type, kRepFloat64); |
200 } | 205 } |
201 return jsgraph()->graph()->NewNode(op, node); | 206 return jsgraph()->graph()->NewNode(op, node); |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
253 return MakeInt32Constant(OpParameter<float>(node)); | 258 return MakeInt32Constant(OpParameter<float>(node)); |
254 case IrOpcode::kNumberConstant: | 259 case IrOpcode::kNumberConstant: |
255 case IrOpcode::kFloat64Constant: | 260 case IrOpcode::kFloat64Constant: |
256 return MakeInt32Constant(OpParameter<double>(node)); | 261 return MakeInt32Constant(OpParameter<double>(node)); |
257 default: | 262 default: |
258 break; | 263 break; |
259 } | 264 } |
260 // Select the correct X -> Word32 operator. | 265 // Select the correct X -> Word32 operator. |
261 const Operator* op; | 266 const Operator* op; |
262 Type* type = NodeProperties::GetType(node); | 267 Type* type = NodeProperties::GetType(node); |
| 268 |
263 if (output_type & kRepBit) { | 269 if (output_type & kRepBit) { |
264 return node; // Sloppy comparison -> word32 | 270 return node; // Sloppy comparison -> word32 |
265 } else if (output_type & kRepFloat64) { | 271 } else if (output_type & kRepFloat64) { |
266 if (output_type & kTypeUint32 || type->Is(Type::Unsigned32())) { | 272 if (output_type & kTypeUint32 || type->Is(Type::Unsigned32())) { |
267 op = machine()->ChangeFloat64ToUint32(); | 273 op = machine()->ChangeFloat64ToUint32(); |
268 } else if (output_type & kTypeInt32 || type->Is(Type::Signed32())) { | 274 } else if (output_type & kTypeInt32 || type->Is(Type::Signed32())) { |
269 op = machine()->ChangeFloat64ToInt32(); | 275 op = machine()->ChangeFloat64ToInt32(); |
270 } else { | 276 } else { |
271 op = machine()->TruncateFloat64ToInt32(TruncationMode::kJavaScript); | 277 op = machine()->TruncateFloat64ToInt32(TruncationMode::kJavaScript); |
272 } | 278 } |
(...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
464 Factory* factory() const { return isolate()->factory(); } | 470 Factory* factory() const { return isolate()->factory(); } |
465 SimplifiedOperatorBuilder* simplified() { return jsgraph()->simplified(); } | 471 SimplifiedOperatorBuilder* simplified() { return jsgraph()->simplified(); } |
466 MachineOperatorBuilder* machine() { return jsgraph()->machine(); } | 472 MachineOperatorBuilder* machine() { return jsgraph()->machine(); } |
467 }; | 473 }; |
468 | 474 |
469 } // namespace compiler | 475 } // namespace compiler |
470 } // namespace internal | 476 } // namespace internal |
471 } // namespace v8 | 477 } // namespace v8 |
472 | 478 |
473 #endif // V8_COMPILER_REPRESENTATION_CHANGE_H_ | 479 #endif // V8_COMPILER_REPRESENTATION_CHANGE_H_ |
OLD | NEW |