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

Side by Side Diff: src/IceTargetLoweringMIPS32.cpp

Issue 2656723003: [SubZero] Fix code generation of AtomicCmpxchg (Closed)
Patch Set: Created 3 years, 11 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 unified diff | Download patch
« no previous file with comments | « no previous file | tests_lit/llvm2ice_tests/nacl-atomic-intrinsics.ll » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // 1 //
2 // The Subzero Code Generator 2 // The Subzero Code Generator
3 // 3 //
4 // This file is distributed under the University of Illinois Open Source 4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details. 5 // License. See LICENSE.TXT for details.
6 // 6 //
7 //===----------------------------------------------------------------------===// 7 //===----------------------------------------------------------------------===//
8 /// 8 ///
9 /// \file 9 /// \file
10 /// \brief Implements the TargetLoweringMIPS32 class, which consists almost 10 /// \brief Implements the TargetLoweringMIPS32 class, which consists almost
(...skipping 4536 matching lines...) Expand 10 before | Expand all | Expand 10 after
4547 auto *New = Instr->getArg(2); 4547 auto *New = Instr->getArg(2);
4548 auto *Expected = Instr->getArg(1); 4548 auto *Expected = Instr->getArg(1);
4549 auto *ActualAddress = Instr->getArg(0); 4549 auto *ActualAddress = Instr->getArg(0);
4550 4550
4551 if (DestTy == IceType_i64) { 4551 if (DestTy == IceType_i64) {
4552 InstMIPS32Label *Retry1 = InstMIPS32Label::create(Func, this); 4552 InstMIPS32Label *Retry1 = InstMIPS32Label::create(Func, this);
4553 auto *T1 = I32Reg(); 4553 auto *T1 = I32Reg();
4554 auto *T2 = I32Reg(); 4554 auto *T2 = I32Reg();
4555 auto *T3 = I32Reg(); 4555 auto *T3 = I32Reg();
4556 auto *T4 = I32Reg(); 4556 auto *T4 = I32Reg();
4557 _sync(); 4557 auto *T5 = I32Reg();
4558 auto *T6 = I32Reg();
4558 Variable *ValHi, *ValLo, *ExpectedLo, *ExpectedHi; 4559 Variable *ValHi, *ValLo, *ExpectedLo, *ExpectedHi;
4559 if (llvm::isa<ConstantUndef>(Expected)) { 4560 if (llvm::isa<ConstantUndef>(Expected)) {
4560 ExpectedLo = legalizeToReg(Ctx->getConstantZero(IceType_i32)); 4561 ExpectedLo = legalizeToReg(Ctx->getConstantZero(IceType_i32));
4561 ExpectedHi = legalizeToReg(Ctx->getConstantZero(IceType_i32)); 4562 ExpectedHi = legalizeToReg(Ctx->getConstantZero(IceType_i32));
4562 } else if (auto *Expected64 = llvm::dyn_cast<Variable64On32>(Expected)) { 4563 } else if (auto *Expected64 = llvm::dyn_cast<Variable64On32>(Expected)) {
4563 ExpectedLo = legalizeToReg(loOperand(Expected64)); 4564 ExpectedLo = legalizeToReg(loOperand(Expected64));
4564 ExpectedHi = legalizeToReg(hiOperand(Expected64)); 4565 ExpectedHi = legalizeToReg(hiOperand(Expected64));
4565 } else if (auto *C64 = llvm::dyn_cast<ConstantInteger64>(Expected)) { 4566 } else if (auto *C64 = llvm::dyn_cast<ConstantInteger64>(Expected)) {
4566 const uint64_t Value = C64->getValue(); 4567 const uint64_t Value = C64->getValue();
4567 uint64_t Upper32Bits = (Value >> INT32_BITS) & 0xFFFFFFFF; 4568 uint64_t Upper32Bits = (Value >> INT32_BITS) & 0xFFFFFFFF;
(...skipping 18 matching lines...) Expand all
4586 auto *Dest64 = llvm::cast<Variable64On32>(Dest); 4587 auto *Dest64 = llvm::cast<Variable64On32>(Dest);
4587 auto *BaseR = legalizeToReg(ActualAddress); 4588 auto *BaseR = legalizeToReg(ActualAddress);
4588 auto *AddrLo = OperandMIPS32Mem::create( 4589 auto *AddrLo = OperandMIPS32Mem::create(
4589 Func, IceType_i32, BaseR, 4590 Func, IceType_i32, BaseR,
4590 llvm::cast<ConstantInteger32>(Ctx->getConstantInt32(0))); 4591 llvm::cast<ConstantInteger32>(Ctx->getConstantInt32(0)));
4591 auto *AddrHi = OperandMIPS32Mem::create( 4592 auto *AddrHi = OperandMIPS32Mem::create(
4592 Func, IceType_i32, BaseR, 4593 Func, IceType_i32, BaseR,
4593 llvm::cast<ConstantInteger32>(Ctx->getConstantInt32(4))); 4594 llvm::cast<ConstantInteger32>(Ctx->getConstantInt32(4)));
4594 lowerLoad(InstLoad::create(Func, T3, AddrLo)); 4595 lowerLoad(InstLoad::create(Func, T3, AddrLo));
4595 lowerLoad(InstLoad::create(Func, T4, AddrHi)); 4596 lowerLoad(InstLoad::create(Func, T4, AddrHi));
4597 _sync();
4596 Context.insert(Retry); 4598 Context.insert(Retry);
4597 Sandboxer(this).ll(T1, AddrLo); 4599 Sandboxer(this).ll(T1, AddrLo);
4598 _br(NoTarget, NoTarget, T1, ExpectedLo, Exit, CondMIPS32::Cond::NE); 4600 _br(NoTarget, NoTarget, T1, ExpectedLo, Exit, CondMIPS32::Cond::NE);
4599 Sandboxer(this).sc(ValLo, AddrLo); 4601 _mov(T5, ValLo);
4600 _br(NoTarget, NoTarget, ValLo, getZero(), Retry, CondMIPS32::Cond::EQ); 4602 Sandboxer(this).sc(T5, AddrLo);
4603 Context.insert<InstFakeUse>(ValLo);
4604 Context.insert<InstFakeUse>(ExpectedLo);
4605 _br(NoTarget, NoTarget, T5, getZero(), Retry, CondMIPS32::Cond::EQ);
4601 Context.insert(Retry1); 4606 Context.insert(Retry1);
4602 Sandboxer(this).ll(T2, AddrHi); 4607 Sandboxer(this).ll(T2, AddrHi);
4603 _br(NoTarget, NoTarget, T2, ExpectedHi, Exit, CondMIPS32::Cond::NE); 4608 _br(NoTarget, NoTarget, T2, ExpectedHi, Exit, CondMIPS32::Cond::NE);
4604 Sandboxer(this).sc(ValHi, AddrHi); 4609 _mov(T6, ValHi);
4605 _br(NoTarget, NoTarget, ValHi, getZero(), Retry1, CondMIPS32::Cond::EQ); 4610 Sandboxer(this).sc(T6, AddrHi);
4611 Context.insert<InstFakeUse>(ValHi);
4612 Context.insert<InstFakeUse>(ExpectedHi);
4613 _br(NoTarget, NoTarget, T6, getZero(), Retry1, CondMIPS32::Cond::EQ);
4606 Context.insert<InstFakeUse>(getZero()); 4614 Context.insert<InstFakeUse>(getZero());
4607 Context.insert(Exit); 4615 Context.insert(Exit);
4608 _mov(Dest64->getLo(), T3); 4616 _mov(Dest64->getLo(), T3);
4609 _mov(Dest64->getHi(), T4); 4617 _mov(Dest64->getHi(), T4);
4610 _sync(); 4618 _sync();
4611 } else if (DestTy == IceType_i8 || DestTy == IceType_i16) { 4619 } else if (DestTy == IceType_i8 || DestTy == IceType_i16) {
4612 auto *NewR = legalizeToReg(New); 4620 auto *NewR = legalizeToReg(New);
4613 auto *ExpectedR = legalizeToReg(Expected); 4621 auto *ExpectedR = legalizeToReg(Expected);
4614 auto *ActualAddressR = legalizeToReg(ActualAddress); 4622 auto *ActualAddressR = legalizeToReg(ActualAddress);
4615 const uint32_t ShiftAmount = 4623 const uint32_t ShiftAmount =
4616 (INT32_BITS - CHAR_BITS * typeWidthInBytes(DestTy)); 4624 (INT32_BITS - CHAR_BITS * typeWidthInBytes(DestTy));
4617 const uint32_t Mask = (1 << (CHAR_BITS * typeWidthInBytes(DestTy))) - 1; 4625 const uint32_t Mask = (1 << (CHAR_BITS * typeWidthInBytes(DestTy))) - 1;
4618 auto *RegAt = getPhysicalRegister(RegMIPS32::Reg_AT); 4626 auto *RegAt = getPhysicalRegister(RegMIPS32::Reg_AT);
4619 auto *T1 = I32Reg(); 4627 auto *T1 = I32Reg();
4620 auto *T2 = I32Reg(); 4628 auto *T2 = I32Reg();
4621 auto *T3 = I32Reg(); 4629 auto *T3 = I32Reg();
4622 auto *T4 = I32Reg(); 4630 auto *T4 = I32Reg();
4623 auto *T5 = I32Reg(); 4631 auto *T5 = I32Reg();
4624 auto *T6 = I32Reg(); 4632 auto *T6 = I32Reg();
4625 auto *T7 = I32Reg(); 4633 auto *T7 = I32Reg();
4626 auto *T8 = I32Reg(); 4634 auto *T8 = I32Reg();
4627 auto *T9 = I32Reg(); 4635 auto *T9 = I32Reg();
4628 _sync();
4629 _addiu(RegAt, getZero(), -4); 4636 _addiu(RegAt, getZero(), -4);
4630 _and(T1, ActualAddressR, RegAt); 4637 _and(T1, ActualAddressR, RegAt);
4631 _andi(RegAt, ActualAddressR, 3); 4638 _andi(RegAt, ActualAddressR, 3);
4632 _sll(T2, RegAt, 3); 4639 _sll(T2, RegAt, 3);
4633 _ori(RegAt, getZero(), Mask); 4640 _ori(RegAt, getZero(), Mask);
4634 _sllv(T3, RegAt, T2); 4641 _sllv(T3, RegAt, T2);
4635 _nor(T4, getZero(), T3); 4642 _nor(T4, getZero(), T3);
4636 _andi(RegAt, ExpectedR, Mask); 4643 _andi(RegAt, ExpectedR, Mask);
4637 _sllv(T5, RegAt, T2); 4644 _sllv(T5, RegAt, T2);
4638 _andi(RegAt, NewR, Mask); 4645 _andi(RegAt, NewR, Mask);
4639 _sllv(T6, RegAt, T2); 4646 _sllv(T6, RegAt, T2);
4647 _sync();
4640 Context.insert(Retry); 4648 Context.insert(Retry);
4641 Sandboxer(this).ll(T7, formMemoryOperand(T1, DestTy)); 4649 Sandboxer(this).ll(T7, formMemoryOperand(T1, DestTy));
4642 _and(T8, T7, T3); 4650 _and(T8, T7, T3);
4643 _br(NoTarget, NoTarget, T8, T5, Exit, CondMIPS32::Cond::NE); 4651 _br(NoTarget, NoTarget, T8, T5, Exit, CondMIPS32::Cond::NE);
4644 _and(RegAt, T7, T4); 4652 _and(RegAt, T7, T4);
4645 _or(T9, RegAt, T6); 4653 _or(T9, RegAt, T6);
4646 Sandboxer(this).sc(T9, formMemoryOperand(T1, DestTy)); 4654 Sandboxer(this).sc(T9, formMemoryOperand(T1, DestTy));
4655 Context.insert<InstFakeUse>(T6);
4647 _br(NoTarget, NoTarget, getZero(), T9, Retry, CondMIPS32::Cond::EQ); 4656 _br(NoTarget, NoTarget, getZero(), T9, Retry, CondMIPS32::Cond::EQ);
4648 Context.insert<InstFakeUse>(getZero()); 4657 Context.insert<InstFakeUse>(getZero());
4649 Context.insert(Exit); 4658 Context.insert(Exit);
4650 _srlv(RegAt, T8, T2); 4659 _srlv(RegAt, T8, T2);
4651 _sll(RegAt, RegAt, ShiftAmount); 4660 _sll(RegAt, RegAt, ShiftAmount);
4652 _sra(RegAt, RegAt, ShiftAmount); 4661 _sra(RegAt, RegAt, ShiftAmount);
4653 _mov(Dest, RegAt); 4662 _mov(Dest, RegAt);
4654 _sync(); 4663 _sync();
4655 Context.insert<InstFakeUse>(ExpectedR); 4664 Context.insert<InstFakeUse>(ExpectedR);
4656 Context.insert<InstFakeUse>(NewR); 4665 Context.insert<InstFakeUse>(NewR);
4657 } else { 4666 } else {
4658 auto *T1 = I32Reg(); 4667 auto *T1 = I32Reg();
4659 _sync(); 4668 auto *T2 = I32Reg();
4660 Context.insert(Retry);
4661 auto *NewR = legalizeToReg(New); 4669 auto *NewR = legalizeToReg(New);
4662 auto *ExpectedR = legalizeToReg(Expected); 4670 auto *ExpectedR = legalizeToReg(Expected);
4663 auto *ActualAddressR = legalizeToReg(ActualAddress); 4671 auto *ActualAddressR = legalizeToReg(ActualAddress);
4672 _sync();
4673 Context.insert(Retry);
4664 Sandboxer(this).ll(T1, formMemoryOperand(ActualAddressR, DestTy)); 4674 Sandboxer(this).ll(T1, formMemoryOperand(ActualAddressR, DestTy));
4665 _br(NoTarget, NoTarget, T1, ExpectedR, Exit, CondMIPS32::Cond::NE); 4675 _br(NoTarget, NoTarget, T1, ExpectedR, Exit, CondMIPS32::Cond::NE);
4666 Sandboxer(this).sc(NewR, formMemoryOperand(ActualAddressR, DestTy)); 4676 _mov(T2, NewR);
4667 _br(NoTarget, NoTarget, NewR, getZero(), Retry, CondMIPS32::Cond::EQ); 4677 Sandboxer(this).sc(T2, formMemoryOperand(ActualAddressR, DestTy));
4678 _br(NoTarget, NoTarget, T2, getZero(), Retry, CondMIPS32::Cond::EQ);
4668 Context.insert<InstFakeUse>(getZero()); 4679 Context.insert<InstFakeUse>(getZero());
4669 Context.insert(Exit); 4680 Context.insert(Exit);
4670 _mov(Dest, T1); 4681 _mov(Dest, T1);
4671 _sync(); 4682 _sync();
4672 Context.insert<InstFakeUse>(ExpectedR); 4683 Context.insert<InstFakeUse>(ExpectedR);
4673 Context.insert<InstFakeUse>(NewR); 4684 Context.insert<InstFakeUse>(NewR);
4674 } 4685 }
4675 return; 4686 return;
4676 } 4687 }
4677 case Intrinsics::AtomicRMW: { 4688 case Intrinsics::AtomicRMW: {
(...skipping 1505 matching lines...) Expand 10 before | Expand all | Expand 10 after
6183 auto *T6 = Target->makeReg(IceType_i32, RegMIPS32::Reg_T6); 6194 auto *T6 = Target->makeReg(IceType_i32, RegMIPS32::Reg_T6);
6184 Target->Context.insert<InstFakeDef>(T6); 6195 Target->Context.insert<InstFakeDef>(T6);
6185 Target->_and(CallTargetR, CallTargetR, T6); 6196 Target->_and(CallTargetR, CallTargetR, T6);
6186 } 6197 }
6187 } 6198 }
6188 return Target->Context.insert<InstMIPS32Call>(ReturnReg, CallTarget); 6199 return Target->Context.insert<InstMIPS32Call>(ReturnReg, CallTarget);
6189 } 6200 }
6190 6201
6191 } // end of namespace MIPS32 6202 } // end of namespace MIPS32
6192 } // end of namespace Ice 6203 } // end of namespace Ice
OLDNEW
« no previous file with comments | « no previous file | tests_lit/llvm2ice_tests/nacl-atomic-intrinsics.ll » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698