Revert "Revert "Upgrade to 5.0.71.48"" DO NOT MERGE
This reverts commit f2e3994fa5148cc3d9946666f0b0596290192b0e,
and updates the x64 makefile properly so it doesn't break that
build.
FPIIM-449
Change-Id: Ib83e35bfbae6af627451c926a9650ec57c045605
(cherry picked from commit 109988c7ccb6f3fd1a58574fa3dfb88beaef6632)
diff --git a/src/interpreter/bytecodes.cc b/src/interpreter/bytecodes.cc
index 2d4406c..c3b17c7 100644
--- a/src/interpreter/bytecodes.cc
+++ b/src/interpreter/bytecodes.cc
@@ -57,6 +57,7 @@
// static
uint8_t Bytecodes::ToByte(Bytecode bytecode) {
+ DCHECK(bytecode <= Bytecode::kLast);
return static_cast<uint8_t>(bytecode);
}
@@ -70,6 +71,21 @@
// static
+Bytecode Bytecodes::GetDebugBreak(Bytecode bytecode) {
+ switch (Size(bytecode)) {
+#define CASE(Name, ...) \
+ case BytecodeTraits<__VA_ARGS__, OPERAND_TERM>::kSize: \
+ return Bytecode::k##Name;
+ DEBUG_BREAK_BYTECODE_LIST(CASE)
+#undef CASE
+ default:
+ break;
+ }
+ UNREACHABLE();
+ return static_cast<Bytecode>(-1);
+}
+
+// static
int Bytecodes::Size(Bytecode bytecode) {
DCHECK(bytecode <= Bytecode::kLast);
switch (bytecode) {
@@ -100,6 +116,21 @@
// static
+int Bytecodes::NumberOfRegisterOperands(Bytecode bytecode) {
+ DCHECK(bytecode <= Bytecode::kLast);
+ switch (bytecode) {
+#define CASE(Name, ...) \
+ case Bytecode::k##Name: \
+ typedef BytecodeTraits<__VA_ARGS__, OPERAND_TERM> Name##Trait; \
+ return Name##Trait::kRegisterOperandCount;
+ BYTECODE_LIST(CASE)
+#undef CASE
+ }
+ UNREACHABLE();
+ return false;
+}
+
+// static
OperandType Bytecodes::GetOperandType(Bytecode bytecode, int i) {
DCHECK(bytecode <= Bytecode::kLast);
switch (bytecode) {
@@ -130,6 +161,21 @@
// static
+int Bytecodes::GetRegisterOperandBitmap(Bytecode bytecode) {
+ DCHECK(bytecode <= Bytecode::kLast);
+ switch (bytecode) {
+#define CASE(Name, ...) \
+ case Bytecode::k##Name: \
+ typedef BytecodeTraits<__VA_ARGS__, OPERAND_TERM> Name##Trait; \
+ return Name##Trait::kRegisterOperandBitmap;
+ BYTECODE_LIST(CASE)
+#undef CASE
+ }
+ UNREACHABLE();
+ return false;
+}
+
+// static
int Bytecodes::GetOperandOffset(Bytecode bytecode, int i) {
DCHECK(bytecode <= Bytecode::kLast);
switch (bytecode) {
@@ -164,6 +210,7 @@
bytecode == Bytecode::kJumpIfFalse ||
bytecode == Bytecode::kJumpIfToBooleanTrue ||
bytecode == Bytecode::kJumpIfToBooleanFalse ||
+ bytecode == Bytecode::kJumpIfNotHole ||
bytecode == Bytecode::kJumpIfNull ||
bytecode == Bytecode::kJumpIfUndefined;
}
@@ -175,6 +222,7 @@
bytecode == Bytecode::kJumpIfFalseConstant ||
bytecode == Bytecode::kJumpIfToBooleanTrueConstant ||
bytecode == Bytecode::kJumpIfToBooleanFalseConstant ||
+ bytecode == Bytecode::kJumpIfNotHoleConstant ||
bytecode == Bytecode::kJumpIfNullConstant ||
bytecode == Bytecode::kJumpIfUndefinedConstant;
}
@@ -186,6 +234,7 @@
bytecode == Bytecode::kJumpIfFalseConstantWide ||
bytecode == Bytecode::kJumpIfToBooleanTrueConstantWide ||
bytecode == Bytecode::kJumpIfToBooleanFalseConstantWide ||
+ bytecode == Bytecode::kJumpIfNotHoleConstantWide ||
bytecode == Bytecode::kJumpIfNullConstantWide ||
bytecode == Bytecode::kJumpIfUndefinedConstantWide;
}
@@ -227,10 +276,122 @@
// static
+bool Bytecodes::IsCallOrNew(Bytecode bytecode) {
+ return bytecode == Bytecode::kCall || bytecode == Bytecode::kTailCall ||
+ bytecode == Bytecode::kNew || bytecode == Bytecode::kCallWide ||
+ bytecode == Bytecode::kTailCallWide || bytecode == Bytecode::kNewWide;
+}
+
+// static
+bool Bytecodes::IsDebugBreak(Bytecode bytecode) {
+ switch (bytecode) {
+#define CASE(Name, ...) case Bytecode::k##Name:
+ DEBUG_BREAK_BYTECODE_LIST(CASE);
+#undef CASE
+ return true;
+ default:
+ break;
+ }
+ return false;
+}
+
+// static
bool Bytecodes::IsJumpOrReturn(Bytecode bytecode) {
return bytecode == Bytecode::kReturn || IsJump(bytecode);
}
+// static
+bool Bytecodes::IsIndexOperandType(OperandType operand_type) {
+ return operand_type == OperandType::kIdx8 ||
+ operand_type == OperandType::kIdx16;
+}
+
+// static
+bool Bytecodes::IsImmediateOperandType(OperandType operand_type) {
+ return operand_type == OperandType::kImm8;
+}
+
+// static
+bool Bytecodes::IsRegisterCountOperandType(OperandType operand_type) {
+ return (operand_type == OperandType::kRegCount8 ||
+ operand_type == OperandType::kRegCount16);
+}
+
+// static
+bool Bytecodes::IsMaybeRegisterOperandType(OperandType operand_type) {
+ return (operand_type == OperandType::kMaybeReg8 ||
+ operand_type == OperandType::kMaybeReg16);
+}
+
+// static
+bool Bytecodes::IsRegisterOperandType(OperandType operand_type) {
+ switch (operand_type) {
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ return true;
+ REGISTER_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ break;
+ NON_REGISTER_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+ }
+ return false;
+}
+
+// static
+bool Bytecodes::IsRegisterInputOperandType(OperandType operand_type) {
+ switch (operand_type) {
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ return true;
+ REGISTER_INPUT_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ break;
+ NON_REGISTER_OPERAND_TYPE_LIST(CASE)
+ REGISTER_OUTPUT_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+ }
+ return false;
+}
+
+// static
+bool Bytecodes::IsRegisterOutputOperandType(OperandType operand_type) {
+ switch (operand_type) {
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ return true;
+ REGISTER_OUTPUT_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+#define CASE(Name, _) \
+ case OperandType::k##Name: \
+ break;
+ NON_REGISTER_OPERAND_TYPE_LIST(CASE)
+ REGISTER_INPUT_OPERAND_TYPE_LIST(CASE)
+#undef CASE
+ }
+ return false;
+}
+
+namespace {
+static Register DecodeRegister(const uint8_t* operand_start,
+ OperandType operand_type) {
+ switch (Bytecodes::SizeOfOperand(operand_type)) {
+ case OperandSize::kByte:
+ return Register::FromOperand(*operand_start);
+ case OperandSize::kShort:
+ return Register::FromWideOperand(ReadUnalignedUInt16(operand_start));
+ case OperandSize::kNone: {
+ UNREACHABLE();
+ }
+ }
+ return Register();
+}
+} // namespace
+
// static
std::ostream& Bytecodes::Decode(std::ostream& os, const uint8_t* bytecode_start,
@@ -251,16 +412,20 @@
os << bytecode << " ";
+ // Operands for the debug break are from the original instruction.
+ if (IsDebugBreak(bytecode)) return os;
+
int number_of_operands = NumberOfOperands(bytecode);
+ int range = 0;
for (int i = 0; i < number_of_operands; i++) {
OperandType op_type = GetOperandType(bytecode, i);
const uint8_t* operand_start =
&bytecode_start[GetOperandOffset(bytecode, i)];
switch (op_type) {
- case interpreter::OperandType::kCount8:
+ case interpreter::OperandType::kRegCount8:
os << "#" << static_cast<unsigned int>(*operand_start);
break;
- case interpreter::OperandType::kCount16:
+ case interpreter::OperandType::kRegCount16:
os << '#' << ReadUnalignedUInt16(operand_start);
break;
case interpreter::OperandType::kIdx8:
@@ -272,48 +437,28 @@
case interpreter::OperandType::kImm8:
os << "#" << static_cast<int>(static_cast<int8_t>(*operand_start));
break;
+ case interpreter::OperandType::kMaybeReg8:
+ case interpreter::OperandType::kMaybeReg16:
case interpreter::OperandType::kReg8:
- case interpreter::OperandType::kMaybeReg8: {
- Register reg = Register::FromOperand(*operand_start);
- if (reg.is_function_context()) {
- os << "<context>";
- } else if (reg.is_function_closure()) {
- os << "<closure>";
- } else if (reg.is_new_target()) {
- os << "<new.target>";
- } else if (reg.is_parameter()) {
- int parameter_index = reg.ToParameterIndex(parameter_count);
- if (parameter_index == 0) {
- os << "<this>";
- } else {
- os << "a" << parameter_index - 1;
- }
- } else {
- os << "r" << reg.index();
- }
+ case interpreter::OperandType::kReg16:
+ case interpreter::OperandType::kRegOut8:
+ case interpreter::OperandType::kRegOut16: {
+ Register reg = DecodeRegister(operand_start, op_type);
+ os << reg.ToString(parameter_count);
break;
}
- case interpreter::OperandType::kRegPair8: {
- Register reg = Register::FromOperand(*operand_start);
- if (reg.is_parameter()) {
- int parameter_index = reg.ToParameterIndex(parameter_count);
- DCHECK_NE(parameter_index, 0);
- os << "a" << parameter_index - 1 << "-" << parameter_index;
- } else {
- os << "r" << reg.index() << "-" << reg.index() + 1;
- }
- break;
- }
- case interpreter::OperandType::kReg16: {
- Register reg =
- Register::FromWideOperand(ReadUnalignedUInt16(operand_start));
- if (reg.is_parameter()) {
- int parameter_index = reg.ToParameterIndex(parameter_count);
- DCHECK_NE(parameter_index, 0);
- os << "a" << parameter_index - 1;
- } else {
- os << "r" << reg.index();
- }
+ case interpreter::OperandType::kRegOutTriple8:
+ case interpreter::OperandType::kRegOutTriple16:
+ range += 1;
+ case interpreter::OperandType::kRegOutPair8:
+ case interpreter::OperandType::kRegOutPair16:
+ case interpreter::OperandType::kRegPair8:
+ case interpreter::OperandType::kRegPair16: {
+ range += 1;
+ Register first_reg = DecodeRegister(operand_start, op_type);
+ Register last_reg = Register(first_reg.index() + range);
+ os << first_reg.ToString(parameter_count) << "-"
+ << last_reg.ToString(parameter_count);
break;
}
case interpreter::OperandType::kNone:
@@ -327,7 +472,6 @@
return os;
}
-
std::ostream& operator<<(std::ostream& os, const Bytecode& bytecode) {
return os << Bytecodes::ToString(bytecode);
}
@@ -342,22 +486,33 @@
return os << Bytecodes::OperandSizeToString(operand_size);
}
-
static const int kLastParamRegisterIndex =
-InterpreterFrameConstants::kLastParamFromRegisterPointer / kPointerSize;
static const int kFunctionClosureRegisterIndex =
-InterpreterFrameConstants::kFunctionFromRegisterPointer / kPointerSize;
-static const int kFunctionContextRegisterIndex =
+static const int kCurrentContextRegisterIndex =
-InterpreterFrameConstants::kContextFromRegisterPointer / kPointerSize;
static const int kNewTargetRegisterIndex =
-InterpreterFrameConstants::kNewTargetFromRegisterPointer / kPointerSize;
+// The register space is a signed 16-bit space. Register operands
+// occupy range above 0. Parameter indices are biased with the
+// negative value kLastParamRegisterIndex for ease of access in the
+// interpreter.
+static const int kMaxParameterIndex = kMaxInt16 + kLastParamRegisterIndex;
+static const int kMaxRegisterIndex = -kMinInt16;
+static const int kMaxReg8Index = -kMinInt8;
+static const int kMinReg8Index = -kMaxInt8;
+static const int kMaxReg16Index = -kMinInt16;
+static const int kMinReg16Index = -kMaxInt16;
-// Registers occupy range 0-127 in 8-bit value leaving 128 unused values.
-// Parameter indices are biased with the negative value kLastParamRegisterIndex
-// for ease of access in the interpreter.
-static const int kMaxParameterIndex = 128 + kLastParamRegisterIndex;
+bool Register::is_byte_operand() const {
+ return index_ >= kMinReg8Index && index_ <= kMaxReg8Index;
+}
+bool Register::is_short_operand() const {
+ return index_ >= kMinReg16Index && index_ <= kMaxReg16Index;
+}
Register Register::FromParameterIndex(int index, int parameter_count) {
DCHECK_GE(index, 0);
@@ -365,7 +520,6 @@
DCHECK_LE(parameter_count, kMaxParameterIndex + 1);
int register_index = kLastParamRegisterIndex - parameter_count + index + 1;
DCHECK_LT(register_index, 0);
- DCHECK_GE(register_index, kMinInt8);
return Register(register_index);
}
@@ -386,13 +540,13 @@
}
-Register Register::function_context() {
- return Register(kFunctionContextRegisterIndex);
+Register Register::current_context() {
+ return Register(kCurrentContextRegisterIndex);
}
-bool Register::is_function_context() const {
- return index() == kFunctionContextRegisterIndex;
+bool Register::is_current_context() const {
+ return index() == kCurrentContextRegisterIndex;
}
@@ -403,13 +557,14 @@
return index() == kNewTargetRegisterIndex;
}
-
int Register::MaxParameterIndex() { return kMaxParameterIndex; }
+int Register::MaxRegisterIndex() { return kMaxRegisterIndex; }
+
+int Register::MaxRegisterIndexForByteOperand() { return kMaxReg8Index; }
uint8_t Register::ToOperand() const {
- DCHECK_GE(index_, kMinInt8);
- DCHECK_LE(index_, kMaxInt8);
+ DCHECK(is_byte_operand());
return static_cast<uint8_t>(-index_);
}
@@ -420,8 +575,7 @@
uint16_t Register::ToWideOperand() const {
- DCHECK_GE(index_, kMinInt16);
- DCHECK_LE(index_, kMaxInt16);
+ DCHECK(is_short_operand());
return static_cast<uint16_t>(-index_);
}
@@ -431,6 +585,16 @@
}
+uint32_t Register::ToRawOperand() const {
+ return static_cast<uint32_t>(-index_);
+}
+
+
+Register Register::FromRawOperand(uint32_t operand) {
+ return Register(-static_cast<int32_t>(operand));
+}
+
+
bool Register::AreContiguous(Register reg1, Register reg2, Register reg3,
Register reg4, Register reg5) {
if (reg1.index() + 1 != reg2.index()) {
@@ -448,6 +612,29 @@
return true;
}
+std::string Register::ToString(int parameter_count) {
+ if (is_current_context()) {
+ return std::string("<context>");
+ } else if (is_function_closure()) {
+ return std::string("<closure>");
+ } else if (is_new_target()) {
+ return std::string("<new.target>");
+ } else if (is_parameter()) {
+ int parameter_index = ToParameterIndex(parameter_count);
+ if (parameter_index == 0) {
+ return std::string("<this>");
+ } else {
+ std::ostringstream s;
+ s << "a" << parameter_index - 1;
+ return s.str();
+ }
+ } else {
+ std::ostringstream s;
+ s << "r" << index();
+ return s.str();
+ }
+}
+
} // namespace interpreter
} // namespace internal
} // namespace v8