Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(151)

Unified Diff: src/compiler/x64/code-generator-x64.cc

Issue 612573004: [turbofan] cleanup x64 code generator a little (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: rebase Created 6 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/compiler/x64/code-generator-x64.cc
diff --git a/src/compiler/x64/code-generator-x64.cc b/src/compiler/x64/code-generator-x64.cc
index fdf63855d59cac64d5f9083657a8688d769c4347..e6dfaf1e7785051423cf910210c20c894e299400 100644
--- a/src/compiler/x64/code-generator-x64.cc
+++ b/src/compiler/x64/code-generator-x64.cc
@@ -19,130 +19,34 @@ namespace compiler {
#define __ masm()->
-// TODO(turbofan): Cleanup these hacks.
-enum Immediate64Type { kImm64Value, kImm64Handle, kImm64Reference };
-
-
-struct Immediate64 {
- uint64_t value;
- Handle<Object> handle;
- ExternalReference reference;
- Immediate64Type type;
-};
-
-
-enum RegisterOrOperandType { kRegister, kDoubleRegister, kOperand };
-
-
-struct RegisterOrOperand {
- RegisterOrOperand() : operand(no_reg, 0) {}
- Register reg;
- DoubleRegister double_reg;
- Operand operand;
- RegisterOrOperandType type;
-};
-
-
// Adds X64 specific methods for decoding operands.
class X64OperandConverter : public InstructionOperandConverter {
public:
X64OperandConverter(CodeGenerator* gen, Instruction* instr)
: InstructionOperandConverter(gen, instr) {}
- RegisterOrOperand InputRegisterOrOperand(int index) {
- return ToRegisterOrOperand(instr_->InputAt(index));
- }
-
Immediate InputImmediate(int index) {
return ToImmediate(instr_->InputAt(index));
}
- RegisterOrOperand OutputRegisterOrOperand() {
- return ToRegisterOrOperand(instr_->Output());
- }
-
- Immediate64 InputImmediate64(int index) {
- return ToImmediate64(instr_->InputAt(index));
- }
+ Operand InputOperand(int index) { return ToOperand(instr_->InputAt(index)); }
- Immediate64 ToImmediate64(InstructionOperand* operand) {
- Constant constant = ToConstant(operand);
- Immediate64 immediate;
- immediate.value = 0xbeefdeaddeefbeed;
- immediate.type = kImm64Value;
- switch (constant.type()) {
- case Constant::kInt32:
- case Constant::kInt64:
- immediate.value = constant.ToInt64();
- return immediate;
- case Constant::kFloat32:
- immediate.type = kImm64Handle;
- immediate.handle =
- isolate()->factory()->NewNumber(constant.ToFloat32(), TENURED);
- return immediate;
- case Constant::kFloat64:
- immediate.type = kImm64Handle;
- immediate.handle =
- isolate()->factory()->NewNumber(constant.ToFloat64(), TENURED);
- return immediate;
- case Constant::kExternalReference:
- immediate.type = kImm64Reference;
- immediate.reference = constant.ToExternalReference();
- return immediate;
- case Constant::kHeapObject:
- immediate.type = kImm64Handle;
- immediate.handle = constant.ToHeapObject();
- return immediate;
- }
- UNREACHABLE();
- return immediate;
- }
+ Operand OutputOperand() { return ToOperand(instr_->Output()); }
Immediate ToImmediate(InstructionOperand* operand) {
Constant constant = ToConstant(operand);
- switch (constant.type()) {
- case Constant::kInt32:
- return Immediate(constant.ToInt32());
- case Constant::kInt64:
- case Constant::kFloat32:
- case Constant::kFloat64:
- case Constant::kExternalReference:
- case Constant::kHeapObject:
- break;
+ if (constant.type() == Constant::kInt32) {
+ return Immediate(constant.ToInt32());
}
UNREACHABLE();
return Immediate(-1);
}
Operand ToOperand(InstructionOperand* op, int extra = 0) {
- RegisterOrOperand result = ToRegisterOrOperand(op, extra);
- DCHECK_EQ(kOperand, result.type);
- return result.operand;
- }
-
- RegisterOrOperand ToRegisterOrOperand(InstructionOperand* op, int extra = 0) {
- RegisterOrOperand result;
- if (op->IsRegister()) {
- DCHECK(extra == 0);
- result.type = kRegister;
- result.reg = ToRegister(op);
- return result;
- } else if (op->IsDoubleRegister()) {
- DCHECK(extra == 0);
- DCHECK(extra == 0);
- result.type = kDoubleRegister;
- result.double_reg = ToDoubleRegister(op);
- return result;
- }
-
DCHECK(op->IsStackSlot() || op->IsDoubleStackSlot());
-
- result.type = kOperand;
// The linkage computes where all spill slots are located.
FrameOffset offset = linkage()->GetFrameOffset(op->index(), frame(), extra);
- result.operand =
- Operand(offset.from_stack_pointer() ? rsp : rbp, offset.offset());
- return result;
+ return Operand(offset.from_stack_pointer() ? rsp : rbp, offset.offset());
}
static int NextOffset(int* offset) {
@@ -232,23 +136,51 @@ static bool HasImmediateInput(Instruction* instr, int index) {
}
-#define ASSEMBLE_BINOP(asm_instr) \
- do { \
- if (HasImmediateInput(instr, 1)) { \
- RegisterOrOperand input = i.InputRegisterOrOperand(0); \
- if (input.type == kRegister) { \
- __ asm_instr(input.reg, i.InputImmediate(1)); \
- } else { \
- __ asm_instr(input.operand, i.InputImmediate(1)); \
- } \
- } else { \
- RegisterOrOperand input = i.InputRegisterOrOperand(1); \
- if (input.type == kRegister) { \
- __ asm_instr(i.InputRegister(0), input.reg); \
- } else { \
- __ asm_instr(i.InputRegister(0), input.operand); \
- } \
- } \
+#define ASSEMBLE_UNOP(asm_instr) \
+ do { \
+ if (instr->Output()->IsRegister()) { \
+ __ asm_instr(i.OutputRegister()); \
+ } else { \
+ __ asm_instr(i.OutputOperand()); \
+ } \
+ } while (0)
+
+
+#define ASSEMBLE_BINOP(asm_instr) \
+ do { \
+ if (HasImmediateInput(instr, 1)) { \
+ if (instr->InputAt(0)->IsRegister()) { \
+ __ asm_instr(i.InputRegister(0), i.InputImmediate(1)); \
+ } else { \
+ __ asm_instr(i.InputOperand(0), i.InputImmediate(1)); \
+ } \
+ } else { \
+ if (instr->InputAt(1)->IsRegister()) { \
+ __ asm_instr(i.InputRegister(0), i.InputRegister(1)); \
+ } else { \
+ __ asm_instr(i.InputRegister(0), i.InputOperand(1)); \
+ } \
+ } \
+ } while (0)
+
+
+#define ASSEMBLE_MULT(asm_instr) \
+ do { \
+ if (HasImmediateInput(instr, 1)) { \
+ if (instr->InputAt(0)->IsRegister()) { \
+ __ asm_instr(i.OutputRegister(), i.InputRegister(0), \
+ i.InputImmediate(1)); \
+ } else { \
+ __ asm_instr(i.OutputRegister(), i.InputOperand(0), \
+ i.InputImmediate(1)); \
+ } \
+ } else { \
+ if (instr->InputAt(1)->IsRegister()) { \
+ __ asm_instr(i.OutputRegister(), i.InputRegister(1)); \
+ } else { \
+ __ asm_instr(i.OutputRegister(), i.InputOperand(1)); \
+ } \
+ } \
} while (0)
@@ -335,38 +267,10 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
ASSEMBLE_BINOP(testq);
break;
case kX64Imul32:
- if (HasImmediateInput(instr, 1)) {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ imull(i.OutputRegister(), input.reg, i.InputImmediate(1));
- } else {
- __ imull(i.OutputRegister(), input.operand, i.InputImmediate(1));
- }
- } else {
- RegisterOrOperand input = i.InputRegisterOrOperand(1);
- if (input.type == kRegister) {
- __ imull(i.OutputRegister(), input.reg);
- } else {
- __ imull(i.OutputRegister(), input.operand);
- }
- }
+ ASSEMBLE_MULT(imull);
break;
case kX64Imul:
- if (HasImmediateInput(instr, 1)) {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ imulq(i.OutputRegister(), input.reg, i.InputImmediate(1));
- } else {
- __ imulq(i.OutputRegister(), input.operand, i.InputImmediate(1));
- }
- } else {
- RegisterOrOperand input = i.InputRegisterOrOperand(1);
- if (input.type == kRegister) {
- __ imulq(i.OutputRegister(), input.reg);
- } else {
- __ imulq(i.OutputRegister(), input.operand);
- }
- }
+ ASSEMBLE_MULT(imulq);
break;
case kX64Idiv32:
__ cdq();
@@ -384,42 +288,18 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
__ xorq(rdx, rdx);
__ divq(i.InputRegister(1));
break;
- case kX64Not: {
- RegisterOrOperand output = i.OutputRegisterOrOperand();
- if (output.type == kRegister) {
- __ notq(output.reg);
- } else {
- __ notq(output.operand);
- }
+ case kX64Not:
+ ASSEMBLE_UNOP(notq);
break;
- }
- case kX64Not32: {
- RegisterOrOperand output = i.OutputRegisterOrOperand();
- if (output.type == kRegister) {
- __ notl(output.reg);
- } else {
- __ notl(output.operand);
- }
+ case kX64Not32:
+ ASSEMBLE_UNOP(notl);
break;
- }
- case kX64Neg: {
- RegisterOrOperand output = i.OutputRegisterOrOperand();
- if (output.type == kRegister) {
- __ negq(output.reg);
- } else {
- __ negq(output.operand);
- }
+ case kX64Neg:
+ ASSEMBLE_UNOP(negq);
break;
- }
- case kX64Neg32: {
- RegisterOrOperand output = i.OutputRegisterOrOperand();
- if (output.type == kRegister) {
- __ negl(output.reg);
- } else {
- __ negl(output.operand);
- }
+ case kX64Neg32:
+ ASSEMBLE_UNOP(negl);
break;
- }
case kX64Or32:
ASSEMBLE_BINOP(orl);
break;
@@ -456,15 +336,13 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
case kX64Ror:
ASSEMBLE_SHIFT(rorq, 6);
break;
- case kSSEFloat64Cmp: {
- RegisterOrOperand input = i.InputRegisterOrOperand(1);
- if (input.type == kDoubleRegister) {
- __ ucomisd(i.InputDoubleRegister(0), input.double_reg);
+ case kSSEFloat64Cmp:
+ if (instr->InputAt(1)->IsDoubleRegister()) {
+ __ ucomisd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
} else {
- __ ucomisd(i.InputDoubleRegister(0), input.operand);
+ __ ucomisd(i.InputDoubleRegister(0), i.InputOperand(1));
}
break;
- }
case kSSEFloat64Add:
__ addsd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
break;
@@ -508,56 +386,47 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
__ addq(rsp, Immediate(kDoubleSize));
break;
}
- case kSSEFloat64Sqrt: {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kDoubleRegister) {
- __ sqrtsd(i.OutputDoubleRegister(), input.double_reg);
+ case kSSEFloat64Sqrt:
+ if (instr->InputAt(0)->IsDoubleRegister()) {
+ __ sqrtsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
} else {
- __ sqrtsd(i.OutputDoubleRegister(), input.operand);
+ __ sqrtsd(i.OutputDoubleRegister(), i.InputOperand(0));
}
break;
- }
case kSSECvtss2sd:
__ cvtss2sd(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
break;
case kSSECvtsd2ss:
__ cvtsd2ss(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
break;
- case kSSEFloat64ToInt32: {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kDoubleRegister) {
- __ cvttsd2si(i.OutputRegister(), input.double_reg);
+ case kSSEFloat64ToInt32:
+ if (instr->InputAt(0)->IsDoubleRegister()) {
+ __ cvttsd2si(i.OutputRegister(), i.InputDoubleRegister(0));
} else {
- __ cvttsd2si(i.OutputRegister(), input.operand);
+ __ cvttsd2si(i.OutputRegister(), i.InputOperand(0));
}
break;
- }
- case kSSEFloat64ToUint32: {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kDoubleRegister) {
- __ cvttsd2siq(i.OutputRegister(), input.double_reg);
+ case kSSEFloat64ToUint32:
+ if (instr->InputAt(0)->IsDoubleRegister()) {
+ __ cvttsd2siq(i.OutputRegister(), i.InputDoubleRegister(0));
} else {
- __ cvttsd2siq(i.OutputRegister(), input.operand);
+ __ cvttsd2siq(i.OutputRegister(), i.InputOperand(0));
}
__ andl(i.OutputRegister(), i.OutputRegister()); // clear upper bits.
// TODO(turbofan): generated code should not look at the upper 32 bits
// of the result, but those bits could escape to the outside world.
break;
- }
- case kSSEInt32ToFloat64: {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ cvtlsi2sd(i.OutputDoubleRegister(), input.reg);
+ case kSSEInt32ToFloat64:
+ if (instr->InputAt(0)->IsRegister()) {
+ __ cvtlsi2sd(i.OutputDoubleRegister(), i.InputRegister(0));
} else {
- __ cvtlsi2sd(i.OutputDoubleRegister(), input.operand);
+ __ cvtlsi2sd(i.OutputDoubleRegister(), i.InputOperand(0));
}
break;
- }
- case kSSEUint32ToFloat64: {
+ case kSSEUint32ToFloat64:
// TODO(turbofan): X64 SSE cvtqsi2sd should support operands.
__ cvtqsi2sd(i.OutputDoubleRegister(), i.InputRegister(0));
break;
- }
case kX64Movsxbl:
__ movsxbl(i.OutputRegister(), i.MemoryOperand());
break;
@@ -593,11 +462,10 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
case kX64Movl:
if (instr->HasOutput()) {
if (instr->addressing_mode() == kMode_None) {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ movl(i.OutputRegister(), input.reg);
+ if (instr->InputAt(0)->IsRegister()) {
+ __ movl(i.OutputRegister(), i.InputRegister(0));
} else {
- __ movl(i.OutputRegister(), input.operand);
+ __ movl(i.OutputRegister(), i.InputOperand(0));
}
} else {
__ movl(i.OutputRegister(), i.MemoryOperand());
@@ -613,11 +481,10 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
}
break;
case kX64Movsxlq: {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ movsxlq(i.OutputRegister(), input.reg);
+ if (instr->InputAt(0)->IsRegister()) {
+ __ movsxlq(i.OutputRegister(), i.InputRegister(0));
} else {
- __ movsxlq(i.OutputRegister(), input.operand);
+ __ movsxlq(i.OutputRegister(), i.InputOperand(0));
}
break;
}
@@ -656,11 +523,10 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
if (HasImmediateInput(instr, 0)) {
__ pushq(i.InputImmediate(0));
} else {
- RegisterOrOperand input = i.InputRegisterOrOperand(0);
- if (input.type == kRegister) {
- __ pushq(input.reg);
+ if (instr->InputAt(0)->IsRegister()) {
+ __ pushq(i.InputRegister(0));
} else {
- __ pushq(input.operand);
+ __ pushq(i.InputOperand(0));
}
}
break;
@@ -968,16 +834,27 @@ void CodeGenerator::AssembleMove(InstructionOperand* source,
if (destination->IsRegister() || destination->IsStackSlot()) {
Register dst = destination->IsRegister() ? g.ToRegister(destination)
: kScratchRegister;
- Immediate64 imm = g.ToImmediate64(constant_source);
- switch (imm.type) {
- case kImm64Value:
- __ Set(dst, imm.value);
+ switch (src.type()) {
+ case Constant::kInt32:
+ // TODO(dcarney): don't need scratch in this case.
+ __ movq(dst, Immediate(src.ToInt32()));
+ break;
+ case Constant::kInt64:
+ __ Set(dst, src.ToInt64());
+ break;
+ case Constant::kFloat32:
+ __ Move(dst,
+ isolate()->factory()->NewNumber(src.ToFloat32(), TENURED));
+ break;
+ case Constant::kFloat64:
+ __ Move(dst,
+ isolate()->factory()->NewNumber(src.ToFloat64(), TENURED));
break;
- case kImm64Reference:
- __ Move(dst, imm.reference);
+ case Constant::kExternalReference:
+ __ Move(dst, src.ToExternalReference());
break;
- case kImm64Handle:
- __ Move(dst, imm.handle);
+ case Constant::kHeapObject:
+ __ Move(dst, src.ToHeapObject());
break;
}
if (destination->IsStackSlot()) {
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698