Index: src/compiler/representation-change.h |
diff --git a/src/compiler/representation-change.h b/src/compiler/representation-change.h |
index 839335d1fce847da03801d807e0659b5b04b36fb..8a38644e9495e0e35bb86ace049b3dc32f01cb7b 100644 |
--- a/src/compiler/representation-change.h |
+++ b/src/compiler/representation-change.h |
@@ -73,6 +73,86 @@ class Truncation final { |
static bool LessGeneral(TruncationKind rep1, TruncationKind rep2); |
}; |
+enum class TypeCheckKind : uint8_t { |
+ kNone, |
+ kSigned32, |
+ kNumberOrUndefined, |
+ kNumber |
+}; |
+ |
+// The {UseInfo} class is used to describe a use of an input of a node. |
+// |
+// This information is used in two different ways, based on the phase: |
+// |
+// 1. During propagation, the use info is used to inform the input node |
+// about what part of the input is used (we call this truncation) and what |
+// is the preferred representation. |
+// |
+// 2. During lowering, the use info is used to properly convert the input |
+// to the preferred representation. The preferred representation might be |
+// insufficient to do the conversion (e.g. word32->float64 conv), so we also |
+// need the signedness information to produce the correct value. |
+class UseInfo { |
+ public: |
+ UseInfo(MachineRepresentation representation, Truncation truncation, |
+ TypeCheckKind type_check = TypeCheckKind::kNone) |
+ : representation_(representation), |
+ truncation_(truncation), |
+ type_check_(type_check) {} |
+ static UseInfo TruncatingWord32() { |
+ return UseInfo(MachineRepresentation::kWord32, Truncation::Word32()); |
+ } |
+ static UseInfo TruncatingWord64() { |
+ return UseInfo(MachineRepresentation::kWord64, Truncation::Word64()); |
+ } |
+ static UseInfo Bool() { |
+ return UseInfo(MachineRepresentation::kBit, Truncation::Bool()); |
+ } |
+ static UseInfo TruncatingFloat32() { |
+ return UseInfo(MachineRepresentation::kFloat32, Truncation::Float32()); |
+ } |
+ static UseInfo TruncatingFloat64() { |
+ return UseInfo(MachineRepresentation::kFloat64, Truncation::Float64()); |
+ } |
+ static UseInfo PointerInt() { |
+ return kPointerSize == 4 ? TruncatingWord32() : TruncatingWord64(); |
+ } |
+ static UseInfo AnyTagged() { |
+ return UseInfo(MachineRepresentation::kTagged, Truncation::Any()); |
+ } |
+ |
+ // Possibly deoptimizing conversions. |
+ static UseInfo CheckedSigned32AsWord32() { |
+ return UseInfo(MachineRepresentation::kWord32, Truncation::Any(), |
+ TypeCheckKind::kSigned32); |
+ } |
+ static UseInfo CheckedNumberOrUndefinedAsFloat64() { |
+ return UseInfo(MachineRepresentation::kFloat64, Truncation::Any(), |
+ TypeCheckKind::kNumberOrUndefined); |
+ } |
+ |
+ // Undetermined representation. |
+ static UseInfo Any() { |
+ return UseInfo(MachineRepresentation::kNone, Truncation::Any()); |
+ } |
+ static UseInfo AnyTruncatingToBool() { |
+ return UseInfo(MachineRepresentation::kNone, Truncation::Bool()); |
+ } |
+ |
+ // Value not used. |
+ static UseInfo None() { |
+ return UseInfo(MachineRepresentation::kNone, Truncation::None()); |
+ } |
+ |
+ MachineRepresentation representation() const { return representation_; } |
+ Truncation truncation() const { return truncation_; } |
+ TypeCheckKind type_check() const { return type_check_; } |
+ |
+ private: |
+ MachineRepresentation representation_; |
+ Truncation truncation_; |
+ TypeCheckKind type_check_; |
+}; |
// Contains logic related to changing the representation of values for constants |
// and other nodes, as well as lowering Simplified->Machine operators. |
@@ -90,9 +170,10 @@ class RepresentationChanger final { |
// out signedness for the word32->float64 conversion, then we check that the |
// uses truncate to word32 (so they do not care about signedness). |
Node* GetRepresentationFor(Node* node, MachineRepresentation output_rep, |
- Type* output_type, MachineRepresentation use_rep, |
- Truncation truncation = Truncation::None()); |
+ Type* output_type, Node* use_node, |
+ UseInfo use_info); |
const Operator* Int32OperatorFor(IrOpcode::Value opcode); |
+ const Operator* Int32OverflowOperatorFor(IrOpcode::Value opcode); |
const Operator* Uint32OperatorFor(IrOpcode::Value opcode); |
const Operator* Float64OperatorFor(IrOpcode::Value opcode); |
@@ -122,13 +203,20 @@ class RepresentationChanger final { |
Type* output_type, Truncation truncation); |
Node* GetFloat64RepresentationFor(Node* node, |
MachineRepresentation output_rep, |
- Type* output_type, Truncation truncation); |
+ Type* output_type, Node* use_node, |
+ UseInfo use_info); |
Node* GetWord32RepresentationFor(Node* node, MachineRepresentation output_rep, |
- Type* output_type, Truncation truncation); |
+ Type* output_type, Node* use_node, |
+ UseInfo use_info); |
Node* GetBitRepresentationFor(Node* node, MachineRepresentation output_rep, |
Type* output_type); |
Node* GetWord64RepresentationFor(Node* node, MachineRepresentation output_rep, |
Type* output_type); |
+ Node* GetCheckedWord32RepresentationFor(Node* node, |
+ MachineRepresentation output_rep, |
+ Type* output_type, Node* use_node, |
+ Truncation truncation, |
+ TypeCheckKind check); |
Node* TypeError(Node* node, MachineRepresentation output_rep, |
Type* output_type, MachineRepresentation use); |
Node* MakeTruncatedInt32Constant(double value); |
@@ -138,6 +226,8 @@ class RepresentationChanger final { |
Node* InsertChangeTaggedSignedToInt32(Node* node); |
Node* InsertChangeTaggedToFloat64(Node* node); |
+ Node* InsertConversion(Node* node, const Operator* op, Node* use_node); |
+ |
JSGraph* jsgraph() const { return jsgraph_; } |
Isolate* isolate() const { return isolate_; } |
Factory* factory() const { return isolate()->factory(); } |