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

Side by Side Diff: src/arm/code-stubs-arm.cc

Issue 14813029: Error found in test262 on ARM: BinaryOpStub could call out to a built-in and push … (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Code review comments Created 7 years, 7 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 | Annotate | Revision Log
« no previous file with comments | « src/arm/code-stubs-arm.h ('k') | src/arm/simulator-arm.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 2144 matching lines...) Expand 10 before | Expand all | Expand 10 after
2155 BinaryOpStub_GenerateSmiCode( 2155 BinaryOpStub_GenerateSmiCode(
2156 masm, &call_runtime, &call_runtime, op_, ALLOW_HEAPNUMBER_RESULTS, 2156 masm, &call_runtime, &call_runtime, op_, ALLOW_HEAPNUMBER_RESULTS,
2157 mode_); 2157 mode_);
2158 } 2158 }
2159 2159
2160 // Code falls through if the result is not returned as either a smi or heap 2160 // Code falls through if the result is not returned as either a smi or heap
2161 // number. 2161 // number.
2162 GenerateTypeTransition(masm); 2162 GenerateTypeTransition(masm);
2163 2163
2164 __ bind(&call_runtime); 2164 __ bind(&call_runtime);
2165 GenerateRegisterArgsPush(masm); 2165 {
2166 GenerateCallRuntime(masm); 2166 FrameScope scope(masm, StackFrame::INTERNAL);
2167 GenerateRegisterArgsPush(masm);
2168 GenerateCallRuntime(masm);
2169 }
2170 __ Ret();
2167 } 2171 }
2168 2172
2169 2173
2170 void BinaryOpStub::GenerateBothStringStub(MacroAssembler* masm) { 2174 void BinaryOpStub::GenerateBothStringStub(MacroAssembler* masm) {
2171 Label call_runtime; 2175 Label call_runtime;
2172 ASSERT(left_type_ == BinaryOpIC::STRING && right_type_ == BinaryOpIC::STRING); 2176 ASSERT(left_type_ == BinaryOpIC::STRING && right_type_ == BinaryOpIC::STRING);
2173 ASSERT(op_ == Token::ADD); 2177 ASSERT(op_ == Token::ADD);
2174 // If both arguments are strings, call the string add stub. 2178 // If both arguments are strings, call the string add stub.
2175 // Otherwise, do a transition. 2179 // Otherwise, do a transition.
2176 2180
2177 // Registers containing left and right operands respectively. 2181 // Registers containing left and right operands respectively.
2178 Register left = r1; 2182 Register left = r1;
2179 Register right = r0; 2183 Register right = r0;
2180 2184
2181 // Test if left operand is a string. 2185 // Test if left operand is a string.
2182 __ JumpIfSmi(left, &call_runtime); 2186 __ JumpIfSmi(left, &call_runtime);
2183 __ CompareObjectType(left, r2, r2, FIRST_NONSTRING_TYPE); 2187 __ CompareObjectType(left, r2, r2, FIRST_NONSTRING_TYPE);
2184 __ b(ge, &call_runtime); 2188 __ b(ge, &call_runtime);
2185 2189
2186 // Test if right operand is a string. 2190 // Test if right operand is a string.
2187 __ JumpIfSmi(right, &call_runtime); 2191 __ JumpIfSmi(right, &call_runtime);
2188 __ CompareObjectType(right, r2, r2, FIRST_NONSTRING_TYPE); 2192 __ CompareObjectType(right, r2, r2, FIRST_NONSTRING_TYPE);
2189 __ b(ge, &call_runtime); 2193 __ b(ge, &call_runtime);
2190 2194
2191 StringAddStub string_add_stub(NO_STRING_CHECK_IN_STUB); 2195 StringAddStub string_add_stub((StringAddFlags)
2196 (ERECT_FRAME | NO_STRING_CHECK_IN_STUB));
2192 GenerateRegisterArgsPush(masm); 2197 GenerateRegisterArgsPush(masm);
2193 __ TailCallStub(&string_add_stub); 2198 __ TailCallStub(&string_add_stub);
2194 2199
2195 __ bind(&call_runtime); 2200 __ bind(&call_runtime);
2196 GenerateTypeTransition(masm); 2201 GenerateTypeTransition(masm);
2197 } 2202 }
2198 2203
2199 2204
2200 void BinaryOpStub::GenerateInt32Stub(MacroAssembler* masm) { 2205 void BinaryOpStub::GenerateInt32Stub(MacroAssembler* masm) {
2201 ASSERT(Max(left_type_, right_type_) == BinaryOpIC::INT32); 2206 ASSERT(Max(left_type_, right_type_) == BinaryOpIC::INT32);
(...skipping 250 matching lines...) Expand 10 before | Expand all | Expand 10 after
2452 // We never expect DIV to yield an integer result, so we always generate 2457 // We never expect DIV to yield an integer result, so we always generate
2453 // type transition code for DIV operations expecting an integer result: the 2458 // type transition code for DIV operations expecting an integer result: the
2454 // code will fall through to this type transition. 2459 // code will fall through to this type transition.
2455 if (transition.is_linked() || 2460 if (transition.is_linked() ||
2456 ((op_ == Token::DIV) && (result_type_ <= BinaryOpIC::INT32))) { 2461 ((op_ == Token::DIV) && (result_type_ <= BinaryOpIC::INT32))) {
2457 __ bind(&transition); 2462 __ bind(&transition);
2458 GenerateTypeTransition(masm); 2463 GenerateTypeTransition(masm);
2459 } 2464 }
2460 2465
2461 __ bind(&call_runtime); 2466 __ bind(&call_runtime);
2462 GenerateRegisterArgsPush(masm); 2467 {
2463 GenerateCallRuntime(masm); 2468 FrameScope scope(masm, StackFrame::INTERNAL);
2469 GenerateRegisterArgsPush(masm);
2470 GenerateCallRuntime(masm);
2471 }
2472 __ Ret();
2464 } 2473 }
2465 2474
2466 2475
2467 void BinaryOpStub::GenerateOddballStub(MacroAssembler* masm) { 2476 void BinaryOpStub::GenerateOddballStub(MacroAssembler* masm) {
2468 Label call_runtime; 2477 Label call_runtime;
2469 2478
2470 if (op_ == Token::ADD) { 2479 if (op_ == Token::ADD) {
2471 // Handle string addition here, because it is the only operation 2480 // Handle string addition here, because it is the only operation
2472 // that does not do a ToNumber conversion on the operands. 2481 // that does not do a ToNumber conversion on the operands.
2473 GenerateAddStrings(masm); 2482 GenerateAddStrings(masm);
(...skipping 26 matching lines...) Expand all
2500 void BinaryOpStub::GenerateNumberStub(MacroAssembler* masm) { 2509 void BinaryOpStub::GenerateNumberStub(MacroAssembler* masm) {
2501 Label call_runtime, transition; 2510 Label call_runtime, transition;
2502 BinaryOpStub_GenerateFPOperation( 2511 BinaryOpStub_GenerateFPOperation(
2503 masm, left_type_, right_type_, false, 2512 masm, left_type_, right_type_, false,
2504 &transition, &call_runtime, &transition, op_, mode_); 2513 &transition, &call_runtime, &transition, op_, mode_);
2505 2514
2506 __ bind(&transition); 2515 __ bind(&transition);
2507 GenerateTypeTransition(masm); 2516 GenerateTypeTransition(masm);
2508 2517
2509 __ bind(&call_runtime); 2518 __ bind(&call_runtime);
2510 GenerateRegisterArgsPush(masm); 2519 {
2511 GenerateCallRuntime(masm); 2520 FrameScope scope(masm, StackFrame::INTERNAL);
2521 GenerateRegisterArgsPush(masm);
2522 GenerateCallRuntime(masm);
2523 }
2524 __ Ret();
2512 } 2525 }
2513 2526
2514 2527
2515 void BinaryOpStub::GenerateGeneric(MacroAssembler* masm) { 2528 void BinaryOpStub::GenerateGeneric(MacroAssembler* masm) {
2516 Label call_runtime, call_string_add_or_runtime, transition; 2529 Label call_runtime, call_string_add_or_runtime, transition;
2517 2530
2518 BinaryOpStub_GenerateSmiCode( 2531 BinaryOpStub_GenerateSmiCode(
2519 masm, &call_runtime, &call_runtime, op_, ALLOW_HEAPNUMBER_RESULTS, mode_); 2532 masm, &call_runtime, &call_runtime, op_, ALLOW_HEAPNUMBER_RESULTS, mode_);
2520 2533
2521 BinaryOpStub_GenerateFPOperation( 2534 BinaryOpStub_GenerateFPOperation(
2522 masm, left_type_, right_type_, false, 2535 masm, left_type_, right_type_, false,
2523 &call_string_add_or_runtime, &call_runtime, &transition, op_, mode_); 2536 &call_string_add_or_runtime, &call_runtime, &transition, op_, mode_);
2524 2537
2525 __ bind(&transition); 2538 __ bind(&transition);
2526 GenerateTypeTransition(masm); 2539 GenerateTypeTransition(masm);
2527 2540
2528 __ bind(&call_string_add_or_runtime); 2541 __ bind(&call_string_add_or_runtime);
2529 if (op_ == Token::ADD) { 2542 if (op_ == Token::ADD) {
2530 GenerateAddStrings(masm); 2543 GenerateAddStrings(masm);
2531 } 2544 }
2532 2545
2533 __ bind(&call_runtime); 2546 __ bind(&call_runtime);
2534 GenerateRegisterArgsPush(masm); 2547 {
2535 GenerateCallRuntime(masm); 2548 FrameScope scope(masm, StackFrame::INTERNAL);
2549 GenerateRegisterArgsPush(masm);
2550 GenerateCallRuntime(masm);
2551 }
2552 __ Ret();
2536 } 2553 }
2537 2554
2538 2555
2539 void BinaryOpStub::GenerateAddStrings(MacroAssembler* masm) { 2556 void BinaryOpStub::GenerateAddStrings(MacroAssembler* masm) {
2540 ASSERT(op_ == Token::ADD); 2557 ASSERT(op_ == Token::ADD);
2541 Label left_not_string, call_runtime; 2558 Label left_not_string, call_runtime;
2542 2559
2543 Register left = r1; 2560 Register left = r1;
2544 Register right = r0; 2561 Register right = r0;
2545 2562
2546 // Check if left argument is a string. 2563 // Check if left argument is a string.
2547 __ JumpIfSmi(left, &left_not_string); 2564 __ JumpIfSmi(left, &left_not_string);
2548 __ CompareObjectType(left, r2, r2, FIRST_NONSTRING_TYPE); 2565 __ CompareObjectType(left, r2, r2, FIRST_NONSTRING_TYPE);
2549 __ b(ge, &left_not_string); 2566 __ b(ge, &left_not_string);
2550 2567
2551 StringAddStub string_add_left_stub(NO_STRING_CHECK_LEFT_IN_STUB); 2568 StringAddStub string_add_left_stub((StringAddFlags)
2569 (ERECT_FRAME | NO_STRING_CHECK_LEFT_IN_STUB));
2552 GenerateRegisterArgsPush(masm); 2570 GenerateRegisterArgsPush(masm);
2553 __ TailCallStub(&string_add_left_stub); 2571 __ TailCallStub(&string_add_left_stub);
2554 2572
2555 // Left operand is not a string, test right. 2573 // Left operand is not a string, test right.
2556 __ bind(&left_not_string); 2574 __ bind(&left_not_string);
2557 __ JumpIfSmi(right, &call_runtime); 2575 __ JumpIfSmi(right, &call_runtime);
2558 __ CompareObjectType(right, r2, r2, FIRST_NONSTRING_TYPE); 2576 __ CompareObjectType(right, r2, r2, FIRST_NONSTRING_TYPE);
2559 __ b(ge, &call_runtime); 2577 __ b(ge, &call_runtime);
2560 2578
2561 StringAddStub string_add_right_stub(NO_STRING_CHECK_RIGHT_IN_STUB); 2579 StringAddStub string_add_right_stub((StringAddFlags)
2580 (ERECT_FRAME | NO_STRING_CHECK_RIGHT_IN_STUB));
2562 GenerateRegisterArgsPush(masm); 2581 GenerateRegisterArgsPush(masm);
2563 __ TailCallStub(&string_add_right_stub); 2582 __ TailCallStub(&string_add_right_stub);
2564 2583
2565 // At least one argument is not a string. 2584 // At least one argument is not a string.
2566 __ bind(&call_runtime); 2585 __ bind(&call_runtime);
2567 } 2586 }
2568 2587
2569 2588
2570 void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm, 2589 void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm,
2571 Register result, 2590 Register result,
(...skipping 3243 matching lines...) Expand 10 before | Expand all | Expand 10 after
5815 5834
5816 // Stack on entry: 5835 // Stack on entry:
5817 // sp[0]: second argument (right). 5836 // sp[0]: second argument (right).
5818 // sp[4]: first argument (left). 5837 // sp[4]: first argument (left).
5819 5838
5820 // Load the two arguments. 5839 // Load the two arguments.
5821 __ ldr(r0, MemOperand(sp, 1 * kPointerSize)); // First argument. 5840 __ ldr(r0, MemOperand(sp, 1 * kPointerSize)); // First argument.
5822 __ ldr(r1, MemOperand(sp, 0 * kPointerSize)); // Second argument. 5841 __ ldr(r1, MemOperand(sp, 0 * kPointerSize)); // Second argument.
5823 5842
5824 // Make sure that both arguments are strings if not known in advance. 5843 // Make sure that both arguments are strings if not known in advance.
5825 if (flags_ == NO_STRING_ADD_FLAGS) { 5844 if ((flags_ & NO_STRING_ADD_FLAGS) != 0) {
5826 __ JumpIfEitherSmi(r0, r1, &call_runtime); 5845 __ JumpIfEitherSmi(r0, r1, &call_runtime);
5827 // Load instance types. 5846 // Load instance types.
5828 __ ldr(r4, FieldMemOperand(r0, HeapObject::kMapOffset)); 5847 __ ldr(r4, FieldMemOperand(r0, HeapObject::kMapOffset));
5829 __ ldr(r5, FieldMemOperand(r1, HeapObject::kMapOffset)); 5848 __ ldr(r5, FieldMemOperand(r1, HeapObject::kMapOffset));
5830 __ ldrb(r4, FieldMemOperand(r4, Map::kInstanceTypeOffset)); 5849 __ ldrb(r4, FieldMemOperand(r4, Map::kInstanceTypeOffset));
5831 __ ldrb(r5, FieldMemOperand(r5, Map::kInstanceTypeOffset)); 5850 __ ldrb(r5, FieldMemOperand(r5, Map::kInstanceTypeOffset));
5832 STATIC_ASSERT(kStringTag == 0); 5851 STATIC_ASSERT(kStringTag == 0);
5833 // If either is not a string, go to runtime. 5852 // If either is not a string, go to runtime.
5834 __ tst(r4, Operand(kIsNotStringMask)); 5853 __ tst(r4, Operand(kIsNotStringMask));
5835 __ tst(r5, Operand(kIsNotStringMask), eq); 5854 __ tst(r5, Operand(kIsNotStringMask), eq);
(...skipping 271 matching lines...) Expand 10 before | Expand all | Expand 10 after
6107 // r6: first character of result. 6126 // r6: first character of result.
6108 StringHelper::GenerateCopyCharacters(masm, r6, r7, r2, r4, false); 6127 StringHelper::GenerateCopyCharacters(masm, r6, r7, r2, r4, false);
6109 // r6: next character of result. 6128 // r6: next character of result.
6110 StringHelper::GenerateCopyCharacters(masm, r6, r1, r3, r4, false); 6129 StringHelper::GenerateCopyCharacters(masm, r6, r1, r3, r4, false);
6111 __ IncrementCounter(counters->string_add_native(), 1, r2, r3); 6130 __ IncrementCounter(counters->string_add_native(), 1, r2, r3);
6112 __ add(sp, sp, Operand(2 * kPointerSize)); 6131 __ add(sp, sp, Operand(2 * kPointerSize));
6113 __ Ret(); 6132 __ Ret();
6114 6133
6115 // Just jump to runtime to add the two strings. 6134 // Just jump to runtime to add the two strings.
6116 __ bind(&call_runtime); 6135 __ bind(&call_runtime);
6117 __ TailCallRuntime(Runtime::kStringAdd, 2, 1); 6136 if ((flags_ & ERECT_FRAME) != 0) {
6137 GenerateRegisterArgsPop(masm);
6138 // Build a frame
6139 {
6140 FrameScope scope(masm, StackFrame::INTERNAL);
6141 GenerateRegisterArgsPush(masm);
6142 __ CallRuntime(Runtime::kStringAdd, 2);
6143 }
6144 __ Ret();
6145 } else {
6146 __ TailCallRuntime(Runtime::kStringAdd, 2, 1);
6147 }
6118 6148
6119 if (call_builtin.is_linked()) { 6149 if (call_builtin.is_linked()) {
6120 __ bind(&call_builtin); 6150 __ bind(&call_builtin);
6121 __ InvokeBuiltin(builtin_id, JUMP_FUNCTION); 6151 if ((flags_ & ERECT_FRAME) != 0) {
6152 GenerateRegisterArgsPop(masm);
6153 // Build a frame
6154 {
6155 FrameScope scope(masm, StackFrame::INTERNAL);
6156 GenerateRegisterArgsPush(masm);
6157 __ InvokeBuiltin(builtin_id, CALL_FUNCTION);
6158 }
6159 __ Ret();
6160 } else {
6161 __ InvokeBuiltin(builtin_id, JUMP_FUNCTION);
6162 }
6122 } 6163 }
6123 } 6164 }
6124 6165
6125 6166
6167 void StringAddStub::GenerateRegisterArgsPush(MacroAssembler* masm) {
6168 __ push(r0);
6169 __ push(r1);
6170 }
6171
6172
6173 void StringAddStub::GenerateRegisterArgsPop(MacroAssembler* masm) {
6174 __ pop(r1);
6175 __ pop(r0);
6176 }
6177
6178
6126 void StringAddStub::GenerateConvertArgument(MacroAssembler* masm, 6179 void StringAddStub::GenerateConvertArgument(MacroAssembler* masm,
6127 int stack_offset, 6180 int stack_offset,
6128 Register arg, 6181 Register arg,
6129 Register scratch1, 6182 Register scratch1,
6130 Register scratch2, 6183 Register scratch2,
6131 Register scratch3, 6184 Register scratch3,
6132 Register scratch4, 6185 Register scratch4,
6133 Label* slow) { 6186 Label* slow) {
6134 // First check if the argument is already a string. 6187 // First check if the argument is already a string.
6135 Label not_string, done; 6188 Label not_string, done;
(...skipping 1269 matching lines...) Expand 10 before | Expand all | Expand 10 after
7405 __ Jump(generic_construct_stub, RelocInfo::CODE_TARGET); 7458 __ Jump(generic_construct_stub, RelocInfo::CODE_TARGET);
7406 } 7459 }
7407 } 7460 }
7408 7461
7409 7462
7410 #undef __ 7463 #undef __
7411 7464
7412 } } // namespace v8::internal 7465 } } // namespace v8::internal
7413 7466
7414 #endif // V8_TARGET_ARCH_ARM 7467 #endif // V8_TARGET_ARCH_ARM
OLDNEW
« no previous file with comments | « src/arm/code-stubs-arm.h ('k') | src/arm/simulator-arm.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698