OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #if V8_TARGET_ARCH_ARM | 5 #if V8_TARGET_ARCH_ARM |
6 | 6 |
7 #include "src/code-stubs.h" | 7 #include "src/code-stubs.h" |
8 #include "src/api-arguments.h" | 8 #include "src/api-arguments.h" |
9 #include "src/base/bits.h" | 9 #include "src/base/bits.h" |
10 #include "src/bootstrapper.h" | 10 #include "src/bootstrapper.h" |
(...skipping 1151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1162 DCHECK(!AreAliased(r4, r5, LoadWithVectorDescriptor::VectorRegister(), | 1162 DCHECK(!AreAliased(r4, r5, LoadWithVectorDescriptor::VectorRegister(), |
1163 LoadWithVectorDescriptor::SlotRegister())); | 1163 LoadWithVectorDescriptor::SlotRegister())); |
1164 | 1164 |
1165 NamedLoadHandlerCompiler::GenerateLoadFunctionPrototype(masm, receiver, r4, | 1165 NamedLoadHandlerCompiler::GenerateLoadFunctionPrototype(masm, receiver, r4, |
1166 r5, &miss); | 1166 r5, &miss); |
1167 __ bind(&miss); | 1167 __ bind(&miss); |
1168 PropertyAccessCompiler::TailCallBuiltin( | 1168 PropertyAccessCompiler::TailCallBuiltin( |
1169 masm, PropertyAccessCompiler::MissBuiltin(Code::LOAD_IC)); | 1169 masm, PropertyAccessCompiler::MissBuiltin(Code::LOAD_IC)); |
1170 } | 1170 } |
1171 | 1171 |
1172 | |
1173 void LoadIndexedStringStub::Generate(MacroAssembler* masm) { | |
1174 // Return address is in lr. | |
1175 Label miss; | |
1176 | |
1177 Register receiver = LoadDescriptor::ReceiverRegister(); | |
1178 Register index = LoadDescriptor::NameRegister(); | |
1179 Register scratch = r5; | |
1180 Register result = r0; | |
1181 DCHECK(!scratch.is(receiver) && !scratch.is(index)); | |
1182 DCHECK(!scratch.is(LoadWithVectorDescriptor::VectorRegister()) && | |
1183 result.is(LoadWithVectorDescriptor::SlotRegister())); | |
1184 | |
1185 // StringCharAtGenerator doesn't use the result register until it's passed | |
1186 // the different miss possibilities. If it did, we would have a conflict | |
1187 // when FLAG_vector_ics is true. | |
1188 StringCharAtGenerator char_at_generator(receiver, index, scratch, result, | |
1189 &miss, // When not a string. | |
1190 &miss, // When not a number. | |
1191 &miss, // When index out of range. | |
1192 RECEIVER_IS_STRING); | |
1193 char_at_generator.GenerateFast(masm); | |
1194 __ Ret(); | |
1195 | |
1196 StubRuntimeCallHelper call_helper; | |
1197 char_at_generator.GenerateSlow(masm, PART_OF_IC_HANDLER, call_helper); | |
1198 | |
1199 __ bind(&miss); | |
1200 PropertyAccessCompiler::TailCallBuiltin( | |
1201 masm, PropertyAccessCompiler::MissBuiltin(Code::KEYED_LOAD_IC)); | |
1202 } | |
1203 | |
1204 | |
1205 void RegExpExecStub::Generate(MacroAssembler* masm) { | 1172 void RegExpExecStub::Generate(MacroAssembler* masm) { |
1206 // Just jump directly to runtime if native RegExp is not selected at compile | 1173 // Just jump directly to runtime if native RegExp is not selected at compile |
1207 // time or if regexp entry in generated code is turned off runtime switch or | 1174 // time or if regexp entry in generated code is turned off runtime switch or |
1208 // at compilation. | 1175 // at compilation. |
1209 #ifdef V8_INTERPRETED_REGEXP | 1176 #ifdef V8_INTERPRETED_REGEXP |
1210 __ TailCallRuntime(Runtime::kRegExpExec); | 1177 __ TailCallRuntime(Runtime::kRegExpExec); |
1211 #else // V8_INTERPRETED_REGEXP | 1178 #else // V8_INTERPRETED_REGEXP |
1212 | 1179 |
1213 // Stack frame on entry. | 1180 // Stack frame on entry. |
1214 // sp[0]: last_match_info (expected JSArray) | 1181 // sp[0]: last_match_info (expected JSArray) |
(...skipping 627 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1842 __ SmiTag(index_); | 1809 __ SmiTag(index_); |
1843 __ Push(object_, index_); | 1810 __ Push(object_, index_); |
1844 __ CallRuntime(Runtime::kStringCharCodeAtRT); | 1811 __ CallRuntime(Runtime::kStringCharCodeAtRT); |
1845 __ Move(result_, r0); | 1812 __ Move(result_, r0); |
1846 call_helper.AfterCall(masm); | 1813 call_helper.AfterCall(masm); |
1847 __ jmp(&exit_); | 1814 __ jmp(&exit_); |
1848 | 1815 |
1849 __ Abort(kUnexpectedFallthroughFromCharCodeAtSlowCase); | 1816 __ Abort(kUnexpectedFallthroughFromCharCodeAtSlowCase); |
1850 } | 1817 } |
1851 | 1818 |
1852 | |
1853 // ------------------------------------------------------------------------- | |
1854 // StringCharFromCodeGenerator | |
1855 | |
1856 void StringCharFromCodeGenerator::GenerateFast(MacroAssembler* masm) { | |
1857 // Fast case of Heap::LookupSingleCharacterStringFromCode. | |
1858 STATIC_ASSERT(kSmiTag == 0); | |
1859 STATIC_ASSERT(kSmiShiftSize == 0); | |
1860 DCHECK(base::bits::IsPowerOfTwo32(String::kMaxOneByteCharCodeU + 1)); | |
1861 __ tst(code_, Operand(kSmiTagMask | | |
1862 ((~String::kMaxOneByteCharCodeU) << kSmiTagSize))); | |
1863 __ b(ne, &slow_case_); | |
1864 | |
1865 __ LoadRoot(result_, Heap::kSingleCharacterStringCacheRootIndex); | |
1866 // At this point code register contains smi tagged one-byte char code. | |
1867 __ add(result_, result_, Operand::PointerOffsetFromSmiKey(code_)); | |
1868 __ ldr(result_, FieldMemOperand(result_, FixedArray::kHeaderSize)); | |
1869 __ CompareRoot(result_, Heap::kUndefinedValueRootIndex); | |
1870 __ b(eq, &slow_case_); | |
1871 __ bind(&exit_); | |
1872 } | |
1873 | |
1874 | |
1875 void StringCharFromCodeGenerator::GenerateSlow( | |
1876 MacroAssembler* masm, | |
1877 const RuntimeCallHelper& call_helper) { | |
1878 __ Abort(kUnexpectedFallthroughToCharFromCodeSlowCase); | |
1879 | |
1880 __ bind(&slow_case_); | |
1881 call_helper.BeforeCall(masm); | |
1882 __ push(code_); | |
1883 __ CallRuntime(Runtime::kStringCharFromCode); | |
1884 __ Move(result_, r0); | |
1885 call_helper.AfterCall(masm); | |
1886 __ jmp(&exit_); | |
1887 | |
1888 __ Abort(kUnexpectedFallthroughFromCharFromCodeSlowCase); | |
1889 } | |
1890 | |
1891 void StringHelper::GenerateFlatOneByteStringEquals( | 1819 void StringHelper::GenerateFlatOneByteStringEquals( |
1892 MacroAssembler* masm, Register left, Register right, Register scratch1, | 1820 MacroAssembler* masm, Register left, Register right, Register scratch1, |
1893 Register scratch2, Register scratch3) { | 1821 Register scratch2, Register scratch3) { |
1894 Register length = scratch1; | 1822 Register length = scratch1; |
1895 | 1823 |
1896 // Compare lengths. | 1824 // Compare lengths. |
1897 Label strings_not_equal, check_zero_length; | 1825 Label strings_not_equal, check_zero_length; |
1898 __ ldr(length, FieldMemOperand(left, String::kLengthOffset)); | 1826 __ ldr(length, FieldMemOperand(left, String::kLengthOffset)); |
1899 __ ldr(scratch2, FieldMemOperand(right, String::kLengthOffset)); | 1827 __ ldr(scratch2, FieldMemOperand(right, String::kLengthOffset)); |
1900 __ cmp(length, scratch2); | 1828 __ cmp(length, scratch2); |
(...skipping 1511 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3412 CallApiFunctionAndReturn(masm, api_function_address, thunk_ref, | 3340 CallApiFunctionAndReturn(masm, api_function_address, thunk_ref, |
3413 kStackUnwindSpace, NULL, return_value_operand, NULL); | 3341 kStackUnwindSpace, NULL, return_value_operand, NULL); |
3414 } | 3342 } |
3415 | 3343 |
3416 #undef __ | 3344 #undef __ |
3417 | 3345 |
3418 } // namespace internal | 3346 } // namespace internal |
3419 } // namespace v8 | 3347 } // namespace v8 |
3420 | 3348 |
3421 #endif // V8_TARGET_ARCH_ARM | 3349 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |