Commit 141bc11e authored by jyan's avatar jyan Committed by Commit bot

S390: Fix storing to below stack to avoid sampler handler corrupting stored value

R=joransiu@ca.ibm.com, mbrandy@us.ibm.com, michael_dawson@ca.ibm.com
BUG=

Review-Url: https://codereview.chromium.org/1936953004
Cr-Commit-Position: refs/heads/master@{#35953}
parent 59b9ff3f
...@@ -1302,8 +1302,8 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction( ...@@ -1302,8 +1302,8 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
#endif #endif
case kS390_Push: case kS390_Push:
if (instr->InputAt(0)->IsDoubleRegister()) { if (instr->InputAt(0)->IsDoubleRegister()) {
__ StoreDouble(i.InputDoubleRegister(0), MemOperand(sp, -kDoubleSize));
__ lay(sp, MemOperand(sp, -kDoubleSize)); __ lay(sp, MemOperand(sp, -kDoubleSize));
__ StoreDouble(i.InputDoubleRegister(0), MemOperand(sp));
frame_access_state()->IncreaseSPDelta(kDoubleSize / kPointerSize); frame_access_state()->IncreaseSPDelta(kDoubleSize / kPointerSize);
} else { } else {
__ Push(i.InputRegister(0)); __ Push(i.InputRegister(0));
...@@ -1312,14 +1312,14 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction( ...@@ -1312,14 +1312,14 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
break; break;
case kS390_PushFrame: { case kS390_PushFrame: {
int num_slots = i.InputInt32(1); int num_slots = i.InputInt32(1);
__ lay(sp, MemOperand(sp, -num_slots * kPointerSize));
if (instr->InputAt(0)->IsDoubleRegister()) { if (instr->InputAt(0)->IsDoubleRegister()) {
__ StoreDouble(i.InputDoubleRegister(0), __ StoreDouble(i.InputDoubleRegister(0),
MemOperand(sp, -num_slots * kPointerSize)); MemOperand(sp));
} else { } else {
__ StoreP(i.InputRegister(0), __ StoreP(i.InputRegister(0),
MemOperand(sp, -num_slots * kPointerSize)); MemOperand(sp));
} }
__ lay(sp, MemOperand(sp, -num_slots * kPointerSize));
break; break;
} }
case kS390_StoreToStackSlot: { case kS390_StoreToStackSlot: {
...@@ -1494,36 +1494,30 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction( ...@@ -1494,36 +1494,30 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
__ ldebr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); __ ldebr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
break; break;
case kS390_DoubleExtractLowWord32: case kS390_DoubleExtractLowWord32:
// TODO(john.yan): this can cause problem when interrupting, __ lgdr(i.OutputRegister(), i.InputDoubleRegister(0));
// use freg->greg instruction __ llgfr(i.OutputRegister(), i.OutputRegister());
__ stdy(i.InputDoubleRegister(0), MemOperand(sp, -kDoubleSize));
__ LoadlW(i.OutputRegister(),
MemOperand(sp, -kDoubleSize + Register::kMantissaOffset));
break; break;
case kS390_DoubleExtractHighWord32: case kS390_DoubleExtractHighWord32:
// TODO(john.yan): this can cause problem when interrupting, __ lgdr(i.OutputRegister(), i.InputDoubleRegister(0));
// use freg->greg instruction __ srlg(i.OutputRegister(), i.OutputRegister(), Operand(32));
__ stdy(i.InputDoubleRegister(0), MemOperand(sp, -kDoubleSize));
__ LoadlW(i.OutputRegister(),
MemOperand(sp, -kDoubleSize + Register::kExponentOffset));
break; break;
case kS390_DoubleInsertLowWord32: case kS390_DoubleInsertLowWord32:
__ InsertDoubleLow(i.OutputDoubleRegister(), i.InputRegister(1)); __ lgdr(kScratchReg, i.OutputDoubleRegister());
__ lr(kScratchReg, i.InputRegister(1));
__ ldgr(i.OutputDoubleRegister(), kScratchReg);
break; break;
case kS390_DoubleInsertHighWord32: case kS390_DoubleInsertHighWord32:
__ InsertDoubleHigh(i.OutputDoubleRegister(), i.InputRegister(1)); __ sllg(kScratchReg, i.InputRegister(1), Operand(32));
__ lgdr(r0, i.OutputDoubleRegister());
__ lr(kScratchReg, r0);
__ ldgr(i.OutputDoubleRegister(), kScratchReg);
break; break;
case kS390_DoubleConstruct: case kS390_DoubleConstruct:
// TODO(john.yan): this can cause problem when interrupting, __ sllg(kScratchReg, i.InputRegister(0), Operand(32));
// use greg->freg instruction __ lr(kScratchReg, i.InputRegister(1));
#if V8_TARGET_LITTLE_ENDIAN
__ StoreW(i.InputRegister(0), MemOperand(sp, -kDoubleSize / 2)); // Bitwise convert from GPR to FPR
__ StoreW(i.InputRegister(1), MemOperand(sp, -kDoubleSize)); __ ldgr(i.OutputDoubleRegister(), kScratchReg);
#else
__ StoreW(i.InputRegister(1), MemOperand(sp, -kDoubleSize / 2));
__ StoreW(i.InputRegister(0), MemOperand(sp, -kDoubleSize));
#endif
__ ldy(i.OutputDoubleRegister(), MemOperand(sp, -kDoubleSize));
break; break;
case kS390_LoadWordS8: case kS390_LoadWordS8:
ASSEMBLE_LOAD_INTEGER(LoadlB); ASSEMBLE_LOAD_INTEGER(LoadlB);
......
...@@ -5210,14 +5210,11 @@ void LCodeGen::DoClampTToUint8(LClampTToUint8* instr) { ...@@ -5210,14 +5210,11 @@ void LCodeGen::DoClampTToUint8(LClampTToUint8* instr) {
void LCodeGen::DoDoubleBits(LDoubleBits* instr) { void LCodeGen::DoDoubleBits(LDoubleBits* instr) {
DoubleRegister value_reg = ToDoubleRegister(instr->value()); DoubleRegister value_reg = ToDoubleRegister(instr->value());
Register result_reg = ToRegister(instr->result()); Register result_reg = ToRegister(instr->result());
// TODO(joransiu): Use non-memory version. __ lgdr(result_reg, value_reg);
__ stdy(value_reg, MemOperand(sp, -kDoubleSize));
if (instr->hydrogen()->bits() == HDoubleBits::HIGH) { if (instr->hydrogen()->bits() == HDoubleBits::HIGH) {
__ LoadlW(result_reg, __ srlg(result_reg, result_reg, Operand(32));
MemOperand(sp, -kDoubleSize + Register::kExponentOffset));
} else { } else {
__ LoadlW(result_reg, __ llgfr(result_reg, result_reg);
MemOperand(sp, -kDoubleSize + Register::kMantissaOffset));
} }
} }
...@@ -5225,7 +5222,6 @@ void LCodeGen::DoConstructDouble(LConstructDouble* instr) { ...@@ -5225,7 +5222,6 @@ void LCodeGen::DoConstructDouble(LConstructDouble* instr) {
Register hi_reg = ToRegister(instr->hi()); Register hi_reg = ToRegister(instr->hi());
Register lo_reg = ToRegister(instr->lo()); Register lo_reg = ToRegister(instr->lo());
DoubleRegister result_reg = ToDoubleRegister(instr->result()); DoubleRegister result_reg = ToDoubleRegister(instr->result());
// TODO(joransiu): Construct with ldgr
Register scratch = scratch0(); Register scratch = scratch0();
// Combine hi_reg:lo_reg into a single 64-bit register. // Combine hi_reg:lo_reg into a single 64-bit register.
......
...@@ -364,7 +364,7 @@ void Assembler::target_at_put(int pos, int target_pos, bool* is_branch) { ...@@ -364,7 +364,7 @@ void Assembler::target_at_put(int pos, int target_pos, bool* is_branch) {
if (BRC == opcode || BRCT == opcode || BRCTG == opcode) { if (BRC == opcode || BRCT == opcode || BRCTG == opcode) {
int16_t imm16 = target_pos - pos; int16_t imm16 = target_pos - pos;
instr &= (~0xffff); instr &= (~0xffff);
CHECK(is_int16(imm16)); DCHECK(is_int16(imm16));
instr_at_put<FourByteInstr>(pos, instr | (imm16 >> 1)); instr_at_put<FourByteInstr>(pos, instr | (imm16 >> 1));
return; return;
} else if (BRCL == opcode || LARL == opcode || BRASL == opcode) { } else if (BRCL == opcode || LARL == opcode || BRASL == opcode) {
...@@ -374,7 +374,7 @@ void Assembler::target_at_put(int pos, int target_pos, bool* is_branch) { ...@@ -374,7 +374,7 @@ void Assembler::target_at_put(int pos, int target_pos, bool* is_branch) {
instr_at_put<SixByteInstr>(pos, instr | (imm32 >> 1)); instr_at_put<SixByteInstr>(pos, instr | (imm32 >> 1));
return; return;
} else if (LLILF == opcode) { } else if (LLILF == opcode) {
CHECK(target_pos == kEndOfChain || target_pos >= 0); DCHECK(target_pos == kEndOfChain || target_pos >= 0);
// Emitted label constant, not part of a branch. // Emitted label constant, not part of a branch.
// Make label relative to Code* of generated Code object. // Make label relative to Code* of generated Code object.
int32_t imm32 = target_pos + (Code::kHeaderSize - kHeapObjectTag); int32_t imm32 = target_pos + (Code::kHeaderSize - kHeapObjectTag);
...@@ -2538,6 +2538,7 @@ void Assembler::mvghi(const MemOperand& opnd1, const Operand& i2) { ...@@ -2538,6 +2538,7 @@ void Assembler::mvghi(const MemOperand& opnd1, const Operand& i2) {
// Store Register (64) // Store Register (64)
void Assembler::stg(Register src, const MemOperand& dst) { void Assembler::stg(Register src, const MemOperand& dst) {
DCHECK(!(dst.rb().code() == 15 && dst.offset() < 0));
rxy_form(STG, src, dst.rx(), dst.rb(), dst.offset()); rxy_form(STG, src, dst.rx(), dst.rb(), dst.offset());
} }
...@@ -2735,6 +2736,7 @@ void Assembler::std(DoubleRegister r1, const MemOperand& opnd) { ...@@ -2735,6 +2736,7 @@ void Assembler::std(DoubleRegister r1, const MemOperand& opnd) {
// Store Double (64) // Store Double (64)
void Assembler::stdy(DoubleRegister r1, const MemOperand& opnd) { void Assembler::stdy(DoubleRegister r1, const MemOperand& opnd) {
DCHECK(!(opnd.rb().code() == 15 && opnd.offset() < 0));
rxy_form(STDY, r1, opnd.rx(), opnd.rb(), opnd.offset()); rxy_form(STDY, r1, opnd.rx(), opnd.rb(), opnd.offset());
} }
...@@ -2745,6 +2747,7 @@ void Assembler::ste(DoubleRegister r1, const MemOperand& opnd) { ...@@ -2745,6 +2747,7 @@ void Assembler::ste(DoubleRegister r1, const MemOperand& opnd) {
// Store Float (32) // Store Float (32)
void Assembler::stey(DoubleRegister r1, const MemOperand& opnd) { void Assembler::stey(DoubleRegister r1, const MemOperand& opnd) {
DCHECK(!(opnd.rb().code() == 15 && opnd.offset() < 0));
rxy_form(STEY, r1, opnd.rx(), opnd.rb(), opnd.offset()); rxy_form(STEY, r1, opnd.rx(), opnd.rb(), opnd.offset());
} }
......
...@@ -4260,10 +4260,9 @@ void ProfileEntryHookStub::Generate(MacroAssembler* masm) { ...@@ -4260,10 +4260,9 @@ void ProfileEntryHookStub::Generate(MacroAssembler* masm) {
// zLinux ABI requires caller's frame to have sufficient space for callee // zLinux ABI requires caller's frame to have sufficient space for callee
// preserved regsiter save area. // preserved regsiter save area.
__ LoadImmP(r0, Operand::Zero()); __ LoadImmP(r0, Operand::Zero());
__ StoreP(r0, MemOperand(sp, -kCalleeRegisterSaveAreaSize -
kNumRequiredStackFrameSlots * kPointerSize));
__ lay(sp, MemOperand(sp, -kCalleeRegisterSaveAreaSize - __ lay(sp, MemOperand(sp, -kCalleeRegisterSaveAreaSize -
kNumRequiredStackFrameSlots * kPointerSize)); kNumRequiredStackFrameSlots * kPointerSize));
__ StoreP(r0, MemOperand(sp));
#if defined(USE_SIMULATOR) #if defined(USE_SIMULATOR)
// Under the simulator we need to indirect the entry hook through a // Under the simulator we need to indirect the entry hook through a
// trampoline function at a known address. // trampoline function at a known address.
......
...@@ -205,26 +205,6 @@ void MacroAssembler::Move(DoubleRegister dst, DoubleRegister src) { ...@@ -205,26 +205,6 @@ void MacroAssembler::Move(DoubleRegister dst, DoubleRegister src) {
} }
} }
void MacroAssembler::InsertDoubleLow(DoubleRegister dst, Register src) {
StoreDouble(dst, MemOperand(sp, -kDoubleSize));
#if V8_TARGET_LITTLE_ENDIAN
StoreW(src, MemOperand(sp, -kDoubleSize));
#else
StoreW(src, MemOperand(sp, -kDoubleSize / 2));
#endif
ldy(dst, MemOperand(sp, -kDoubleSize));
}
void MacroAssembler::InsertDoubleHigh(DoubleRegister dst, Register src) {
StoreDouble(dst, MemOperand(sp, -kDoubleSize));
#if V8_TARGET_LITTLE_ENDIAN
StoreW(src, MemOperand(sp, -kDoubleSize / 2));
#else
StoreW(src, MemOperand(sp, -kDoubleSize));
#endif
ldy(dst, MemOperand(sp, -kDoubleSize));
}
void MacroAssembler::MultiPush(RegList regs, Register location) { void MacroAssembler::MultiPush(RegList regs, Register location) {
int16_t num_to_push = NumberOfBitsSet(regs); int16_t num_to_push = NumberOfBitsSet(regs);
int16_t stack_offset = num_to_push * kPointerSize; int16_t stack_offset = num_to_push * kPointerSize;
...@@ -1113,9 +1093,8 @@ void MacroAssembler::EnterExitFrame(bool save_doubles, int stack_space) { ...@@ -1113,9 +1093,8 @@ void MacroAssembler::EnterExitFrame(bool save_doubles, int stack_space) {
ClearRightImm(sp, sp, Operand(3)); // equivalent to &= -8 ClearRightImm(sp, sp, Operand(3)); // equivalent to &= -8
} }
StoreP(MemOperand(sp, -kNumRequiredStackFrameSlots * kPointerSize),
Operand::Zero(), r0);
lay(sp, MemOperand(sp, -kNumRequiredStackFrameSlots * kPointerSize)); lay(sp, MemOperand(sp, -kNumRequiredStackFrameSlots * kPointerSize));
StoreP(MemOperand(sp), Operand::Zero(), r0);
// Set the exit frame sp value to point just before the return address // Set the exit frame sp value to point just before the return address
// location. // location.
lay(r1, MemOperand(sp, kStackFrameSPSlot * kPointerSize)); lay(r1, MemOperand(sp, kStackFrameSPSlot * kPointerSize));
...@@ -2330,9 +2309,8 @@ void MacroAssembler::TestDoubleIsMinusZero(DoubleRegister input, ...@@ -2330,9 +2309,8 @@ void MacroAssembler::TestDoubleIsMinusZero(DoubleRegister input,
} }
void MacroAssembler::TestDoubleSign(DoubleRegister input, Register scratch) { void MacroAssembler::TestDoubleSign(DoubleRegister input, Register scratch) {
stdy(input, MemOperand(sp, -kDoubleSize)); lgdr(scratch, input);
LoadlW(scratch, MemOperand(sp, -kDoubleSize + Register::kExponentOffset)); cgfi(scratch, Operand::Zero());
Cmp32(scratch, Operand::Zero());
} }
void MacroAssembler::TestHeapNumberSign(Register input, Register scratch) { void MacroAssembler::TestHeapNumberSign(Register input, Register scratch) {
...@@ -2377,8 +2355,8 @@ void MacroAssembler::TryInt32Floor(Register result, DoubleRegister double_input, ...@@ -2377,8 +2355,8 @@ void MacroAssembler::TryInt32Floor(Register result, DoubleRegister double_input,
Label exception; Label exception;
// Move high word into input_high // Move high word into input_high
StoreDouble(double_input, MemOperand(sp, -kDoubleSize));
lay(sp, MemOperand(sp, -kDoubleSize)); lay(sp, MemOperand(sp, -kDoubleSize));
StoreDouble(double_input, MemOperand(sp));
LoadlW(input_high, MemOperand(sp, Register::kExponentOffset)); LoadlW(input_high, MemOperand(sp, Register::kExponentOffset));
la(sp, MemOperand(sp, kDoubleSize)); la(sp, MemOperand(sp, kDoubleSize));
...@@ -2444,8 +2422,8 @@ void MacroAssembler::TruncateDoubleToI(Register result, ...@@ -2444,8 +2422,8 @@ void MacroAssembler::TruncateDoubleToI(Register result,
// If we fell through then inline version didn't succeed - call stub instead. // If we fell through then inline version didn't succeed - call stub instead.
push(r14); push(r14);
// Put input on stack. // Put input on stack.
StoreDouble(double_input, MemOperand(sp, -kDoubleSize));
lay(sp, MemOperand(sp, -kDoubleSize)); lay(sp, MemOperand(sp, -kDoubleSize));
StoreDouble(double_input, MemOperand(sp));
DoubleToIStub stub(isolate(), sp, result, 0, true, true); DoubleToIStub stub(isolate(), sp, result, 0, true, true);
CallStub(&stub); CallStub(&stub);
......
...@@ -214,9 +214,6 @@ class MacroAssembler : public Assembler { ...@@ -214,9 +214,6 @@ class MacroAssembler : public Assembler {
void Move(Register dst, Register src, Condition cond = al); void Move(Register dst, Register src, Condition cond = al);
void Move(DoubleRegister dst, DoubleRegister src); void Move(DoubleRegister dst, DoubleRegister src);
void InsertDoubleLow(DoubleRegister dst, Register src);
void InsertDoubleHigh(DoubleRegister dst, Register src);
void MultiPush(RegList regs, Register location = sp); void MultiPush(RegList regs, Register location = sp);
void MultiPop(RegList regs, Register location = sp); void MultiPop(RegList regs, Register location = sp);
......
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