diff options
author | Steve Block <steveblock@google.com> | 2009-12-15 10:12:09 +0000 |
---|---|---|
committer | Steve Block <steveblock@google.com> | 2009-12-17 17:41:10 +0000 |
commit | 643ca7872b450ea4efacab6188849e5aac2ba161 (patch) | |
tree | 6982576c228bcd1a7efe98afed544d840751094c /JavaScriptCore/jit/JITOpcodes.cpp | |
parent | d026980fde6eb3b01c1fe49441174e89cd1be298 (diff) | |
download | external_webkit-643ca7872b450ea4efacab6188849e5aac2ba161.zip external_webkit-643ca7872b450ea4efacab6188849e5aac2ba161.tar.gz external_webkit-643ca7872b450ea4efacab6188849e5aac2ba161.tar.bz2 |
Merge webkit.org at r51976 : Initial merge by git.
Change-Id: Ib0e7e2f0fb4bee5a186610272edf3186f0986b43
Diffstat (limited to 'JavaScriptCore/jit/JITOpcodes.cpp')
-rw-r--r-- | JavaScriptCore/jit/JITOpcodes.cpp | 155 |
1 files changed, 143 insertions, 12 deletions
diff --git a/JavaScriptCore/jit/JITOpcodes.cpp b/JavaScriptCore/jit/JITOpcodes.cpp index 14736cf..77fec28 100644 --- a/JavaScriptCore/jit/JITOpcodes.cpp +++ b/JavaScriptCore/jit/JITOpcodes.cpp @@ -52,8 +52,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable Jump string_failureCases2 = branchPtr(NotEqual, Address(regT0), ImmPtr(m_globalData->jsStringVPtr)); // Checks out okay! - get the length from the Ustring. - loadPtr(Address(regT0, OBJECT_OFFSETOF(JSString, m_value) + OBJECT_OFFSETOF(UString, m_rep)), regT2); - load32(Address(regT2, OBJECT_OFFSETOF(UString::Rep, len)), regT2); + load32(Address(regT0, OBJECT_OFFSETOF(JSString, m_stringLength)), regT2); Jump string_failureCases3 = branch32(Above, regT2, Imm32(INT_MAX)); move(regT2, regT0); @@ -138,7 +137,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable loadPtr(Address(regT2, OBJECT_OFFSETOF(FunctionExecutable, m_jitCode)), regT0); jump(regT0); -#if PLATFORM(X86) +#if PLATFORM(X86) || PLATFORM(ARM_TRADITIONAL) Label nativeCallThunk = align(); preserveReturnAddressAfterCall(regT0); emitPutToCallFrameHeader(regT0, RegisterFile::ReturnPC); // Push return address @@ -149,6 +148,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable emitGetFromCallFrameHeaderPtr(RegisterFile::ScopeChain, regT1, regT1); emitPutToCallFrameHeader(regT1, RegisterFile::ScopeChain); +#if PLATFORM(X86) emitGetFromCallFrameHeader32(RegisterFile::ArgumentCount, regT0); /* We have two structs that we use to describe the stackframe we set up for our @@ -248,6 +248,66 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable // so pull them off now addPtr(Imm32(NativeCallFrameSize - sizeof(NativeFunctionCalleeSignature)), stackPointerRegister); +#elif PLATFORM(ARM_TRADITIONAL) + emitGetFromCallFrameHeader32(RegisterFile::ArgumentCount, regT0); + + // Allocate stack space for our arglist + COMPILE_ASSERT((sizeof(ArgList) & 0x7) == 0 && sizeof(JSValue) == 8 && sizeof(Register) == 8, ArgList_should_by_8byte_aligned); + subPtr(Imm32(sizeof(ArgList)), stackPointerRegister); + + // Set up arguments + subPtr(Imm32(1), regT0); // Don't include 'this' in argcount + + // Push argcount + storePtr(regT0, Address(stackPointerRegister, OBJECT_OFFSETOF(ArgList, m_argCount))); + + // Calculate the start of the callframe header, and store in regT1 + move(callFrameRegister, regT1); + sub32(Imm32(RegisterFile::CallFrameHeaderSize * (int32_t)sizeof(Register)), regT1); + + // Calculate start of arguments as callframe header - sizeof(Register) * argcount (regT1) + mul32(Imm32(sizeof(Register)), regT0, regT0); + subPtr(regT0, regT1); + + // push pointer to arguments + storePtr(regT1, Address(stackPointerRegister, OBJECT_OFFSETOF(ArgList, m_args))); + + // Argument passing method: + // r0 - points to return value + // r1 - callFrame + // r2 - callee + // stack: this(JSValue) and a pointer to ArgList + + move(stackPointerRegister, regT3); + subPtr(Imm32(8), stackPointerRegister); + move(stackPointerRegister, regT0); + subPtr(Imm32(8 + 4 + 4 /* padding */), stackPointerRegister); + + // Setup arg4: + storePtr(regT3, Address(stackPointerRegister, 8)); + + // Setup arg3 + // regT1 currently points to the first argument, regT1-sizeof(Register) points to 'this' + load32(Address(regT1, -(int32_t)sizeof(void*) * 2), regT3); + storePtr(regT3, Address(stackPointerRegister, 0)); + load32(Address(regT1, -(int32_t)sizeof(void*)), regT3); + storePtr(regT3, Address(stackPointerRegister, 4)); + + // Setup arg2: + emitGetFromCallFrameHeaderPtr(RegisterFile::Callee, regT2); + + // Setup arg1: + move(callFrameRegister, regT1); + + call(Address(regT2, OBJECT_OFFSETOF(JSFunction, m_data))); + + // Load return value + load32(Address(stackPointerRegister, 16), regT0); + load32(Address(stackPointerRegister, 20), regT1); + + addPtr(Imm32(sizeof(ArgList) + 16 + 8), stackPointerRegister); +#endif + // Check for an exception move(ImmPtr(&globalData->exception), regT2); Jump sawException = branch32(NotEqual, tagFor(0, regT2), Imm32(JSValue::EmptyValueTag)); @@ -394,7 +454,7 @@ void JIT::emitSlow_op_loop_if_less(Instruction* currentInstruction, Vector<SlowC linkSlowCase(iter); // int32 check linkSlowCase(iter); // int32 check - JITStubCall stubCall(this, cti_op_loop_if_less); + JITStubCall stubCall(this, cti_op_jless); stubCall.addArgument(op1); stubCall.addArgument(op2); stubCall.call(); @@ -683,6 +743,50 @@ void JIT::emitSlow_op_loop_if_true(Instruction* currentInstruction, Vector<SlowC emitJumpSlowToHot(branchTest32(NonZero, regT0), target); } +void JIT::emit_op_loop_if_false(Instruction* currentInstruction) +{ + unsigned cond = currentInstruction[1].u.operand; + unsigned target = currentInstruction[2].u.operand; + + emitTimeoutCheck(); + + emitLoad(cond, regT1, regT0); + + Jump isTrue = branch32(Equal, regT1, Imm32(JSValue::TrueTag)); + addJump(branch32(Equal, regT1, Imm32(JSValue::FalseTag)), target); + + Jump isNotInteger = branch32(NotEqual, regT1, Imm32(JSValue::Int32Tag)); + Jump isTrue2 = branch32(NotEqual, regT0, Imm32(0)); + addJump(jump(), target); + + if (supportsFloatingPoint()) { + isNotInteger.link(this); + + addSlowCase(branch32(Above, regT1, Imm32(JSValue::LowestTag))); + + zeroDouble(fpRegT0); + emitLoadDouble(cond, fpRegT1); + addJump(branchDouble(DoubleEqualOrUnordered, fpRegT0, fpRegT1), target); + } else + addSlowCase(isNotInteger); + + isTrue.link(this); + isTrue2.link(this); +} + +void JIT::emitSlow_op_loop_if_false(Instruction* currentInstruction, Vector<SlowCaseEntry>::iterator& iter) +{ + unsigned cond = currentInstruction[1].u.operand; + unsigned target = currentInstruction[2].u.operand; + + linkSlowCase(iter); + + JITStubCall stubCall(this, cti_op_jtrue); + stubCall.addArgument(cond); + stubCall.call(); + emitJumpSlowToHot(branchTest32(Zero, regT0), target); +} + void JIT::emit_op_resolve_base(Instruction* currentInstruction) { JITStubCall stubCall(this, cti_op_resolve_base); @@ -786,7 +890,7 @@ void JIT::emit_op_jfalse(Instruction* currentInstruction) zeroDouble(fpRegT0); emitLoadDouble(cond, fpRegT1); - addJump(branchDouble(DoubleEqual, fpRegT0, fpRegT1), target); + addJump(branchDouble(DoubleEqualOrUnordered, fpRegT0, fpRegT1), target); } else addSlowCase(isNotInteger); @@ -1532,8 +1636,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable Jump string_failureCases2 = branchPtr(NotEqual, Address(regT0), ImmPtr(m_globalData->jsStringVPtr)); // Checks out okay! - get the length from the Ustring. - loadPtr(Address(regT0, OBJECT_OFFSETOF(JSString, m_value) + OBJECT_OFFSETOF(UString, m_rep)), regT0); - load32(Address(regT0, OBJECT_OFFSETOF(UString::Rep, len)), regT0); + load32(Address(regT0, OBJECT_OFFSETOF(JSString, m_stringLength)), regT0); Jump string_failureCases3 = branch32(Above, regT0, Imm32(JSImmediate::maxImmediateInt)); @@ -1756,7 +1859,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable // so pull them off now addPtr(Imm32(NativeCallFrameSize - sizeof(NativeFunctionCalleeSignature)), stackPointerRegister); -#elif PLATFORM(ARM_TRADITIONAL) +#elif PLATFORM(ARM) emitGetFromCallFrameHeader32(RegisterFile::ArgumentCount, regT0); // Allocate stack space for our arglist @@ -1790,7 +1893,7 @@ void JIT::privateCompileCTIMachineTrampolines(RefPtr<ExecutablePool>* executable move(callFrameRegister, regT0); // Setup arg4: This is a plain hack - move(stackPointerRegister, ARMRegisters::S0); + move(stackPointerRegister, ARMRegisters::r3); call(Address(regT1, OBJECT_OFFSETOF(JSFunction, m_data))); @@ -2196,6 +2299,25 @@ void JIT::emit_op_loop_if_true(Instruction* currentInstruction) isZero.link(this); }; + +void JIT::emit_op_loop_if_false(Instruction* currentInstruction) +{ + emitTimeoutCheck(); + + + unsigned target = currentInstruction[2].u.operand; + emitGetVirtualRegister(currentInstruction[1].u.operand, regT0); + + addJump(branchPtr(Equal, regT0, ImmPtr(JSValue::encode(jsNumber(m_globalData, 0)))), target); + Jump isNonZero = emitJumpIfImmediateInteger(regT0); + + addJump(branchPtr(Equal, regT0, ImmPtr(JSValue::encode(jsBoolean(false)))), target); + addSlowCase(branchPtr(NotEqual, regT0, ImmPtr(JSValue::encode(jsBoolean(true))))); + + isNonZero.link(this); + RECORD_JUMP_TARGET(target); +}; + void JIT::emit_op_resolve_base(Instruction* currentInstruction) { JITStubCall stubCall(this, cti_op_resolve_base); @@ -2882,14 +3004,14 @@ void JIT::emitSlow_op_loop_if_less(Instruction* currentInstruction, Vector<SlowC unsigned target = currentInstruction[3].u.operand; if (isOperandConstantImmediateInt(op2)) { linkSlowCase(iter); - JITStubCall stubCall(this, cti_op_loop_if_less); + JITStubCall stubCall(this, cti_op_jless); stubCall.addArgument(regT0); stubCall.addArgument(op2, regT2); stubCall.call(); emitJumpSlowToHot(branchTest32(NonZero, regT0), target); } else if (isOperandConstantImmediateInt(op1)) { linkSlowCase(iter); - JITStubCall stubCall(this, cti_op_loop_if_less); + JITStubCall stubCall(this, cti_op_jless); stubCall.addArgument(op1, regT2); stubCall.addArgument(regT0); stubCall.call(); @@ -2897,7 +3019,7 @@ void JIT::emitSlow_op_loop_if_less(Instruction* currentInstruction, Vector<SlowC } else { linkSlowCase(iter); linkSlowCase(iter); - JITStubCall stubCall(this, cti_op_loop_if_less); + JITStubCall stubCall(this, cti_op_jless); stubCall.addArgument(regT0); stubCall.addArgument(regT1); stubCall.call(); @@ -2954,6 +3076,15 @@ void JIT::emitSlow_op_loop_if_true(Instruction* currentInstruction, Vector<SlowC emitJumpSlowToHot(branchTest32(NonZero, regT0), currentInstruction[2].u.operand); } +void JIT::emitSlow_op_loop_if_false(Instruction* currentInstruction, Vector<SlowCaseEntry>::iterator& iter) +{ + linkSlowCase(iter); + JITStubCall stubCall(this, cti_op_jtrue); + stubCall.addArgument(regT0); + stubCall.call(); + emitJumpSlowToHot(branchTest32(Zero, regT0), currentInstruction[2].u.operand); // inverted! +} + void JIT::emitSlow_op_not(Instruction* currentInstruction, Vector<SlowCaseEntry>::iterator& iter) { linkSlowCase(iter); |