Changeset 194011 in webkit
- Timestamp:
- Dec 12, 2015 3:04:54 PM (8 years ago)
- Location:
- trunk/Source/JavaScriptCore
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/JavaScriptCore/ChangeLog
r194007 r194011 1 2015-12-12 Benjamin Poulain <benjamin@webkit.org> 2 3 [JSC] Add lowering for B3's Store8 opcode 4 https://bugs.webkit.org/show_bug.cgi?id=152208 5 6 Reviewed by Geoffrey Garen. 7 8 B3 has an opcode to store 8bit values but it had 9 no lowering. 10 11 * b3/B3LowerToAir.cpp: 12 (JSC::B3::Air::LowerToAir::createStore): 13 (JSC::B3::Air::LowerToAir::lower): 14 * b3/air/AirOpcode.opcodes: 15 * b3/testb3.cpp: 16 (JSC::B3::testStore8Arg): 17 (JSC::B3::testStore8Imm): 18 (JSC::B3::testStorePartial8BitRegisterOnX86): 19 (JSC::B3::run): 20 1 21 2015-12-12 Csaba Osztrogonác <ossy@webkit.org> 2 22 -
trunk/Source/JavaScriptCore/b3/B3LowerToAir.cpp
r194003 r194011 747 747 } 748 748 749 Inst createStore(Value* value, const Arg& dest) 750 { 751 Air::Opcode move = moveForType(value->type()); 752 749 Inst createStore(Air::Opcode move, Value* value, const Arg& dest) 750 { 753 751 if (imm(value) && isValidForm(move, Arg::Imm, dest.kind())) 754 752 return Inst(move, m_value, imm(value), dest); 755 753 756 754 return Inst(move, m_value, tmp(value), dest); 755 } 756 757 Inst createStore(Value* value, const Arg& dest) 758 { 759 Air::Opcode moveOpcode = moveForType(value->type()); 760 return createStore(moveOpcode, value, dest); 757 761 } 758 762 … … 1558 1562 } 1559 1563 1564 case B3::Store8: { 1565 Value* valueToStore = m_value->child(0); 1566 m_insts.last().append(createStore(Air::Store8, valueToStore, addr(m_value))); 1567 return; 1568 } 1569 1560 1570 case Trunc: { 1561 1571 ASSERT(tmp(m_value->child(0)) == tmp(m_value)); -
trunk/Source/JavaScriptCore/b3/air/AirOpcode.opcodes
r194003 r194011 326 326 Index, Tmp 327 327 328 Store8 U:G, D:G 329 Tmp, Index 330 Tmp, Addr 331 Imm, Index 332 Imm, Addr 333 328 334 Load8SignedExtendTo32 U:G, D:G 329 335 Addr, Tmp -
trunk/Source/JavaScriptCore/b3/testb3.cpp
r194003 r194011 3703 3703 CHECK(!compileAndRun<int>(proc)); 3704 3704 CHECK(slot == value); 3705 } 3706 3707 void testStore8Arg() 3708 { 3709 { // Direct addressing. 3710 Procedure proc; 3711 BasicBlock* root = proc.addBlock(); 3712 3713 Value* value = root->appendNew<Value>(proc, Trunc, Origin(), 3714 root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR0)); 3715 Value* address = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR1); 3716 3717 root->appendNew<MemoryValue>(proc, Store8, Origin(), value, address); 3718 root->appendNew<ControlValue>(proc, Return, Origin(), value); 3719 3720 int8_t storage = 0; 3721 CHECK(compileAndRun<int64_t>(proc, 42, &storage) == 42); 3722 CHECK(storage == 42); 3723 } 3724 3725 { // Indexed addressing. 3726 Procedure proc; 3727 BasicBlock* root = proc.addBlock(); 3728 3729 Value* value = root->appendNew<Value>(proc, Trunc, Origin(), 3730 root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR0)); 3731 Value* base = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR1); 3732 Value* offset = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR2); 3733 Value* displacement = root->appendNew<Const64Value>(proc, Origin(), -1); 3734 3735 Value* baseDisplacement = root->appendNew<Value>(proc, Add, Origin(), displacement, base); 3736 Value* address = root->appendNew<Value>(proc, Add, Origin(), baseDisplacement, offset); 3737 3738 root->appendNew<MemoryValue>(proc, Store8, Origin(), value, address); 3739 root->appendNew<ControlValue>(proc, Return, Origin(), value); 3740 3741 int8_t storage = 0; 3742 CHECK(compileAndRun<int64_t>(proc, 42, &storage, 1) == 42); 3743 CHECK(storage == 42); 3744 } 3745 } 3746 3747 void testStore8Imm() 3748 { 3749 { // Direct addressing. 3750 Procedure proc; 3751 BasicBlock* root = proc.addBlock(); 3752 3753 Value* value = root->appendNew<Const32Value>(proc, Origin(), 42); 3754 Value* address = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR0); 3755 3756 root->appendNew<MemoryValue>(proc, Store8, Origin(), value, address); 3757 root->appendNew<ControlValue>(proc, Return, Origin(), value); 3758 3759 int8_t storage = 0; 3760 CHECK(compileAndRun<int64_t>(proc, &storage) == 42); 3761 CHECK(storage == 42); 3762 } 3763 3764 { // Indexed addressing. 3765 Procedure proc; 3766 BasicBlock* root = proc.addBlock(); 3767 3768 Value* value = root->appendNew<Const32Value>(proc, Origin(), 42); 3769 Value* base = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR0); 3770 Value* offset = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR1); 3771 Value* displacement = root->appendNew<Const64Value>(proc, Origin(), -1); 3772 3773 Value* baseDisplacement = root->appendNew<Value>(proc, Add, Origin(), displacement, base); 3774 Value* address = root->appendNew<Value>(proc, Add, Origin(), baseDisplacement, offset); 3775 3776 root->appendNew<MemoryValue>(proc, Store8, Origin(), value, address); 3777 root->appendNew<ControlValue>(proc, Return, Origin(), value); 3778 3779 int8_t storage = 0; 3780 CHECK(compileAndRun<int64_t>(proc, &storage, 1) == 42); 3781 CHECK(storage == 42); 3782 } 3783 } 3784 3785 void testStorePartial8BitRegisterOnX86() 3786 { 3787 Procedure proc; 3788 BasicBlock* root = proc.addBlock(); 3789 3790 // We want to have this in ECX. 3791 Value* returnValue = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR0); 3792 3793 // We want this suck in EDX. 3794 Value* whereToStore = root->appendNew<ArgumentRegValue>(proc, Origin(), GPRInfo::argumentGPR1); 3795 3796 // The patch point is there to help us force the hand of the compiler. 3797 PatchpointValue* patchpoint = root->appendNew<PatchpointValue>(proc, Int32, Origin()); 3798 3799 // For the value above to be materialized and give the allocator 3800 // a stronger insentive to name those register the way we need. 3801 patchpoint->append(ConstrainedValue(returnValue, ValueRep(GPRInfo::regT3))); 3802 patchpoint->append(ConstrainedValue(whereToStore, ValueRep(GPRInfo::regT2))); 3803 3804 // We'll produce EDI. 3805 patchpoint->resultConstraint = ValueRep::reg(GPRInfo::regT6); 3806 3807 // Give the allocator a good reason not to use any other register. 3808 RegisterSet clobberSet = RegisterSet::allGPRs(); 3809 clobberSet.exclude(RegisterSet::stackRegisters()); 3810 clobberSet.exclude(RegisterSet::reservedHardwareRegisters()); 3811 clobberSet.clear(GPRInfo::regT3); 3812 clobberSet.clear(GPRInfo::regT2); 3813 clobberSet.clear(GPRInfo::regT6); 3814 patchpoint->clobberLate(clobberSet); 3815 3816 // Set EDI. 3817 patchpoint->setGenerator( 3818 [&] (CCallHelpers& jit, const StackmapGenerationParams& params) { 3819 AllowMacroScratchRegisterUsage allowScratch(jit); 3820 jit.xor64(params[0].gpr(), params[0].gpr()); 3821 }); 3822 3823 // If everything went well, we should have the big number in eax, 3824 // patchpoint == EDI and whereToStore = EDX. 3825 // Since EDI == 5, and AH = 5 on 8 bit store, this would go wrong 3826 // if we use X86 partial registers. 3827 root->appendNew<MemoryValue>(proc, Store8, Origin(), patchpoint, whereToStore); 3828 3829 root->appendNew<ControlValue>(proc, Return, Origin(), returnValue); 3830 3831 int8_t storage = 0xff; 3832 CHECK(compileAndRun<int64_t>(proc, 0x12345678abcdef12, &storage) == 0x12345678abcdef12); 3833 CHECK(!storage); 3705 3834 } 3706 3835 … … 8140 8269 RUN(testStoreConstant(49)); 8141 8270 RUN(testStoreConstantPtr(49)); 8271 RUN(testStore8Arg()); 8272 RUN(testStore8Imm()); 8273 RUN(testStorePartial8BitRegisterOnX86()); 8142 8274 RUN(testTrunc((static_cast<int64_t>(1) << 40) + 42)); 8143 8275 RUN(testAdd1(45));
Note: See TracChangeset
for help on using the changeset viewer.