Commit df9ac2c1 authored by sigurds@chromium.org's avatar sigurds@chromium.org

Add Float64Floor, Float64Ceil, Float64RoundTruncate, Float64RoundTiesAway operators.

These operators are not supported by any backends yet, and a backend is free to not support them.

R=bmeurer@chromium.org
TEST=unittest/machine-operator

Review URL: https://codereview.chromium.org/668173002

Cr-Commit-Position: refs/heads/master@{#24874}
git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@24874 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent e0734a65
...@@ -26,8 +26,9 @@ class Flags FINAL { ...@@ -26,8 +26,9 @@ class Flags FINAL {
typedef S mask_type; typedef S mask_type;
Flags() : mask_(0) {} Flags() : mask_(0) {}
Flags(flag_type flag) : mask_(flag) {} // NOLINT(runtime/explicit) Flags(flag_type flag) // NOLINT(runtime/explicit)
explicit Flags(mask_type mask) : mask_(mask) {} : mask_(static_cast<S>(flag)) {}
explicit Flags(mask_type mask) : mask_(static_cast<S>(mask)) {}
Flags& operator&=(const Flags& flags) { Flags& operator&=(const Flags& flags) {
mask_ &= flags.mask_; mask_ &= flags.mask_;
......
...@@ -1135,6 +1135,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) { ...@@ -1135,6 +1135,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) {
VisitFloat64Compare(this, node, &cont); VisitFloat64Compare(this, node, &cont);
} }
// static
MachineOperatorBuilder::Flags
InstructionSelector::SupportedMachineOperatorFlags() {
return MachineOperatorBuilder::Flag::kNoFlags;
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -1285,6 +1285,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) { ...@@ -1285,6 +1285,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) {
VisitFloat64Compare(this, node, &cont); VisitFloat64Compare(this, node, &cont);
} }
// static
MachineOperatorBuilder::Flags
InstructionSelector::SupportedMachineOperatorFlags() {
return MachineOperatorBuilder::Flag::kNoFlags;
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -877,6 +877,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) { ...@@ -877,6 +877,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) {
VisitFloat64Compare(this, node, &cont); VisitFloat64Compare(this, node, &cont);
} }
// static
MachineOperatorBuilder::Flags
InstructionSelector::SupportedMachineOperatorFlags() {
return MachineOperatorBuilder::Flag::kNoFlags;
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -85,6 +85,9 @@ class InstructionSelector FINAL { ...@@ -85,6 +85,9 @@ class InstructionSelector FINAL {
return Features(CpuFeatures::SupportedFeatures()); return Features(CpuFeatures::SupportedFeatures());
} }
// TODO(sigurds) This should take a CpuFeatures argument.
static MachineOperatorBuilder::Flags SupportedMachineOperatorFlags();
// =========================================================================== // ===========================================================================
// ============ Architecture-independent graph covering methods. ============= // ============ Architecture-independent graph covering methods. =============
// =========================================================================== // ===========================================================================
......
...@@ -110,6 +110,10 @@ StoreRepresentation const& StoreRepresentationOf(Operator const* op) { ...@@ -110,6 +110,10 @@ StoreRepresentation const& StoreRepresentationOf(Operator const* op) {
V(Float64Div, Operator::kNoProperties, 2, 1) \ V(Float64Div, Operator::kNoProperties, 2, 1) \
V(Float64Mod, Operator::kNoProperties, 2, 1) \ V(Float64Mod, Operator::kNoProperties, 2, 1) \
V(Float64Sqrt, Operator::kNoProperties, 1, 1) \ V(Float64Sqrt, Operator::kNoProperties, 1, 1) \
V(Float64Ceil, Operator::kNoProperties, 1, 1) \
V(Float64Floor, Operator::kNoProperties, 1, 1) \
V(Float64RoundTruncate, Operator::kNoProperties, 1, 1) \
V(Float64RoundTiesAway, Operator::kNoProperties, 1, 1) \
V(Float64Equal, Operator::kCommutative, 2, 1) \ V(Float64Equal, Operator::kCommutative, 2, 1) \
V(Float64LessThan, Operator::kNoProperties, 2, 1) \ V(Float64LessThan, Operator::kNoProperties, 2, 1) \
V(Float64LessThanOrEqual, Operator::kNoProperties, 2, 1) \ V(Float64LessThanOrEqual, Operator::kNoProperties, 2, 1) \
...@@ -188,8 +192,8 @@ static base::LazyInstance<MachineOperatorBuilderImpl>::type kImpl = ...@@ -188,8 +192,8 @@ static base::LazyInstance<MachineOperatorBuilderImpl>::type kImpl =
LAZY_INSTANCE_INITIALIZER; LAZY_INSTANCE_INITIALIZER;
MachineOperatorBuilder::MachineOperatorBuilder(MachineType word) MachineOperatorBuilder::MachineOperatorBuilder(MachineType word, Flags flags)
: impl_(kImpl.Get()), word_(word) { : impl_(kImpl.Get()), word_(word), flags_(flags) {
DCHECK(word == kRepWord32 || word == kRepWord64); DCHECK(word == kRepWord32 || word == kRepWord64);
} }
...@@ -236,7 +240,6 @@ const Operator* MachineOperatorBuilder::Store(StoreRepresentation rep) { ...@@ -236,7 +240,6 @@ const Operator* MachineOperatorBuilder::Store(StoreRepresentation rep) {
UNREACHABLE(); UNREACHABLE();
return NULL; return NULL;
} }
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
#ifndef V8_COMPILER_MACHINE_OPERATOR_H_ #ifndef V8_COMPILER_MACHINE_OPERATOR_H_
#define V8_COMPILER_MACHINE_OPERATOR_H_ #define V8_COMPILER_MACHINE_OPERATOR_H_
#include "src/base/flags.h"
#include "src/compiler/machine-type.h" #include "src/compiler/machine-type.h"
namespace v8 { namespace v8 {
...@@ -57,7 +58,19 @@ StoreRepresentation const& StoreRepresentationOf(Operator const*); ...@@ -57,7 +58,19 @@ StoreRepresentation const& StoreRepresentationOf(Operator const*);
// for generating code to run on architectures such as ia32, x64, arm, etc. // for generating code to run on architectures such as ia32, x64, arm, etc.
class MachineOperatorBuilder FINAL { class MachineOperatorBuilder FINAL {
public: public:
explicit MachineOperatorBuilder(MachineType word = kMachPtr); // Flags that specify which operations are available. This is useful
// for operations that are unsupported by some back-ends.
enum class Flag : unsigned {
kNoFlags = 0,
kFloat64Floor = 1 << 0,
kFloat64Ceil = 1 << 1,
kFloat64RoundTruncate = 1 << 2,
kFloat64RoundTiesAway = 1 << 3
};
typedef base::Flags<Flag, unsigned> Flags;
explicit MachineOperatorBuilder(MachineType word = kMachPtr,
Flags supportedOperators = Flag::kNoFlags);
const Operator* Word32And(); const Operator* Word32And();
const Operator* Word32Or(); const Operator* Word32Or();
...@@ -135,6 +148,20 @@ class MachineOperatorBuilder FINAL { ...@@ -135,6 +148,20 @@ class MachineOperatorBuilder FINAL {
const Operator* Float64LessThan(); const Operator* Float64LessThan();
const Operator* Float64LessThanOrEqual(); const Operator* Float64LessThanOrEqual();
// Floating point rounding.
const Operator* Float64Floor();
const Operator* Float64Ceil();
const Operator* Float64RoundTruncate();
const Operator* Float64RoundTiesAway();
bool HasFloat64Floor() { return flags_ & Flag::kFloat64Floor; }
bool HasFloat64Ceil() { return flags_ & Flag::kFloat64Ceil; }
bool HasFloat64RoundTruncate() {
return flags_ & Flag::kFloat64RoundTruncate;
}
bool HasFloat64RoundTiesAway() {
return flags_ & Flag::kFloat64RoundTiesAway;
}
// load [base + index] // load [base + index]
const Operator* Load(LoadRepresentation rep); const Operator* Load(LoadRepresentation rep);
...@@ -181,8 +208,11 @@ class MachineOperatorBuilder FINAL { ...@@ -181,8 +208,11 @@ class MachineOperatorBuilder FINAL {
private: private:
const MachineOperatorBuilderImpl& impl_; const MachineOperatorBuilderImpl& impl_;
const MachineType word_; const MachineType word_;
const Flags flags_;
}; };
DEFINE_OPERATORS_FOR_FLAGS(MachineOperatorBuilder::Flags)
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
......
...@@ -647,6 +647,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) { ...@@ -647,6 +647,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) {
VisitFloat64Compare(this, node, &cont); VisitFloat64Compare(this, node, &cont);
} }
// static
MachineOperatorBuilder::Flags
InstructionSelector::SupportedMachineOperatorFlags() {
return MachineOperatorBuilder::Flag::kNoFlags;
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -226,6 +226,10 @@ ...@@ -226,6 +226,10 @@
V(Float64Equal) \ V(Float64Equal) \
V(Float64LessThan) \ V(Float64LessThan) \
V(Float64LessThanOrEqual) \ V(Float64LessThanOrEqual) \
V(Float64Floor) \
V(Float64Ceil) \
V(Float64RoundTruncate) \
V(Float64RoundTiesAway) \
V(LoadStackPointer) V(LoadStackPointer)
#define VALUE_OP_LIST(V) \ #define VALUE_OP_LIST(V) \
......
...@@ -178,7 +178,8 @@ Handle<Code> Pipeline::GenerateCode() { ...@@ -178,7 +178,8 @@ Handle<Code> Pipeline::GenerateCode() {
// construction. This is currently only needed for the node cache, which the // construction. This is currently only needed for the node cache, which the
// typer could sweep over later. // typer could sweep over later.
Typer typer(&graph, info()->context()); Typer typer(&graph, info()->context());
MachineOperatorBuilder machine; MachineOperatorBuilder machine(
kMachPtr, InstructionSelector::SupportedMachineOperatorFlags());
CommonOperatorBuilder common(zone()); CommonOperatorBuilder common(zone());
JSOperatorBuilder javascript(zone()); JSOperatorBuilder javascript(zone());
JSGraph jsgraph(&graph, &common, &javascript, &machine); JSGraph jsgraph(&graph, &common, &javascript, &machine);
......
...@@ -915,6 +915,10 @@ class RepresentationSelector { ...@@ -915,6 +915,10 @@ class RepresentationSelector {
case IrOpcode::kFloat64Mod: case IrOpcode::kFloat64Mod:
return VisitFloat64Binop(node); return VisitFloat64Binop(node);
case IrOpcode::kFloat64Sqrt: case IrOpcode::kFloat64Sqrt:
case IrOpcode::kFloat64Floor:
case IrOpcode::kFloat64Ceil:
case IrOpcode::kFloat64RoundTruncate:
case IrOpcode::kFloat64RoundTiesAway:
return VisitUnop(node, kMachFloat64, kMachFloat64); return VisitUnop(node, kMachFloat64, kMachFloat64);
case IrOpcode::kFloat64Equal: case IrOpcode::kFloat64Equal:
case IrOpcode::kFloat64LessThan: case IrOpcode::kFloat64LessThan:
......
...@@ -1770,6 +1770,30 @@ Bounds Typer::Visitor::TypeFloat64LessThanOrEqual(Node* node) { ...@@ -1770,6 +1770,30 @@ Bounds Typer::Visitor::TypeFloat64LessThanOrEqual(Node* node) {
} }
Bounds Typer::Visitor::TypeFloat64Floor(Node* node) {
// TODO(sigurds): We could have a tighter bound here.
return Bounds(Type::Number());
}
Bounds Typer::Visitor::TypeFloat64Ceil(Node* node) {
// TODO(sigurds): We could have a tighter bound here.
return Bounds(Type::Number());
}
Bounds Typer::Visitor::TypeFloat64RoundTruncate(Node* node) {
// TODO(sigurds): We could have a tighter bound here.
return Bounds(Type::Number());
}
Bounds Typer::Visitor::TypeFloat64RoundTiesAway(Node* node) {
// TODO(sigurds): We could have a tighter bound here.
return Bounds(Type::Number());
}
Bounds Typer::Visitor::TypeLoadStackPointer(Node* node) { Bounds Typer::Visitor::TypeLoadStackPointer(Node* node) {
return Bounds(Type::Internal()); return Bounds(Type::Internal());
} }
......
...@@ -702,6 +702,10 @@ GenericGraphVisit::Control Verifier::Visitor::Pre(Node* node) { ...@@ -702,6 +702,10 @@ GenericGraphVisit::Control Verifier::Visitor::Pre(Node* node) {
case IrOpcode::kFloat64Div: case IrOpcode::kFloat64Div:
case IrOpcode::kFloat64Mod: case IrOpcode::kFloat64Mod:
case IrOpcode::kFloat64Sqrt: case IrOpcode::kFloat64Sqrt:
case IrOpcode::kFloat64Floor:
case IrOpcode::kFloat64Ceil:
case IrOpcode::kFloat64RoundTruncate:
case IrOpcode::kFloat64RoundTiesAway:
case IrOpcode::kFloat64Equal: case IrOpcode::kFloat64Equal:
case IrOpcode::kFloat64LessThan: case IrOpcode::kFloat64LessThan:
case IrOpcode::kFloat64LessThanOrEqual: case IrOpcode::kFloat64LessThanOrEqual:
......
...@@ -1108,6 +1108,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) { ...@@ -1108,6 +1108,12 @@ void InstructionSelector::VisitFloat64LessThanOrEqual(Node* node) {
VisitFloat64Compare(this, node, &cont); VisitFloat64Compare(this, node, &cont);
} }
// static
MachineOperatorBuilder::Flags
InstructionSelector::SupportedMachineOperatorFlags() {
return MachineOperatorBuilder::Flag::kNoFlags;
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8
...@@ -202,7 +202,9 @@ const PureOperator kPureOperators[] = { ...@@ -202,7 +202,9 @@ const PureOperator kPureOperators[] = {
PURE(Float64Div, 2, 1), PURE(Float64Mod, 2, 1), PURE(Float64Div, 2, 1), PURE(Float64Mod, 2, 1),
PURE(Float64Sqrt, 1, 1), PURE(Float64Equal, 2, 1), PURE(Float64Sqrt, 1, 1), PURE(Float64Equal, 2, 1),
PURE(Float64LessThan, 2, 1), PURE(Float64LessThanOrEqual, 2, 1), PURE(Float64LessThan, 2, 1), PURE(Float64LessThanOrEqual, 2, 1),
PURE(LoadStackPointer, 0, 1) PURE(LoadStackPointer, 0, 1), PURE(Float64Floor, 1, 1),
PURE(Float64Ceil, 1, 1), PURE(Float64RoundTruncate, 1, 1),
PURE(Float64RoundTiesAway, 1, 1),
#undef PURE #undef PURE
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment