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 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
45 if (IsWord(use_type) && IsWord(output_type)) { | 45 if (IsWord(use_type) && IsWord(output_type)) { |
46 // Both are words less than or equal to 32-bits. | 46 // Both are words less than or equal to 32-bits. |
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, use_type); |
56 } else if (use_type & kRepFloat64) { | 56 } else if (use_type & kRepFloat64) { |
57 return GetFloat64RepresentationFor(node, output_type, use_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; |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
108 node = InsertChangeFloat32ToFloat64(node); | 108 node = InsertChangeFloat32ToFloat64(node); |
109 op = simplified()->ChangeFloat64ToTagged(); | 109 op = simplified()->ChangeFloat64ToTagged(); |
110 } else if (output_type & kRepFloat64) { | 110 } else if (output_type & kRepFloat64) { |
111 op = simplified()->ChangeFloat64ToTagged(); | 111 op = simplified()->ChangeFloat64ToTagged(); |
112 } else { | 112 } else { |
113 return TypeError(node, output_type, kRepTagged); | 113 return TypeError(node, output_type, kRepTagged); |
114 } | 114 } |
115 return jsgraph()->graph()->NewNode(op, node); | 115 return jsgraph()->graph()->NewNode(op, node); |
116 } | 116 } |
117 | 117 |
118 Node* GetFloat32RepresentationFor(Node* node, MachineTypeUnion output_type) { | 118 Node* GetFloat32RepresentationFor(Node* node, MachineTypeUnion output_type, |
| 119 MachineTypeUnion truncation) { |
119 // Eagerly fold representation changes for constants. | 120 // Eagerly fold representation changes for constants. |
120 switch (node->opcode()) { | 121 switch (node->opcode()) { |
121 case IrOpcode::kFloat64Constant: | 122 case IrOpcode::kFloat64Constant: |
122 case IrOpcode::kNumberConstant: | 123 case IrOpcode::kNumberConstant: |
123 return jsgraph()->Float32Constant( | 124 return jsgraph()->Float32Constant( |
124 DoubleToFloat32(OpParameter<double>(node))); | 125 DoubleToFloat32(OpParameter<double>(node))); |
125 case IrOpcode::kInt32Constant: | 126 case IrOpcode::kInt32Constant: |
126 if (output_type & kTypeUint32) { | 127 if (output_type & kTypeUint32) { |
127 uint32_t value = static_cast<uint32_t>(OpParameter<int32_t>(node)); | 128 uint32_t value = static_cast<uint32_t>(OpParameter<int32_t>(node)); |
128 return jsgraph()->Float32Constant(static_cast<float>(value)); | 129 return jsgraph()->Float32Constant(static_cast<float>(value)); |
129 } else { | 130 } else { |
130 int32_t value = OpParameter<int32_t>(node); | 131 int32_t value = OpParameter<int32_t>(node); |
131 return jsgraph()->Float32Constant(static_cast<float>(value)); | 132 return jsgraph()->Float32Constant(static_cast<float>(value)); |
132 } | 133 } |
133 case IrOpcode::kFloat32Constant: | 134 case IrOpcode::kFloat32Constant: |
134 return node; // No change necessary. | 135 return node; // No change necessary. |
135 default: | 136 default: |
136 break; | 137 break; |
137 } | 138 } |
138 // Select the correct X -> Float32 operator. | 139 // Select the correct X -> Float32 operator. |
139 const Operator* op; | 140 const Operator* op; |
140 if (output_type & kRepBit) { | 141 if (output_type & kRepBit) { |
141 return TypeError(node, output_type, kRepFloat32); | 142 return TypeError(node, output_type, kRepFloat32); |
142 } else if (IsWord(output_type)) { | 143 } else if (IsWord(output_type)) { |
143 if (output_type & kTypeUint32) { | 144 if (output_type & kTypeUint32) { |
144 op = machine()->ChangeUint32ToFloat64(); | 145 op = machine()->ChangeUint32ToFloat64(); |
145 } else { | 146 } else { |
| 147 // Either the output is int32 or the uses only care about the |
| 148 // low 32 bits (so we can pick int32 safely). |
| 149 DCHECK(output_type & kTypeInt32 || |
| 150 !(truncation & ~(kTypeInt32 | kTypeUint32 | kRepMask))); |
146 op = machine()->ChangeInt32ToFloat64(); | 151 op = machine()->ChangeInt32ToFloat64(); |
147 } | 152 } |
148 // int32 -> float64 -> float32 | 153 // int32 -> float64 -> float32 |
149 node = jsgraph()->graph()->NewNode(op, node); | 154 node = jsgraph()->graph()->NewNode(op, node); |
150 op = machine()->TruncateFloat64ToFloat32(); | 155 op = machine()->TruncateFloat64ToFloat32(); |
151 } else if (output_type & kRepTagged) { | 156 } else if (output_type & kRepTagged) { |
152 op = simplified() | 157 op = simplified() |
153 ->ChangeTaggedToFloat64(); // tagged -> float64 -> float32 | 158 ->ChangeTaggedToFloat64(); // tagged -> float64 -> float32 |
154 node = jsgraph()->graph()->NewNode(op, node); | 159 node = jsgraph()->graph()->NewNode(op, node); |
155 op = machine()->TruncateFloat64ToFloat32(); | 160 op = machine()->TruncateFloat64ToFloat32(); |
(...skipping 314 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
470 Factory* factory() const { return isolate()->factory(); } | 475 Factory* factory() const { return isolate()->factory(); } |
471 SimplifiedOperatorBuilder* simplified() { return jsgraph()->simplified(); } | 476 SimplifiedOperatorBuilder* simplified() { return jsgraph()->simplified(); } |
472 MachineOperatorBuilder* machine() { return jsgraph()->machine(); } | 477 MachineOperatorBuilder* machine() { return jsgraph()->machine(); } |
473 }; | 478 }; |
474 | 479 |
475 } // namespace compiler | 480 } // namespace compiler |
476 } // namespace internal | 481 } // namespace internal |
477 } // namespace v8 | 482 } // namespace v8 |
478 | 483 |
479 #endif // V8_COMPILER_REPRESENTATION_CHANGE_H_ | 484 #endif // V8_COMPILER_REPRESENTATION_CHANGE_H_ |
OLD | NEW |