// Copyright 2014 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#if V8_TARGET_ARCH_S390

#include "src/code-stubs.h"
#include "src/api-arguments.h"
#include "src/base/bits.h"
#include "src/bootstrapper.h"
#include "src/codegen.h"
#include "src/ic/handler-compiler.h"
#include "src/ic/ic.h"
#include "src/ic/stub-cache.h"
#include "src/isolate.h"
#include "src/regexp/jsregexp.h"
#include "src/regexp/regexp-macro-assembler.h"
#include "src/runtime/runtime.h"
#include "src/s390/code-stubs-s390.h"

namespace v8 {
namespace internal {

static void InitializeArrayConstructorDescriptor(
    Isolate* isolate, CodeStubDescriptor* descriptor,
    int constant_stack_parameter_count) {
  Address deopt_handler =
      Runtime::FunctionForId(Runtime::kArrayConstructor)->entry;

  if (constant_stack_parameter_count == 0) {
    descriptor->Initialize(deopt_handler, constant_stack_parameter_count,
                           JS_FUNCTION_STUB_MODE);
  } else {
    descriptor->Initialize(r2, deopt_handler, constant_stack_parameter_count,
                           JS_FUNCTION_STUB_MODE);
  }
}

static void InitializeInternalArrayConstructorDescriptor(
    Isolate* isolate, CodeStubDescriptor* descriptor,
    int constant_stack_parameter_count) {
  Address deopt_handler =
      Runtime::FunctionForId(Runtime::kInternalArrayConstructor)->entry;

  if (constant_stack_parameter_count == 0) {
    descriptor->Initialize(deopt_handler, constant_stack_parameter_count,
                           JS_FUNCTION_STUB_MODE);
  } else {
    descriptor->Initialize(r2, deopt_handler, constant_stack_parameter_count,
                           JS_FUNCTION_STUB_MODE);
  }
}

void ArrayNoArgumentConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeArrayConstructorDescriptor(isolate(), descriptor, 0);
}

void ArraySingleArgumentConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeArrayConstructorDescriptor(isolate(), descriptor, 1);
}

void ArrayNArgumentsConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeArrayConstructorDescriptor(isolate(), descriptor, -1);
}

void InternalArrayNoArgumentConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeInternalArrayConstructorDescriptor(isolate(), descriptor, 0);
}

void FastArrayPushStub::InitializeDescriptor(CodeStubDescriptor* descriptor) {
  Address deopt_handler = Runtime::FunctionForId(Runtime::kArrayPush)->entry;
  descriptor->Initialize(r2, deopt_handler, -1, JS_FUNCTION_STUB_MODE);
}

void InternalArraySingleArgumentConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeInternalArrayConstructorDescriptor(isolate(), descriptor, 1);
}

void InternalArrayNArgumentsConstructorStub::InitializeDescriptor(
    CodeStubDescriptor* descriptor) {
  InitializeInternalArrayConstructorDescriptor(isolate(), descriptor, -1);
}

#define __ ACCESS_MASM(masm)

static void EmitIdenticalObjectComparison(MacroAssembler* masm, Label* slow,
                                          Condition cond);
static void EmitSmiNonsmiComparison(MacroAssembler* masm, Register lhs,
                                    Register rhs, Label* lhs_not_nan,
                                    Label* slow, bool strict);
static void EmitStrictTwoHeapObjectCompare(MacroAssembler* masm, Register lhs,
                                           Register rhs);

void HydrogenCodeStub::GenerateLightweightMiss(MacroAssembler* masm,
                                               ExternalReference miss) {
  // Update the static counter each time a new code stub is generated.
  isolate()->counters()->code_stubs()->Increment();

  CallInterfaceDescriptor descriptor = GetCallInterfaceDescriptor();
  int param_count = descriptor.GetRegisterParameterCount();
  {
    // Call the runtime system in a fresh internal frame.
    FrameScope scope(masm, StackFrame::INTERNAL);
    DCHECK(param_count == 0 ||
           r2.is(descriptor.GetRegisterParameter(param_count - 1)));
    // Push arguments
    for (int i = 0; i < param_count; ++i) {
      __ push(descriptor.GetRegisterParameter(i));
    }
    __ CallExternalReference(miss, param_count);
  }

  __ Ret();
}

void DoubleToIStub::Generate(MacroAssembler* masm) {
  Label out_of_range, only_low, negate, done, fastpath_done;
  Register input_reg = source();
  Register result_reg = destination();
  DCHECK(is_truncating());

  int double_offset = offset();

  // Immediate values for this stub fit in instructions, so it's safe to use ip.
  Register scratch = GetRegisterThatIsNotOneOf(input_reg, result_reg);
  Register scratch_low =
      GetRegisterThatIsNotOneOf(input_reg, result_reg, scratch);
  Register scratch_high =
      GetRegisterThatIsNotOneOf(input_reg, result_reg, scratch, scratch_low);
  DoubleRegister double_scratch = kScratchDoubleReg;

  __ push(scratch);
  // Account for saved regs if input is sp.
  if (input_reg.is(sp)) double_offset += kPointerSize;

  if (!skip_fastpath()) {
    // Load double input.
    __ LoadDouble(double_scratch, MemOperand(input_reg, double_offset));

    // Do fast-path convert from double to int.
    __ ConvertDoubleToInt64(double_scratch,
#if !V8_TARGET_ARCH_S390X
                            scratch,
#endif
                            result_reg, d0);

// Test for overflow
#if V8_TARGET_ARCH_S390X
    __ TestIfInt32(result_reg, r0);
#else
    __ TestIfInt32(scratch, result_reg, r0);
#endif
    __ beq(&fastpath_done, Label::kNear);
  }

  __ Push(scratch_high, scratch_low);
  // Account for saved regs if input is sp.
  if (input_reg.is(sp)) double_offset += 2 * kPointerSize;

  __ LoadlW(scratch_high,
            MemOperand(input_reg, double_offset + Register::kExponentOffset));
  __ LoadlW(scratch_low,
            MemOperand(input_reg, double_offset + Register::kMantissaOffset));

  __ ExtractBitMask(scratch, scratch_high, HeapNumber::kExponentMask);
  // Load scratch with exponent - 1. This is faster than loading
  // with exponent because Bias + 1 = 1024 which is a *S390* immediate value.
  STATIC_ASSERT(HeapNumber::kExponentBias + 1 == 1024);
  __ SubP(scratch, Operand(HeapNumber::kExponentBias + 1));
  // If exponent is greater than or equal to 84, the 32 less significant
  // bits are 0s (2^84 = 1, 52 significant bits, 32 uncoded bits),
  // the result is 0.
  // Compare exponent with 84 (compare exponent - 1 with 83).
  __ CmpP(scratch, Operand(83));
  __ bge(&out_of_range, Label::kNear);

  // If we reach this code, 31 <= exponent <= 83.
  // So, we don't have to handle cases where 0 <= exponent <= 20 for
  // which we would need to shift right the high part of the mantissa.
  // Scratch contains exponent - 1.
  // Load scratch with 52 - exponent (load with 51 - (exponent - 1)).
  __ Load(r0, Operand(51));
  __ SubP(scratch, r0, scratch);
  __ CmpP(scratch, Operand::Zero());
  __ ble(&only_low, Label::kNear);
  // 21 <= exponent <= 51, shift scratch_low and scratch_high
  // to generate the result.
  __ ShiftRight(scratch_low, scratch_low, scratch);
  // Scratch contains: 52 - exponent.
  // We needs: exponent - 20.
  // So we use: 32 - scratch = 32 - 52 + exponent = exponent - 20.
  __ Load(r0, Operand(32));
  __ SubP(scratch, r0, scratch);
  __ ExtractBitMask(result_reg, scratch_high, HeapNumber::kMantissaMask);
  // Set the implicit 1 before the mantissa part in scratch_high.
  STATIC_ASSERT(HeapNumber::kMantissaBitsInTopWord >= 16);
  __ Load(r0, Operand(1 << ((HeapNumber::kMantissaBitsInTopWord)-16)));
  __ ShiftLeftP(r0, r0, Operand(16));
  __ OrP(result_reg, result_reg, r0);
  __ ShiftLeft(r0, result_reg, scratch);
  __ OrP(result_reg, scratch_low, r0);
  __ b(&negate, Label::kNear);

  __ bind(&out_of_range);
  __ mov(result_reg, Operand::Zero());
  __ b(&done, Label::kNear);

  __ bind(&only_low);
  // 52 <= exponent <= 83, shift only scratch_low.
  // On entry, scratch contains: 52 - exponent.
  __ LoadComplementRR(scratch, scratch);
  __ ShiftLeft(result_reg, scratch_low, scratch);

  __ bind(&negate);
  // If input was positive, scratch_high ASR 31 equals 0 and
  // scratch_high LSR 31 equals zero.
  // New result = (result eor 0) + 0 = result.
  // If the input was negative, we have to negate the result.
  // Input_high ASR 31 equals 0xffffffff and scratch_high LSR 31 equals 1.
  // New result = (result eor 0xffffffff) + 1 = 0 - result.
  __ ShiftRightArith(r0, scratch_high, Operand(31));
#if V8_TARGET_ARCH_S390X
  __ lgfr(r0, r0);
  __ ShiftRightP(r0, r0, Operand(32));
#endif
  __ XorP(result_reg, r0);
  __ ShiftRight(r0, scratch_high, Operand(31));
  __ AddP(result_reg, r0);

  __ bind(&done);
  __ Pop(scratch_high, scratch_low);

  __ bind(&fastpath_done);
  __ pop(scratch);

  __ Ret();
}

// Handle the case where the lhs and rhs are the same object.
// Equality is almost reflexive (everything but NaN), so this is a test
// for "identity and not NaN".
static void EmitIdenticalObjectComparison(MacroAssembler* masm, Label* slow,
                                          Condition cond) {
  Label not_identical;
  Label heap_number, return_equal;
  __ CmpP(r2, r3);
  __ bne(&not_identical);

  // Test for NaN. Sadly, we can't just compare to Factory::nan_value(),
  // so we do the second best thing - test it ourselves.
  // They are both equal and they are not both Smis so both of them are not
  // Smis.  If it's not a heap number, then return equal.
  if (cond == lt || cond == gt) {
    // Call runtime on identical JSObjects.
    __ CompareObjectType(r2, r6, r6, FIRST_JS_RECEIVER_TYPE);
    __ bge(slow);
    // Call runtime on identical symbols since we need to throw a TypeError.
    __ CmpP(r6, Operand(SYMBOL_TYPE));
    __ beq(slow);
    // Call runtime on identical SIMD values since we must throw a TypeError.
    __ CmpP(r6, Operand(SIMD128_VALUE_TYPE));
    __ beq(slow);
  } else {
    __ CompareObjectType(r2, r6, r6, HEAP_NUMBER_TYPE);
    __ beq(&heap_number);
    // Comparing JS objects with <=, >= is complicated.
    if (cond != eq) {
      __ CmpP(r6, Operand(FIRST_JS_RECEIVER_TYPE));
      __ bge(slow);
      // Call runtime on identical symbols since we need to throw a TypeError.
      __ CmpP(r6, Operand(SYMBOL_TYPE));
      __ beq(slow);
      // Call runtime on identical SIMD values since we must throw a TypeError.
      __ CmpP(r6, Operand(SIMD128_VALUE_TYPE));
      __ beq(slow);
      // Normally here we fall through to return_equal, but undefined is
      // special: (undefined == undefined) == true, but
      // (undefined <= undefined) == false!  See ECMAScript 11.8.5.
      if (cond == le || cond == ge) {
        __ CmpP(r6, Operand(ODDBALL_TYPE));
        __ bne(&return_equal);
        __ CompareRoot(r2, Heap::kUndefinedValueRootIndex);
        __ bne(&return_equal);
        if (cond == le) {
          // undefined <= undefined should fail.
          __ LoadImmP(r2, Operand(GREATER));
        } else {
          // undefined >= undefined should fail.
          __ LoadImmP(r2, Operand(LESS));
        }
        __ Ret();
      }
    }
  }

  __ bind(&return_equal);
  if (cond == lt) {
    __ LoadImmP(r2, Operand(GREATER));  // Things aren't less than themselves.
  } else if (cond == gt) {
    __ LoadImmP(r2, Operand(LESS));  // Things aren't greater than themselves.
  } else {
    __ LoadImmP(r2, Operand(EQUAL));  // Things are <=, >=, ==, === themselves
  }
  __ Ret();

  // For less and greater we don't have to check for NaN since the result of
  // x < x is false regardless.  For the others here is some code to check
  // for NaN.
  if (cond != lt && cond != gt) {
    __ bind(&heap_number);
    // It is a heap number, so return non-equal if it's NaN and equal if it's
    // not NaN.

    // The representation of NaN values has all exponent bits (52..62) set,
    // and not all mantissa bits (0..51) clear.
    // Read top bits of double representation (second word of value).
    __ LoadlW(r4, FieldMemOperand(r2, HeapNumber::kExponentOffset));
    // Test that exponent bits are all set.
    STATIC_ASSERT(HeapNumber::kExponentMask == 0x7ff00000u);
    __ ExtractBitMask(r5, r4, HeapNumber::kExponentMask);
    __ CmpLogicalP(r5, Operand(0x7ff));
    __ bne(&return_equal);

    // Shift out flag and all exponent bits, retaining only mantissa.
    __ sll(r4, Operand(HeapNumber::kNonMantissaBitsInTopWord));
    // Or with all low-bits of mantissa.
    __ LoadlW(r5, FieldMemOperand(r2, HeapNumber::kMantissaOffset));
    __ OrP(r2, r5, r4);
    __ CmpP(r2, Operand::Zero());
    // For equal we already have the right value in r2:  Return zero (equal)
    // if all bits in mantissa are zero (it's an Infinity) and non-zero if
    // not (it's a NaN).  For <= and >= we need to load r0 with the failing
    // value if it's a NaN.
    if (cond != eq) {
      Label not_equal;
      __ bne(&not_equal, Label::kNear);
      // All-zero means Infinity means equal.
      __ Ret();
      __ bind(&not_equal);
      if (cond == le) {
        __ LoadImmP(r2, Operand(GREATER));  // NaN <= NaN should fail.
      } else {
        __ LoadImmP(r2, Operand(LESS));  // NaN >= NaN should fail.
      }
    }
    __ Ret();
  }
  // No fall through here.

  __ bind(&not_identical);
}

// See comment at call site.
static void EmitSmiNonsmiComparison(MacroAssembler* masm, Register lhs,
                                    Register rhs, Label* lhs_not_nan,
                                    Label* slow, bool strict) {
  DCHECK((lhs.is(r2) && rhs.is(r3)) || (lhs.is(r3) && rhs.is(r2)));

  Label rhs_is_smi;
  __ JumpIfSmi(rhs, &rhs_is_smi);

  // Lhs is a Smi.  Check whether the rhs is a heap number.
  __ CompareObjectType(rhs, r5, r6, HEAP_NUMBER_TYPE);
  if (strict) {
    // If rhs is not a number and lhs is a Smi then strict equality cannot
    // succeed.  Return non-equal
    // If rhs is r2 then there is already a non zero value in it.
    Label skip;
    __ beq(&skip, Label::kNear);
    if (!rhs.is(r2)) {
      __ mov(r2, Operand(NOT_EQUAL));
    }
    __ Ret();
    __ bind(&skip);
  } else {
    // Smi compared non-strictly with a non-Smi non-heap-number.  Call
    // the runtime.
    __ bne(slow);
  }

  // Lhs is a smi, rhs is a number.
  // Convert lhs to a double in d7.
  __ SmiToDouble(d7, lhs);
  // Load the double from rhs, tagged HeapNumber r2, to d6.
  __ LoadDouble(d6, FieldMemOperand(rhs, HeapNumber::kValueOffset));

  // We now have both loaded as doubles but we can skip the lhs nan check
  // since it's a smi.
  __ b(lhs_not_nan);

  __ bind(&rhs_is_smi);
  // Rhs is a smi.  Check whether the non-smi lhs is a heap number.
  __ CompareObjectType(lhs, r6, r6, HEAP_NUMBER_TYPE);
  if (strict) {
    // If lhs is not a number and rhs is a smi then strict equality cannot
    // succeed.  Return non-equal.
    // If lhs is r2 then there is already a non zero value in it.
    Label skip;
    __ beq(&skip, Label::kNear);
    if (!lhs.is(r2)) {
      __ mov(r2, Operand(NOT_EQUAL));
    }
    __ Ret();
    __ bind(&skip);
  } else {
    // Smi compared non-strictly with a non-smi non-heap-number.  Call
    // the runtime.
    __ bne(slow);
  }

  // Rhs is a smi, lhs is a heap number.
  // Load the double from lhs, tagged HeapNumber r3, to d7.
  __ LoadDouble(d7, FieldMemOperand(lhs, HeapNumber::kValueOffset));
  // Convert rhs to a double in d6.
  __ SmiToDouble(d6, rhs);
  // Fall through to both_loaded_as_doubles.
}

// See comment at call site.
static void EmitStrictTwoHeapObjectCompare(MacroAssembler* masm, Register lhs,
                                           Register rhs) {
  DCHECK((lhs.is(r2) && rhs.is(r3)) || (lhs.is(r3) && rhs.is(r2)));

  // If either operand is a JS object or an oddball value, then they are
  // not equal since their pointers are different.
  // There is no test for undetectability in strict equality.
  STATIC_ASSERT(LAST_TYPE == LAST_JS_RECEIVER_TYPE);
  Label first_non_object;
  // Get the type of the first operand into r4 and compare it with
  // FIRST_JS_RECEIVER_TYPE.
  __ CompareObjectType(rhs, r4, r4, FIRST_JS_RECEIVER_TYPE);
  __ blt(&first_non_object, Label::kNear);

  // Return non-zero (r2 is not zero)
  Label return_not_equal;
  __ bind(&return_not_equal);
  __ Ret();

  __ bind(&first_non_object);
  // Check for oddballs: true, false, null, undefined.
  __ CmpP(r4, Operand(ODDBALL_TYPE));
  __ beq(&return_not_equal);

  __ CompareObjectType(lhs, r5, r5, FIRST_JS_RECEIVER_TYPE);
  __ bge(&return_not_equal);

  // Check for oddballs: true, false, null, undefined.
  __ CmpP(r5, Operand(ODDBALL_TYPE));
  __ beq(&return_not_equal);

  // Now that we have the types we might as well check for
  // internalized-internalized.
  STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0);
  __ OrP(r4, r4, r5);
  __ AndP(r0, r4, Operand(kIsNotStringMask | kIsNotInternalizedMask));
  __ beq(&return_not_equal);
}

// See comment at call site.
static void EmitCheckForTwoHeapNumbers(MacroAssembler* masm, Register lhs,
                                       Register rhs,
                                       Label* both_loaded_as_doubles,
                                       Label* not_heap_numbers, Label* slow) {
  DCHECK((lhs.is(r2) && rhs.is(r3)) || (lhs.is(r3) && rhs.is(r2)));

  __ CompareObjectType(rhs, r5, r4, HEAP_NUMBER_TYPE);
  __ bne(not_heap_numbers);
  __ LoadP(r4, FieldMemOperand(lhs, HeapObject::kMapOffset));
  __ CmpP(r4, r5);
  __ bne(slow);  // First was a heap number, second wasn't.  Go slow case.

  // Both are heap numbers.  Load them up then jump to the code we have
  // for that.
  __ LoadDouble(d6, FieldMemOperand(rhs, HeapNumber::kValueOffset));
  __ LoadDouble(d7, FieldMemOperand(lhs, HeapNumber::kValueOffset));

  __ b(both_loaded_as_doubles);
}

// Fast negative check for internalized-to-internalized equality or receiver
// equality. Also handles the undetectable receiver to null/undefined
// comparison.
static void EmitCheckForInternalizedStringsOrObjects(MacroAssembler* masm,
                                                     Register lhs, Register rhs,
                                                     Label* possible_strings,
                                                     Label* runtime_call) {
  DCHECK((lhs.is(r2) && rhs.is(r3)) || (lhs.is(r3) && rhs.is(r2)));

  // r4 is object type of rhs.
  Label object_test, return_equal, return_unequal, undetectable;
  STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0);
  __ mov(r0, Operand(kIsNotStringMask));
  __ AndP(r0, r4);
  __ bne(&object_test, Label::kNear);
  __ mov(r0, Operand(kIsNotInternalizedMask));
  __ AndP(r0, r4);
  __ bne(possible_strings);
  __ CompareObjectType(lhs, r5, r5, FIRST_NONSTRING_TYPE);
  __ bge(runtime_call);
  __ mov(r0, Operand(kIsNotInternalizedMask));
  __ AndP(r0, r5);
  __ bne(possible_strings);

  // Both are internalized. We already checked they weren't the same pointer so
  // they are not equal. Return non-equal by returning the non-zero object
  // pointer in r2.
  __ Ret();

  __ bind(&object_test);
  __ LoadP(r4, FieldMemOperand(lhs, HeapObject::kMapOffset));
  __ LoadP(r5, FieldMemOperand(rhs, HeapObject::kMapOffset));
  __ LoadlB(r6, FieldMemOperand(r4, Map::kBitFieldOffset));
  __ LoadlB(r7, FieldMemOperand(r5, Map::kBitFieldOffset));
  __ AndP(r0, r6, Operand(1 << Map::kIsUndetectable));
  __ bne(&undetectable);
  __ AndP(r0, r7, Operand(1 << Map::kIsUndetectable));
  __ bne(&return_unequal);

  __ CompareInstanceType(r4, r4, FIRST_JS_RECEIVER_TYPE);
  __ blt(runtime_call);
  __ CompareInstanceType(r5, r5, FIRST_JS_RECEIVER_TYPE);
  __ blt(runtime_call);

  __ bind(&return_unequal);
  // Return non-equal by returning the non-zero object pointer in r2.
  __ Ret();

  __ bind(&undetectable);
  __ AndP(r0, r7, Operand(1 << Map::kIsUndetectable));
  __ beq(&return_unequal);

  // If both sides are JSReceivers, then the result is false according to
  // the HTML specification, which says that only comparisons with null or
  // undefined are affected by special casing for document.all.
  __ CompareInstanceType(r4, r4, ODDBALL_TYPE);
  __ beq(&return_equal);
  __ CompareInstanceType(r5, r5, ODDBALL_TYPE);
  __ bne(&return_unequal);

  __ bind(&return_equal);
  __ LoadImmP(r2, Operand(EQUAL));
  __ Ret();
}

static void CompareICStub_CheckInputType(MacroAssembler* masm, Register input,
                                         Register scratch,
                                         CompareICState::State expected,
                                         Label* fail) {
  Label ok;
  if (expected == CompareICState::SMI) {
    __ JumpIfNotSmi(input, fail);
  } else if (expected == CompareICState::NUMBER) {
    __ JumpIfSmi(input, &ok);
    __ CheckMap(input, scratch, Heap::kHeapNumberMapRootIndex, fail,
                DONT_DO_SMI_CHECK);
  }
  // We could be strict about internalized/non-internalized here, but as long as
  // hydrogen doesn't care, the stub doesn't have to care either.
  __ bind(&ok);
}

// On entry r3 and r4 are the values to be compared.
// On exit r2 is 0, positive or negative to indicate the result of
// the comparison.
void CompareICStub::GenerateGeneric(MacroAssembler* masm) {
  Register lhs = r3;
  Register rhs = r2;
  Condition cc = GetCondition();

  Label miss;
  CompareICStub_CheckInputType(masm, lhs, r4, left(), &miss);
  CompareICStub_CheckInputType(masm, rhs, r5, right(), &miss);

  Label slow;  // Call builtin.
  Label not_smis, both_loaded_as_doubles, lhs_not_nan;

  Label not_two_smis, smi_done;
  __ OrP(r4, r3, r2);
  __ JumpIfNotSmi(r4, &not_two_smis);
  __ SmiUntag(r3);
  __ SmiUntag(r2);
  __ SubP(r2, r3, r2);
  __ Ret();
  __ bind(&not_two_smis);

  // NOTICE! This code is only reached after a smi-fast-case check, so
  // it is certain that at least one operand isn't a smi.

  // Handle the case where the objects are identical.  Either returns the answer
  // or goes to slow.  Only falls through if the objects were not identical.
  EmitIdenticalObjectComparison(masm, &slow, cc);

  // If either is a Smi (we know that not both are), then they can only
  // be strictly equal if the other is a HeapNumber.
  STATIC_ASSERT(kSmiTag == 0);
  DCHECK_EQ(static_cast<Smi*>(0), Smi::FromInt(0));
  __ AndP(r4, lhs, rhs);
  __ JumpIfNotSmi(r4, &not_smis);
  // One operand is a smi.  EmitSmiNonsmiComparison generates code that can:
  // 1) Return the answer.
  // 2) Go to slow.
  // 3) Fall through to both_loaded_as_doubles.
  // 4) Jump to lhs_not_nan.
  // In cases 3 and 4 we have found out we were dealing with a number-number
  // comparison.  The double values of the numbers have been loaded
  // into d7 and d6.
  EmitSmiNonsmiComparison(masm, lhs, rhs, &lhs_not_nan, &slow, strict());

  __ bind(&both_loaded_as_doubles);
  // The arguments have been converted to doubles and stored in d6 and d7
  __ bind(&lhs_not_nan);
  Label no_nan;
  __ cdbr(d7, d6);

  Label nan, equal, less_than;
  __ bunordered(&nan);
  __ beq(&equal, Label::kNear);
  __ blt(&less_than, Label::kNear);
  __ LoadImmP(r2, Operand(GREATER));
  __ Ret();
  __ bind(&equal);
  __ LoadImmP(r2, Operand(EQUAL));
  __ Ret();
  __ bind(&less_than);
  __ LoadImmP(r2, Operand(LESS));
  __ Ret();

  __ bind(&nan);
  // If one of the sides was a NaN then the v flag is set.  Load r2 with
  // whatever it takes to make the comparison fail, since comparisons with NaN
  // always fail.
  if (cc == lt || cc == le) {
    __ LoadImmP(r2, Operand(GREATER));
  } else {
    __ LoadImmP(r2, Operand(LESS));
  }
  __ Ret();

  __ bind(&not_smis);
  // At this point we know we are dealing with two different objects,
  // and neither of them is a Smi.  The objects are in rhs_ and lhs_.
  if (strict()) {
    // This returns non-equal for some object types, or falls through if it
    // was not lucky.
    EmitStrictTwoHeapObjectCompare(masm, lhs, rhs);
  }

  Label check_for_internalized_strings;
  Label flat_string_check;
  // Check for heap-number-heap-number comparison.  Can jump to slow case,
  // or load both doubles into r2, r3, r4, r5 and jump to the code that handles
  // that case.  If the inputs are not doubles then jumps to
  // check_for_internalized_strings.
  // In this case r4 will contain the type of rhs_.  Never falls through.
  EmitCheckForTwoHeapNumbers(masm, lhs, rhs, &both_loaded_as_doubles,
                             &check_for_internalized_strings,
                             &flat_string_check);

  __ bind(&check_for_internalized_strings);
  // In the strict case the EmitStrictTwoHeapObjectCompare already took care of
  // internalized strings.
  if (cc == eq && !strict()) {
    // Returns an answer for two internalized strings or two detectable objects.
    // Otherwise jumps to string case or not both strings case.
    // Assumes that r4 is the type of rhs_ on entry.
    EmitCheckForInternalizedStringsOrObjects(masm, lhs, rhs, &flat_string_check,
                                             &slow);
  }

  // Check for both being sequential one-byte strings,
  // and inline if that is the case.
  __ bind(&flat_string_check);

  __ JumpIfNonSmisNotBothSequentialOneByteStrings(lhs, rhs, r4, r5, &slow);

  __ IncrementCounter(isolate()->counters()->string_compare_native(), 1, r4,
                      r5);
  if (cc == eq) {
    StringHelper::GenerateFlatOneByteStringEquals(masm, lhs, rhs, r4, r5);
  } else {
    StringHelper::GenerateCompareFlatOneByteStrings(masm, lhs, rhs, r4, r5, r6);
  }
  // Never falls through to here.

  __ bind(&slow);

  if (cc == eq) {
    {
      FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
      __ Push(lhs, rhs);
      __ CallRuntime(strict() ? Runtime::kStrictEqual : Runtime::kEqual);
    }
    // Turn true into 0 and false into some non-zero value.
    STATIC_ASSERT(EQUAL == 0);
    __ LoadRoot(r3, Heap::kTrueValueRootIndex);
    __ SubP(r2, r2, r3);
    __ Ret();
  } else {
    __ Push(lhs, rhs);
    int ncr;  // NaN compare result
    if (cc == lt || cc == le) {
      ncr = GREATER;
    } else {
      DCHECK(cc == gt || cc == ge);  // remaining cases
      ncr = LESS;
    }
    __ LoadSmiLiteral(r2, Smi::FromInt(ncr));
    __ push(r2);

    // Call the native; it returns -1 (less), 0 (equal), or 1 (greater)
    // tagged as a small integer.
    __ TailCallRuntime(Runtime::kCompare);
  }

  __ bind(&miss);
  GenerateMiss(masm);
}

void StoreBufferOverflowStub::Generate(MacroAssembler* masm) {
  // We don't allow a GC during a store buffer overflow so there is no need to
  // store the registers in any particular way, but we do have to store and
  // restore them.
  __ MultiPush(kJSCallerSaved | r14.bit());
  if (save_doubles()) {
    __ MultiPushDoubles(kCallerSavedDoubles);
  }
  const int argument_count = 1;
  const int fp_argument_count = 0;
  const Register scratch = r3;

  AllowExternalCallThatCantCauseGC scope(masm);
  __ PrepareCallCFunction(argument_count, fp_argument_count, scratch);
  __ mov(r2, Operand(ExternalReference::isolate_address(isolate())));
  __ CallCFunction(ExternalReference::store_buffer_overflow_function(isolate()),
                   argument_count);
  if (save_doubles()) {
    __ MultiPopDoubles(kCallerSavedDoubles);
  }
  __ MultiPop(kJSCallerSaved | r14.bit());
  __ Ret();
}

void StoreRegistersStateStub::Generate(MacroAssembler* masm) {
  __ PushSafepointRegisters();
  __ b(r14);
}

void RestoreRegistersStateStub::Generate(MacroAssembler* masm) {
  __ PopSafepointRegisters();
  __ b(r14);
}

void MathPowStub::Generate(MacroAssembler* masm) {
  const Register base = r3;
  const Register exponent = MathPowTaggedDescriptor::exponent();
  DCHECK(exponent.is(r4));
  const Register heapnumbermap = r7;
  const Register heapnumber = r2;
  const DoubleRegister double_base = d1;
  const DoubleRegister double_exponent = d2;
  const DoubleRegister double_result = d3;
  const DoubleRegister double_scratch = d0;
  const Register scratch = r1;
  const Register scratch2 = r9;

  Label call_runtime, done, int_exponent;
  if (exponent_type() == ON_STACK) {
    Label base_is_smi, unpack_exponent;
    // The exponent and base are supplied as arguments on the stack.
    // This can only happen if the stub is called from non-optimized code.
    // Load input parameters from stack to double registers.
    __ LoadP(base, MemOperand(sp, 1 * kPointerSize));
    __ LoadP(exponent, MemOperand(sp, 0 * kPointerSize));

    __ LoadRoot(heapnumbermap, Heap::kHeapNumberMapRootIndex);

    __ UntagAndJumpIfSmi(scratch, base, &base_is_smi);
    __ LoadP(scratch, FieldMemOperand(base, JSObject::kMapOffset));
    __ CmpP(scratch, heapnumbermap);
    __ bne(&call_runtime);

    __ LoadDouble(double_base, FieldMemOperand(base, HeapNumber::kValueOffset));
    __ b(&unpack_exponent, Label::kNear);

    __ bind(&base_is_smi);
    __ ConvertIntToDouble(scratch, double_base);
    __ bind(&unpack_exponent);

    __ UntagAndJumpIfSmi(scratch, exponent, &int_exponent);
    __ LoadP(scratch, FieldMemOperand(exponent, JSObject::kMapOffset));
    __ CmpP(scratch, heapnumbermap);
    __ bne(&call_runtime);

    __ LoadDouble(double_exponent,
                  FieldMemOperand(exponent, HeapNumber::kValueOffset));
  } else if (exponent_type() == TAGGED) {
    // Base is already in double_base.
    __ UntagAndJumpIfSmi(scratch, exponent, &int_exponent);

    __ LoadDouble(double_exponent,
                  FieldMemOperand(exponent, HeapNumber::kValueOffset));
  }

  if (exponent_type() != INTEGER) {
    // Detect integer exponents stored as double.
    __ TryDoubleToInt32Exact(scratch, double_exponent, scratch2,
                             double_scratch);
    __ beq(&int_exponent, Label::kNear);

    if (exponent_type() == ON_STACK) {
      // Detect square root case.  Crankshaft detects constant +/-0.5 at
      // compile time and uses DoMathPowHalf instead.  We then skip this check
      // for non-constant cases of +/-0.5 as these hardly occur.
      Label not_plus_half, not_minus_inf1, not_minus_inf2;

      // Test for 0.5.
      __ LoadDoubleLiteral(double_scratch, 0.5, scratch);
      __ cdbr(double_exponent, double_scratch);
      __ bne(&not_plus_half, Label::kNear);

      // Calculates square root of base.  Check for the special case of
      // Math.pow(-Infinity, 0.5) == Infinity (ECMA spec, 15.8.2.13).
      __ LoadDoubleLiteral(double_scratch, -V8_INFINITY, scratch);
      __ cdbr(double_base, double_scratch);
      __ bne(&not_minus_inf1, Label::kNear);
      __ lcdbr(double_result, double_scratch);
      __ b(&done);
      __ bind(&not_minus_inf1);

      // Add +0 to convert -0 to +0.
      __ ldr(double_scratch, double_base);
      __ lzdr(kDoubleRegZero);
      __ adbr(double_scratch, kDoubleRegZero);
      __ sqdbr(double_result, double_scratch);
      __ b(&done);

      __ bind(&not_plus_half);
      __ LoadDoubleLiteral(double_scratch, -0.5, scratch);
      __ cdbr(double_exponent, double_scratch);
      __ bne(&call_runtime);

      // Calculates square root of base.  Check for the special case of
      // Math.pow(-Infinity, -0.5) == 0 (ECMA spec, 15.8.2.13).
      __ LoadDoubleLiteral(double_scratch, -V8_INFINITY, scratch);
      __ cdbr(double_base, double_scratch);
      __ bne(&not_minus_inf2, Label::kNear);
      __ ldr(double_result, kDoubleRegZero);
      __ b(&done);
      __ bind(&not_minus_inf2);

      // Add +0 to convert -0 to +0.
      __ ldr(double_scratch, double_base);
      __ lzdr(kDoubleRegZero);
      __ adbr(double_scratch, kDoubleRegZero);
      __ LoadDoubleLiteral(double_result, 1.0, scratch);
      __ sqdbr(double_scratch, double_scratch);
      __ ddbr(double_result, double_scratch);
      __ b(&done);
    }

    __ push(r14);
    {
      AllowExternalCallThatCantCauseGC scope(masm);
      __ PrepareCallCFunction(0, 2, scratch);
      __ MovToFloatParameters(double_base, double_exponent);
      __ CallCFunction(
          ExternalReference::power_double_double_function(isolate()), 0, 2);
    }
    __ pop(r14);
    __ MovFromFloatResult(double_result);
    __ b(&done);
  }

  // Calculate power with integer exponent.
  __ bind(&int_exponent);

  // Get two copies of exponent in the registers scratch and exponent.
  if (exponent_type() == INTEGER) {
    __ LoadRR(scratch, exponent);
  } else {
    // Exponent has previously been stored into scratch as untagged integer.
    __ LoadRR(exponent, scratch);
  }
  __ ldr(double_scratch, double_base);  // Back up base.
  __ LoadImmP(scratch2, Operand(1));
  __ ConvertIntToDouble(scratch2, double_result);

  // Get absolute value of exponent.
  Label positive_exponent;
  __ CmpP(scratch, Operand::Zero());
  __ bge(&positive_exponent, Label::kNear);
  __ LoadComplementRR(scratch, scratch);
  __ bind(&positive_exponent);

  Label while_true, no_carry, loop_end;
  __ bind(&while_true);
  __ mov(scratch2, Operand(1));
  __ AndP(scratch2, scratch);
  __ beq(&no_carry, Label::kNear);
  __ mdbr(double_result, double_scratch);
  __ bind(&no_carry);
  __ ShiftRightArithP(scratch, scratch, Operand(1));
  __ beq(&loop_end, Label::kNear);
  __ mdbr(double_scratch, double_scratch);
  __ b(&while_true);
  __ bind(&loop_end);

  __ CmpP(exponent, Operand::Zero());
  __ bge(&done);

  // get 1/double_result:
  __ ldr(double_scratch, double_result);
  __ LoadImmP(scratch2, Operand(1));
  __ ConvertIntToDouble(scratch2, double_result);
  __ ddbr(double_result, double_scratch);

  // Test whether result is zero.  Bail out to check for subnormal result.
  // Due to subnormals, x^-y == (1/x)^y does not hold in all cases.
  __ lzdr(kDoubleRegZero);
  __ cdbr(double_result, kDoubleRegZero);
  __ bne(&done, Label::kNear);
  // double_exponent may not containe the exponent value if the input was a
  // smi.  We set it with exponent value before bailing out.
  __ ConvertIntToDouble(exponent, double_exponent);

  // Returning or bailing out.
  if (exponent_type() == ON_STACK) {
    // The arguments are still on the stack.
    __ bind(&call_runtime);
    __ TailCallRuntime(Runtime::kMathPowRT);

    // The stub is called from non-optimized code, which expects the result
    // as heap number in exponent.
    __ bind(&done);
    __ AllocateHeapNumber(heapnumber, scratch, scratch2, heapnumbermap,
                          &call_runtime);
    __ StoreDouble(double_result,
                   FieldMemOperand(heapnumber, HeapNumber::kValueOffset));
    DCHECK(heapnumber.is(r2));
    __ Ret(2);
  } else {
    __ push(r14);
    {
      AllowExternalCallThatCantCauseGC scope(masm);
      __ PrepareCallCFunction(0, 2, scratch);
      __ MovToFloatParameters(double_base, double_exponent);
      __ CallCFunction(
          ExternalReference::power_double_double_function(isolate()), 0, 2);
    }
    __ pop(r14);
    __ MovFromFloatResult(double_result);

    __ bind(&done);
    __ Ret();
  }
}

bool CEntryStub::NeedsImmovableCode() { return true; }

void CodeStub::GenerateStubsAheadOfTime(Isolate* isolate) {
  CEntryStub::GenerateAheadOfTime(isolate);
  StoreBufferOverflowStub::GenerateFixedRegStubsAheadOfTime(isolate);
  StubFailureTrampolineStub::GenerateAheadOfTime(isolate);
  ArrayConstructorStubBase::GenerateStubsAheadOfTime(isolate);
  CreateAllocationSiteStub::GenerateAheadOfTime(isolate);
  CreateWeakCellStub::GenerateAheadOfTime(isolate);
  BinaryOpICStub::GenerateAheadOfTime(isolate);
  StoreRegistersStateStub::GenerateAheadOfTime(isolate);
  RestoreRegistersStateStub::GenerateAheadOfTime(isolate);
  BinaryOpICWithAllocationSiteStub::GenerateAheadOfTime(isolate);
  StoreFastElementStub::GenerateAheadOfTime(isolate);
  TypeofStub::GenerateAheadOfTime(isolate);
}

void StoreRegistersStateStub::GenerateAheadOfTime(Isolate* isolate) {
  StoreRegistersStateStub stub(isolate);
  stub.GetCode();
}

void RestoreRegistersStateStub::GenerateAheadOfTime(Isolate* isolate) {
  RestoreRegistersStateStub stub(isolate);
  stub.GetCode();
}

void CodeStub::GenerateFPStubs(Isolate* isolate) {
  SaveFPRegsMode mode = kSaveFPRegs;
  CEntryStub(isolate, 1, mode).GetCode();
  StoreBufferOverflowStub(isolate, mode).GetCode();
  isolate->set_fp_stubs_generated(true);
}

void CEntryStub::GenerateAheadOfTime(Isolate* isolate) {
  CEntryStub stub(isolate, 1, kDontSaveFPRegs);
  stub.GetCode();
}

void CEntryStub::Generate(MacroAssembler* masm) {
  // Called from JavaScript; parameters are on stack as if calling JS function.
  // r2: number of arguments including receiver
  // r3: pointer to builtin function
  // fp: frame pointer  (restored after C call)
  // sp: stack pointer  (restored as callee's sp after C call)
  // cp: current context  (C callee-saved)
  //
  // If argv_in_register():
  // r4: pointer to the first argument
  ProfileEntryHookStub::MaybeCallEntryHook(masm);

  __ LoadRR(r7, r3);

  if (argv_in_register()) {
    // Move argv into the correct register.
    __ LoadRR(r3, r4);
  } else {
    // Compute the argv pointer.
    __ ShiftLeftP(r3, r2, Operand(kPointerSizeLog2));
    __ lay(r3, MemOperand(r3, sp, -kPointerSize));
  }

  // Enter the exit frame that transitions from JavaScript to C++.
  FrameScope scope(masm, StackFrame::MANUAL);

  // Need at least one extra slot for return address location.
  int arg_stack_space = 1;

  // Pass buffer for return value on stack if necessary
  bool needs_return_buffer =
      result_size() > 2 ||
      (result_size() == 2 && !ABI_RETURNS_OBJECTPAIR_IN_REGS);
  if (needs_return_buffer) {
    arg_stack_space += result_size();
  }

#if V8_TARGET_ARCH_S390X
  // 64-bit linux pass Argument object by reference not value
  arg_stack_space += 2;
#endif

  __ EnterExitFrame(save_doubles(), arg_stack_space);

  // Store a copy of argc, argv in callee-saved registers for later.
  __ LoadRR(r6, r2);
  __ LoadRR(r8, r3);
  // r2, r6: number of arguments including receiver  (C callee-saved)
  // r3, r8: pointer to the first argument
  // r7: pointer to builtin function  (C callee-saved)

  // Result returned in registers or stack, depending on result size and ABI.

  Register isolate_reg = r4;
  if (needs_return_buffer) {
    // The return value is 16-byte non-scalar value.
    // Use frame storage reserved by calling function to pass return
    // buffer as implicit first argument in R2.  Shfit original parameters
    // by one register each.
    __ LoadRR(r4, r3);
    __ LoadRR(r3, r2);
    __ la(r2, MemOperand(sp, (kStackFrameExtraParamSlot + 1) * kPointerSize));
    isolate_reg = r5;
  }
  // Call C built-in.
  __ mov(isolate_reg, Operand(ExternalReference::isolate_address(isolate())));

  Register target = r7;

  // To let the GC traverse the return address of the exit frames, we need to
  // know where the return address is. The CEntryStub is unmovable, so
  // we can store the address on the stack to be able to find it again and
  // we never have to restore it, because it will not change.
  {
    Label return_label;
    __ larl(r14, &return_label);  // Generate the return addr of call later.
    __ StoreP(r14, MemOperand(sp, kStackFrameRASlot * kPointerSize));

    // zLinux ABI requires caller's frame to have sufficient space for callee
    // preserved regsiter save area.
    // __ lay(sp, MemOperand(sp, -kCalleeRegisterSaveAreaSize));
    __ positions_recorder()->WriteRecordedPositions();
    __ b(target);
    __ bind(&return_label);
    // __ la(sp, MemOperand(sp, +kCalleeRegisterSaveAreaSize));
  }

  // If return value is on the stack, pop it to registers.
  if (needs_return_buffer) {
    if (result_size() > 2) __ LoadP(r4, MemOperand(r2, 2 * kPointerSize));
    __ LoadP(r3, MemOperand(r2, kPointerSize));
    __ LoadP(r2, MemOperand(r2));
  }

  // Check result for exception sentinel.
  Label exception_returned;
  __ CompareRoot(r2, Heap::kExceptionRootIndex);
  __ beq(&exception_returned, Label::kNear);

  // Check that there is no pending exception, otherwise we
  // should have returned the exception sentinel.
  if (FLAG_debug_code) {
    Label okay;
    ExternalReference pending_exception_address(
        Isolate::kPendingExceptionAddress, isolate());
    __ mov(r1, Operand(pending_exception_address));
    __ LoadP(r1, MemOperand(r1));
    __ CompareRoot(r1, Heap::kTheHoleValueRootIndex);
    // Cannot use check here as it attempts to generate call into runtime.
    __ beq(&okay, Label::kNear);
    __ stop("Unexpected pending exception");
    __ bind(&okay);
  }

  // Exit C frame and return.
  // r2:r3: result
  // sp: stack pointer
  // fp: frame pointer
  Register argc;
  if (argv_in_register()) {
    // We don't want to pop arguments so set argc to no_reg.
    argc = no_reg;
  } else {
    // r6: still holds argc (callee-saved).
    argc = r6;
  }
  __ LeaveExitFrame(save_doubles(), argc, true);
  __ b(r14);

  // Handling of exception.
  __ bind(&exception_returned);

  ExternalReference pending_handler_context_address(
      Isolate::kPendingHandlerContextAddress, isolate());
  ExternalReference pending_handler_code_address(
      Isolate::kPendingHandlerCodeAddress, isolate());
  ExternalReference pending_handler_offset_address(
      Isolate::kPendingHandlerOffsetAddress, isolate());
  ExternalReference pending_handler_fp_address(
      Isolate::kPendingHandlerFPAddress, isolate());
  ExternalReference pending_handler_sp_address(
      Isolate::kPendingHandlerSPAddress, isolate());

  // Ask the runtime for help to determine the handler. This will set r3 to
  // contain the current pending exception, don't clobber it.
  ExternalReference find_handler(Runtime::kUnwindAndFindExceptionHandler,
                                 isolate());
  {
    FrameScope scope(masm, StackFrame::MANUAL);
    __ PrepareCallCFunction(3, 0, r2);
    __ LoadImmP(r2, Operand::Zero());
    __ LoadImmP(r3, Operand::Zero());
    __ mov(r4, Operand(ExternalReference::isolate_address(isolate())));
    __ CallCFunction(find_handler, 3);
  }

  // Retrieve the handler context, SP and FP.
  __ mov(cp, Operand(pending_handler_context_address));
  __ LoadP(cp, MemOperand(cp));
  __ mov(sp, Operand(pending_handler_sp_address));
  __ LoadP(sp, MemOperand(sp));
  __ mov(fp, Operand(pending_handler_fp_address));
  __ LoadP(fp, MemOperand(fp));

  // If the handler is a JS frame, restore the context to the frame. Note that
  // the context will be set to (cp == 0) for non-JS frames.
  Label skip;
  __ CmpP(cp, Operand::Zero());
  __ beq(&skip, Label::kNear);
  __ StoreP(cp, MemOperand(fp, StandardFrameConstants::kContextOffset));
  __ bind(&skip);

  // Compute the handler entry address and jump to it.
  __ mov(r3, Operand(pending_handler_code_address));
  __ LoadP(r3, MemOperand(r3));
  __ mov(r4, Operand(pending_handler_offset_address));
  __ LoadP(r4, MemOperand(r4));
  __ AddP(r3, r3, Operand(Code::kHeaderSize - kHeapObjectTag));  // Code start
  __ AddP(ip, r3, r4);
  __ Jump(ip);
}

void JSEntryStub::Generate(MacroAssembler* masm) {
  // r2: code entry
  // r3: function
  // r4: receiver
  // r5: argc
  // r6: argv

  Label invoke, handler_entry, exit;

  ProfileEntryHookStub::MaybeCallEntryHook(masm);

// saving floating point registers
#if V8_TARGET_ARCH_S390X
  // 64bit ABI requires f8 to f15 be saved
  __ lay(sp, MemOperand(sp, -8 * kDoubleSize));
  __ std(d8, MemOperand(sp));
  __ std(d9, MemOperand(sp, 1 * kDoubleSize));
  __ std(d10, MemOperand(sp, 2 * kDoubleSize));
  __ std(d11, MemOperand(sp, 3 * kDoubleSize));
  __ std(d12, MemOperand(sp, 4 * kDoubleSize));
  __ std(d13, MemOperand(sp, 5 * kDoubleSize));
  __ std(d14, MemOperand(sp, 6 * kDoubleSize));
  __ std(d15, MemOperand(sp, 7 * kDoubleSize));
#else
  // 31bit ABI requires you to store f4 and f6:
  // http://refspecs.linuxbase.org/ELF/zSeries/lzsabi0_s390.html#AEN417
  __ lay(sp, MemOperand(sp, -2 * kDoubleSize));
  __ std(d4, MemOperand(sp));
  __ std(d6, MemOperand(sp, kDoubleSize));
#endif

  // zLinux ABI
  //    Incoming parameters:
  //          r2: code entry
  //          r3: function
  //          r4: receiver
  //          r5: argc
  //          r6: argv
  //    Requires us to save the callee-preserved registers r6-r13
  //    General convention is to also save r14 (return addr) and
  //    sp/r15 as well in a single STM/STMG
  __ lay(sp, MemOperand(sp, -10 * kPointerSize));
  __ StoreMultipleP(r6, sp, MemOperand(sp, 0));

  // Set up the reserved register for 0.0.
  // __ LoadDoubleLiteral(kDoubleRegZero, 0.0, r0);

  // Push a frame with special values setup to mark it as an entry frame.
  //   Bad FP (-1)
  //   SMI Marker
  //   SMI Marker
  //   kCEntryFPAddress
  //   Frame type
  __ lay(sp, MemOperand(sp, -5 * kPointerSize));
  // Push a bad frame pointer to fail if it is used.
  __ LoadImmP(r10, Operand(-1));

  int marker = type();
  __ LoadSmiLiteral(r9, Smi::FromInt(marker));
  __ LoadSmiLiteral(r8, Smi::FromInt(marker));
  // Save copies of the top frame descriptor on the stack.
  __ mov(r7, Operand(ExternalReference(Isolate::kCEntryFPAddress, isolate())));
  __ LoadP(r7, MemOperand(r7));
  __ StoreMultipleP(r7, r10, MemOperand(sp, kPointerSize));
  // Set up frame pointer for the frame to be pushed.
  // Need to add kPointerSize, because sp has one extra
  // frame already for the frame type being pushed later.
  __ lay(fp,
         MemOperand(sp, -EntryFrameConstants::kCallerFPOffset + kPointerSize));

  // If this is the outermost JS call, set js_entry_sp value.
  Label non_outermost_js;
  ExternalReference js_entry_sp(Isolate::kJSEntrySPAddress, isolate());
  __ mov(r7, Operand(ExternalReference(js_entry_sp)));
  __ LoadAndTestP(r8, MemOperand(r7));
  __ bne(&non_outermost_js, Label::kNear);
  __ StoreP(fp, MemOperand(r7));
  __ LoadSmiLiteral(ip, Smi::FromInt(StackFrame::OUTERMOST_JSENTRY_FRAME));
  Label cont;
  __ b(&cont, Label::kNear);
  __ bind(&non_outermost_js);
  __ LoadSmiLiteral(ip, Smi::FromInt(StackFrame::INNER_JSENTRY_FRAME));

  __ bind(&cont);
  __ StoreP(ip, MemOperand(sp));  // frame-type

  // Jump to a faked try block that does the invoke, with a faked catch
  // block that sets the pending exception.
  __ b(&invoke, Label::kNear);

  __ bind(&handler_entry);
  handler_offset_ = handler_entry.pos();
  // Caught exception: Store result (exception) in the pending exception
  // field in the JSEnv and return a failure sentinel.  Coming in here the
  // fp will be invalid because the PushStackHandler below sets it to 0 to
  // signal the existence of the JSEntry frame.
  __ mov(ip, Operand(ExternalReference(Isolate::kPendingExceptionAddress,
                                       isolate())));

  __ StoreP(r2, MemOperand(ip));
  __ LoadRoot(r2, Heap::kExceptionRootIndex);
  __ b(&exit, Label::kNear);

  // Invoke: Link this frame into the handler chain.
  __ bind(&invoke);
  // Must preserve r2-r6.
  __ PushStackHandler();
  // If an exception not caught by another handler occurs, this handler
  // returns control to the code after the b(&invoke) above, which
  // restores all kCalleeSaved registers (including cp and fp) to their
  // saved values before returning a failure to C.

  // Clear any pending exceptions.
  __ mov(ip, Operand(ExternalReference(Isolate::kPendingExceptionAddress,
                                       isolate())));
  __ mov(r7, Operand(isolate()->factory()->the_hole_value()));
  __ StoreP(r7, MemOperand(ip));

  // Invoke the function by calling through JS entry trampoline builtin.
  // Notice that we cannot store a reference to the trampoline code directly in
  // this stub, because runtime stubs are not traversed when doing GC.

  // Expected registers by Builtins::JSEntryTrampoline
  // r2: code entry
  // r3: function
  // r4: receiver
  // r5: argc
  // r6: argv
  if (type() == StackFrame::ENTRY_CONSTRUCT) {
    ExternalReference construct_entry(Builtins::kJSConstructEntryTrampoline,
                                      isolate());
    __ mov(ip, Operand(construct_entry));
  } else {
    ExternalReference entry(Builtins::kJSEntryTrampoline, isolate());
    __ mov(ip, Operand(entry));
  }
  __ LoadP(ip, MemOperand(ip));  // deref address

  // Branch and link to JSEntryTrampoline.
  // the address points to the start of the code object, skip the header
  __ AddP(ip, Operand(Code::kHeaderSize - kHeapObjectTag));
  Label return_addr;
  // __ basr(r14, ip);
  __ larl(r14, &return_addr);
  __ b(ip);
  __ bind(&return_addr);

  // Unlink this frame from the handler chain.
  __ PopStackHandler();

  __ bind(&exit);  // r2 holds result
  // Check if the current stack frame is marked as the outermost JS frame.
  Label non_outermost_js_2;
  __ pop(r7);
  __ CmpSmiLiteral(r7, Smi::FromInt(StackFrame::OUTERMOST_JSENTRY_FRAME), r0);
  __ bne(&non_outermost_js_2, Label::kNear);
  __ mov(r8, Operand::Zero());
  __ mov(r7, Operand(ExternalReference(js_entry_sp)));
  __ StoreP(r8, MemOperand(r7));
  __ bind(&non_outermost_js_2);

  // Restore the top frame descriptors from the stack.
  __ pop(r5);
  __ mov(ip, Operand(ExternalReference(Isolate::kCEntryFPAddress, isolate())));
  __ StoreP(r5, MemOperand(ip));

  // Reset the stack to the callee saved registers.
  __ lay(sp, MemOperand(sp, -EntryFrameConstants::kCallerFPOffset));

  // Reload callee-saved preserved regs, return address reg (r14) and sp
  __ LoadMultipleP(r6, sp, MemOperand(sp, 0));
  __ la(sp, MemOperand(sp, 10 * kPointerSize));

// saving floating point registers
#if V8_TARGET_ARCH_S390X
  // 64bit ABI requires f8 to f15 be saved
  __ ld(d8, MemOperand(sp));
  __ ld(d9, MemOperand(sp, 1 * kDoubleSize));
  __ ld(d10, MemOperand(sp, 2 * kDoubleSize));
  __ ld(d11, MemOperand(sp, 3 * kDoubleSize));
  __ ld(d12, MemOperand(sp, 4 * kDoubleSize));
  __ ld(d13, MemOperand(sp, 5 * kDoubleSize));
  __ ld(d14, MemOperand(sp, 6 * kDoubleSize));
  __ ld(d15, MemOperand(sp, 7 * kDoubleSize));
  __ la(sp, MemOperand(sp, 8 * kDoubleSize));
#else
  // 31bit ABI requires you to store f4 and f6:
  // http://refspecs.linuxbase.org/ELF/zSeries/lzsabi0_s390.html#AEN417
  __ ld(d4, MemOperand(sp));
  __ ld(d6, MemOperand(sp, kDoubleSize));
  __ la(sp, MemOperand(sp, 2 * kDoubleSize));
#endif

  __ b(r14);
}

void InstanceOfStub::Generate(MacroAssembler* masm) {
  Register const object = r3;              // Object (lhs).
  Register const function = r2;            // Function (rhs).
  Register const object_map = r4;          // Map of {object}.
  Register const function_map = r5;        // Map of {function}.
  Register const function_prototype = r6;  // Prototype of {function}.
  Register const scratch = r7;

  DCHECK(object.is(InstanceOfDescriptor::LeftRegister()));
  DCHECK(function.is(InstanceOfDescriptor::RightRegister()));

  // Check if {object} is a smi.
  Label object_is_smi;
  __ JumpIfSmi(object, &object_is_smi);

  // Lookup the {function} and the {object} map in the global instanceof cache.
  // Note: This is safe because we clear the global instanceof cache whenever
  // we change the prototype of any object.
  Label fast_case, slow_case;
  __ LoadP(object_map, FieldMemOperand(object, HeapObject::kMapOffset));
  __ CompareRoot(function, Heap::kInstanceofCacheFunctionRootIndex);
  __ bne(&fast_case);
  __ CompareRoot(object_map, Heap::kInstanceofCacheMapRootIndex);
  __ bne(&fast_case);
  __ LoadRoot(r2, Heap::kInstanceofCacheAnswerRootIndex);
  __ Ret();

  // If {object} is a smi we can safely return false if {function} is a JS
  // function, otherwise we have to miss to the runtime and throw an exception.
  __ bind(&object_is_smi);
  __ JumpIfSmi(function, &slow_case);
  __ CompareObjectType(function, function_map, scratch, JS_FUNCTION_TYPE);
  __ bne(&slow_case);
  __ LoadRoot(r2, Heap::kFalseValueRootIndex);
  __ Ret();

  // Fast-case: The {function} must be a valid JSFunction.
  __ bind(&fast_case);
  __ JumpIfSmi(function, &slow_case);
  __ CompareObjectType(function, function_map, scratch, JS_FUNCTION_TYPE);
  __ bne(&slow_case);

  // Go to the runtime if the function is not a constructor.
  __ LoadlB(scratch, FieldMemOperand(function_map, Map::kBitFieldOffset));
  __ TestBit(scratch, Map::kIsConstructor, r0);
  __ beq(&slow_case);

  // Ensure that {function} has an instance prototype.
  __ TestBit(scratch, Map::kHasNonInstancePrototype, r0);
  __ bne(&slow_case);

  // Get the "prototype" (or initial map) of the {function}.
  __ LoadP(function_prototype,
           FieldMemOperand(function, JSFunction::kPrototypeOrInitialMapOffset));
  __ AssertNotSmi(function_prototype);

  // Resolve the prototype if the {function} has an initial map.  Afterwards the
  // {function_prototype} will be either the JSReceiver prototype object or the
  // hole value, which means that no instances of the {function} were created so
  // far and hence we should return false.
  Label function_prototype_valid;
  __ CompareObjectType(function_prototype, scratch, scratch, MAP_TYPE);
  __ bne(&function_prototype_valid);
  __ LoadP(function_prototype,
           FieldMemOperand(function_prototype, Map::kPrototypeOffset));
  __ bind(&function_prototype_valid);
  __ AssertNotSmi(function_prototype);

  // Update the global instanceof cache with the current {object} map and
  // {function}.  The cached answer will be set when it is known below.
  __ StoreRoot(function, Heap::kInstanceofCacheFunctionRootIndex);
  __ StoreRoot(object_map, Heap::kInstanceofCacheMapRootIndex);

  // Loop through the prototype chain looking for the {function} prototype.
  // Assume true, and change to false if not found.
  Register const object_instance_type = function_map;
  Register const map_bit_field = function_map;
  Register const null = scratch;
  Register const result = r2;

  Label done, loop, fast_runtime_fallback;
  __ LoadRoot(result, Heap::kTrueValueRootIndex);
  __ LoadRoot(null, Heap::kNullValueRootIndex);
  __ bind(&loop);

  // Check if the object needs to be access checked.
  __ LoadlB(map_bit_field, FieldMemOperand(object_map, Map::kBitFieldOffset));
  __ TestBit(map_bit_field, Map::kIsAccessCheckNeeded, r0);
  __ bne(&fast_runtime_fallback);
  // Check if the current object is a Proxy.
  __ CompareInstanceType(object_map, object_instance_type, JS_PROXY_TYPE);
  __ beq(&fast_runtime_fallback);

  __ LoadP(object, FieldMemOperand(object_map, Map::kPrototypeOffset));
  __ CmpP(object, function_prototype);
  __ beq(&done);
  __ CmpP(object, null);
  __ LoadP(object_map, FieldMemOperand(object, HeapObject::kMapOffset));
  __ bne(&loop);
  __ LoadRoot(result, Heap::kFalseValueRootIndex);
  __ bind(&done);
  __ StoreRoot(result, Heap::kInstanceofCacheAnswerRootIndex);
  __ Ret();

  // Found Proxy or access check needed: Call the runtime
  __ bind(&fast_runtime_fallback);
  __ Push(object, function_prototype);
  // Invalidate the instanceof cache.
  __ LoadSmiLiteral(scratch, Smi::FromInt(0));
  __ StoreRoot(scratch, Heap::kInstanceofCacheFunctionRootIndex);
  __ TailCallRuntime(Runtime::kHasInPrototypeChain);

  // Slow-case: Call the %InstanceOf runtime function.
  __ bind(&slow_case);
  __ Push(object, function);
  __ TailCallRuntime(is_es6_instanceof() ? Runtime::kOrdinaryHasInstance
                                         : Runtime::kInstanceOf);
}

void FunctionPrototypeStub::Generate(MacroAssembler* masm) {
  Label miss;
  Register receiver = LoadDescriptor::ReceiverRegister();
  // Ensure that the vector and slot registers won't be clobbered before
  // calling the miss handler.
  DCHECK(!AreAliased(r6, r7, LoadWithVectorDescriptor::VectorRegister(),
                     LoadWithVectorDescriptor::SlotRegister()));

  NamedLoadHandlerCompiler::GenerateLoadFunctionPrototype(masm, receiver, r6,
                                                          r7, &miss);
  __ bind(&miss);
  PropertyAccessCompiler::TailCallBuiltin(
      masm, PropertyAccessCompiler::MissBuiltin(Code::LOAD_IC));
}

void LoadIndexedStringStub::Generate(MacroAssembler* masm) {
  // Return address is in lr.
  Label miss;

  Register receiver = LoadDescriptor::ReceiverRegister();
  Register index = LoadDescriptor::NameRegister();
  Register scratch = r7;
  Register result = r2;
  DCHECK(!scratch.is(receiver) && !scratch.is(index));
  DCHECK(!scratch.is(LoadWithVectorDescriptor::VectorRegister()) &&
         result.is(LoadWithVectorDescriptor::SlotRegister()));

  // StringCharAtGenerator doesn't use the result register until it's passed
  // the different miss possibilities. If it did, we would have a conflict
  // when FLAG_vector_ics is true.
  StringCharAtGenerator char_at_generator(receiver, index, scratch, result,
                                          &miss,  // When not a string.
                                          &miss,  // When not a number.
                                          &miss,  // When index out of range.
                                          STRING_INDEX_IS_ARRAY_INDEX,
                                          RECEIVER_IS_STRING);
  char_at_generator.GenerateFast(masm);
  __ Ret();

  StubRuntimeCallHelper call_helper;
  char_at_generator.GenerateSlow(masm, PART_OF_IC_HANDLER, call_helper);

  __ bind(&miss);
  PropertyAccessCompiler::TailCallBuiltin(
      masm, PropertyAccessCompiler::MissBuiltin(Code::KEYED_LOAD_IC));
}

void RegExpExecStub::Generate(MacroAssembler* masm) {
// Just jump directly to runtime if native RegExp is not selected at compile
// time or if regexp entry in generated code is turned off runtime switch or
// at compilation.
#ifdef V8_INTERPRETED_REGEXP
  __ TailCallRuntime(Runtime::kRegExpExec);
#else   // V8_INTERPRETED_REGEXP

  // Stack frame on entry.
  //  sp[0]: last_match_info (expected JSArray)
  //  sp[4]: previous index
  //  sp[8]: subject string
  //  sp[12]: JSRegExp object

  const int kLastMatchInfoOffset = 0 * kPointerSize;
  const int kPreviousIndexOffset = 1 * kPointerSize;
  const int kSubjectOffset = 2 * kPointerSize;
  const int kJSRegExpOffset = 3 * kPointerSize;

  Label runtime, br_over, encoding_type_UC16;

  // Allocation of registers for this function. These are in callee save
  // registers and will be preserved by the call to the native RegExp code, as
  // this code is called using the normal C calling convention. When calling
  // directly from generated code the native RegExp code will not do a GC and
  // therefore the content of these registers are safe to use after the call.
  Register subject = r6;
  Register regexp_data = r7;
  Register last_match_info_elements = r8;
  Register code = r9;

  __ CleanseP(r14);

  // Ensure register assigments are consistent with callee save masks
  DCHECK(subject.bit() & kCalleeSaved);
  DCHECK(regexp_data.bit() & kCalleeSaved);
  DCHECK(last_match_info_elements.bit() & kCalleeSaved);
  DCHECK(code.bit() & kCalleeSaved);

  // Ensure that a RegExp stack is allocated.
  ExternalReference address_of_regexp_stack_memory_address =
      ExternalReference::address_of_regexp_stack_memory_address(isolate());
  ExternalReference address_of_regexp_stack_memory_size =
      ExternalReference::address_of_regexp_stack_memory_size(isolate());
  __ mov(r2, Operand(address_of_regexp_stack_memory_size));
  __ LoadAndTestP(r2, MemOperand(r2));
  __ beq(&runtime);

  // Check that the first argument is a JSRegExp object.
  __ LoadP(r2, MemOperand(sp, kJSRegExpOffset));
  __ JumpIfSmi(r2, &runtime);
  __ CompareObjectType(r2, r3, r3, JS_REGEXP_TYPE);
  __ bne(&runtime);

  // Check that the RegExp has been compiled (data contains a fixed array).
  __ LoadP(regexp_data, FieldMemOperand(r2, JSRegExp::kDataOffset));
  if (FLAG_debug_code) {
    __ TestIfSmi(regexp_data);
    __ Check(ne, kUnexpectedTypeForRegExpDataFixedArrayExpected, cr0);
    __ CompareObjectType(regexp_data, r2, r2, FIXED_ARRAY_TYPE);
    __ Check(eq, kUnexpectedTypeForRegExpDataFixedArrayExpected);
  }

  // regexp_data: RegExp data (FixedArray)
  // Check the type of the RegExp. Only continue if type is JSRegExp::IRREGEXP.
  __ LoadP(r2, FieldMemOperand(regexp_data, JSRegExp::kDataTagOffset));
  // DCHECK(Smi::FromInt(JSRegExp::IRREGEXP) < (char *)0xffffu);
  __ CmpSmiLiteral(r2, Smi::FromInt(JSRegExp::IRREGEXP), r0);
  __ bne(&runtime);

  // regexp_data: RegExp data (FixedArray)
  // Check that the number of captures fit in the static offsets vector buffer.
  __ LoadP(r4,
           FieldMemOperand(regexp_data, JSRegExp::kIrregexpCaptureCountOffset));
  // Check (number_of_captures + 1) * 2 <= offsets vector size
  // Or          number_of_captures * 2 <= offsets vector size - 2
  // SmiToShortArrayOffset accomplishes the multiplication by 2 and
  // SmiUntag (which is a nop for 32-bit).
  __ SmiToShortArrayOffset(r4, r4);
  STATIC_ASSERT(Isolate::kJSRegexpStaticOffsetsVectorSize >= 2);
  __ CmpLogicalP(r4, Operand(Isolate::kJSRegexpStaticOffsetsVectorSize - 2));
  __ bgt(&runtime);

  // Reset offset for possibly sliced string.
  __ LoadImmP(ip, Operand::Zero());
  __ LoadP(subject, MemOperand(sp, kSubjectOffset));
  __ JumpIfSmi(subject, &runtime);
  __ LoadRR(r5, subject);  // Make a copy of the original subject string.
  // subject: subject string
  // r5: subject string
  // regexp_data: RegExp data (FixedArray)
  // Handle subject string according to its encoding and representation:
  // (1) Sequential string?  If yes, go to (4).
  // (2) Sequential or cons?  If not, go to (5).
  // (3) Cons string.  If the string is flat, replace subject with first string
  //     and go to (1). Otherwise bail out to runtime.
  // (4) Sequential string.  Load regexp code according to encoding.
  // (E) Carry on.
  /// [...]

  // Deferred code at the end of the stub:
  // (5) Long external string?  If not, go to (7).
  // (6) External string.  Make it, offset-wise, look like a sequential string.
  //     Go to (4).
  // (7) Short external string or not a string?  If yes, bail out to runtime.
  // (8) Sliced string.  Replace subject with parent.  Go to (1).

  Label seq_string /* 4 */, external_string /* 6 */, check_underlying /* 1 */,
      not_seq_nor_cons /* 5 */, not_long_external /* 7 */;

  __ bind(&check_underlying);
  __ LoadP(r2, FieldMemOperand(subject, HeapObject::kMapOffset));
  __ LoadlB(r2, FieldMemOperand(r2, Map::kInstanceTypeOffset));

  // (1) Sequential string?  If yes, go to (4).

  STATIC_ASSERT((kIsNotStringMask | kStringRepresentationMask |
                 kShortExternalStringMask) == 0x93);
  __ mov(r3, Operand(kIsNotStringMask | kStringRepresentationMask |
                     kShortExternalStringMask));
  __ AndP(r3, r2);
  STATIC_ASSERT((kStringTag | kSeqStringTag) == 0);
  __ beq(&seq_string, Label::kNear);  // Go to (4).

  // (2) Sequential or cons? If not, go to (5).
  STATIC_ASSERT(kConsStringTag < kExternalStringTag);
  STATIC_ASSERT(kSlicedStringTag > kExternalStringTag);
  STATIC_ASSERT(kIsNotStringMask > kExternalStringTag);
  STATIC_ASSERT(kShortExternalStringTag > kExternalStringTag);
  STATIC_ASSERT(kExternalStringTag < 0xffffu);
  __ CmpP(r3, Operand(kExternalStringTag));
  __ bge(&not_seq_nor_cons);  // Go to (5).

  // (3) Cons string.  Check that it's flat.
  // Replace subject with first string and reload instance type.
  __ LoadP(r2, FieldMemOperand(subject, ConsString::kSecondOffset));
  __ CompareRoot(r2, Heap::kempty_stringRootIndex);
  __ bne(&runtime);
  __ LoadP(subject, FieldMemOperand(subject, ConsString::kFirstOffset));
  __ b(&check_underlying);

  // (4) Sequential string.  Load regexp code according to encoding.
  __ bind(&seq_string);
  // subject: sequential subject string (or look-alike, external string)
  // r5: original subject string
  // Load previous index and check range before r5 is overwritten.  We have to
  // use r5 instead of subject here because subject might have been only made
  // to look like a sequential string when it actually is an external string.
  __ LoadP(r3, MemOperand(sp, kPreviousIndexOffset));
  __ JumpIfNotSmi(r3, &runtime);
  __ LoadP(r5, FieldMemOperand(r5, String::kLengthOffset));
  __ CmpLogicalP(r5, r3);
  __ ble(&runtime);
  __ SmiUntag(r3);

  STATIC_ASSERT(4 == kOneByteStringTag);
  STATIC_ASSERT(kTwoByteStringTag == 0);
  STATIC_ASSERT(kStringEncodingMask == 4);
  __ ExtractBitMask(r5, r2, kStringEncodingMask, SetRC);
  __ beq(&encoding_type_UC16, Label::kNear);
  __ LoadP(code,
           FieldMemOperand(regexp_data, JSRegExp::kDataOneByteCodeOffset));
  __ b(&br_over, Label::kNear);
  __ bind(&encoding_type_UC16);
  __ LoadP(code, FieldMemOperand(regexp_data, JSRegExp::kDataUC16CodeOffset));
  __ bind(&br_over);

  // (E) Carry on.  String handling is done.
  // code: irregexp code
  // Check that the irregexp code has been generated for the actual string
  // encoding. If it has, the field contains a code object otherwise it contains
  // a smi (code flushing support).
  __ JumpIfSmi(code, &runtime);

  // r3: previous index
  // r5: encoding of subject string (1 if one_byte, 0 if two_byte);
  // code: Address of generated regexp code
  // subject: Subject string
  // regexp_data: RegExp data (FixedArray)
  // All checks done. Now push arguments for native regexp code.
  __ IncrementCounter(isolate()->counters()->regexp_entry_native(), 1, r2, r4);

  // Isolates: note we add an additional parameter here (isolate pointer).
  const int kRegExpExecuteArguments = 10;
  const int kParameterRegisters = 5;
  __ EnterExitFrame(false, kRegExpExecuteArguments - kParameterRegisters);

  // Stack pointer now points to cell where return address is to be written.
  // Arguments are before that on the stack or in registers.

  // Argument 10 (in stack parameter area): Pass current isolate address.
  __ mov(r2, Operand(ExternalReference::isolate_address(isolate())));
  __ StoreP(r2, MemOperand(sp, kStackFrameExtraParamSlot * kPointerSize +
                                   4 * kPointerSize));

  // Argument 9 is a dummy that reserves the space used for
  // the return address added by the ExitFrame in native calls.
  __ mov(r2, Operand::Zero());
  __ StoreP(r2, MemOperand(sp, kStackFrameExtraParamSlot * kPointerSize +
                                   3 * kPointerSize));

  // Argument 8: Indicate that this is a direct call from JavaScript.
  __ mov(r2, Operand(1));
  __ StoreP(r2, MemOperand(sp, kStackFrameExtraParamSlot * kPointerSize +
                                   2 * kPointerSize));

  // Argument 7: Start (high end) of backtracking stack memory area.
  __ mov(r2, Operand(address_of_regexp_stack_memory_address));
  __ LoadP(r2, MemOperand(r2, 0));
  __ mov(r1, Operand(address_of_regexp_stack_memory_size));
  __ LoadP(r1, MemOperand(r1, 0));
  __ AddP(r2, r1);
  __ StoreP(r2, MemOperand(sp, kStackFrameExtraParamSlot * kPointerSize +
                                   1 * kPointerSize));

  // Argument 6: Set the number of capture registers to zero to force
  // global egexps to behave as non-global.  This does not affect non-global
  // regexps.
  __ mov(r2, Operand::Zero());
  __ StoreP(r2, MemOperand(sp, kStackFrameExtraParamSlot * kPointerSize +
                                   0 * kPointerSize));

  // Argument 1 (r2): Subject string.
  // Load the length from the original subject string from the previous stack
  // frame. Therefore we have to use fp, which points exactly to 15 pointer
  // sizes below the previous sp. (Because creating a new stack frame pushes
  // the previous fp onto the stack and moves up sp by 2 * kPointerSize and
  // 13 registers saved on the stack previously)
  __ LoadP(r2, MemOperand(fp, kSubjectOffset + 2 * kPointerSize));

  // Argument 2 (r3): Previous index.
  // Already there
  __ AddP(r1, subject, Operand(SeqString::kHeaderSize - kHeapObjectTag));

  // Argument 5 (r6): static offsets vector buffer.
  __ mov(
      r6,
      Operand(ExternalReference::address_of_static_offsets_vector(isolate())));

  // For arguments 4 (r5) and 3 (r4) get string length, calculate start of data
  // and calculate the shift of the index (0 for one-byte and 1 for two byte).
  __ XorP(r5, Operand(1));
  // If slice offset is not 0, load the length from the original sliced string.
  // Argument 3, r4: Start of string data
  // Prepare start and end index of the input.
  __ ShiftLeftP(ip, ip, r5);
  __ AddP(ip, r1, ip);
  __ ShiftLeftP(r4, r3, r5);
  __ AddP(r4, ip, r4);

  // Argument 4, r5: End of string data
  __ LoadP(r1, FieldMemOperand(r2, String::kLengthOffset));
  __ SmiUntag(r1);
  __ ShiftLeftP(r0, r1, r5);
  __ AddP(r5, ip, r0);

  // Locate the code entry and call it.
  __ AddP(code, Operand(Code::kHeaderSize - kHeapObjectTag));

  DirectCEntryStub stub(isolate());
  stub.GenerateCall(masm, code);

  __ LeaveExitFrame(false, no_reg, true);

  // r2: result (int32)
  // subject: subject string -- needed to reload
  __ LoadP(subject, MemOperand(sp, kSubjectOffset));

  // regexp_data: RegExp data (callee saved)
  // last_match_info_elements: Last match info elements (callee saved)
  // Check the result.
  Label success;
  __ Cmp32(r2, Operand(1));
  // We expect exactly one result since we force the called regexp to behave
  // as non-global.
  __ beq(&success);
  Label failure;
  __ Cmp32(r2, Operand(NativeRegExpMacroAssembler::FAILURE));
  __ beq(&failure);
  __ Cmp32(r2, Operand(NativeRegExpMacroAssembler::EXCEPTION));
  // If not exception it can only be retry. Handle that in the runtime system.
  __ bne(&runtime);
  // Result must now be exception. If there is no pending exception already a
  // stack overflow (on the backtrack stack) was detected in RegExp code but
  // haven't created the exception yet. Handle that in the runtime system.
  // TODO(592): Rerunning the RegExp to get the stack overflow exception.
  __ mov(r3, Operand(isolate()->factory()->the_hole_value()));
  __ mov(r4, Operand(ExternalReference(Isolate::kPendingExceptionAddress,
                                       isolate())));
  __ LoadP(r2, MemOperand(r4, 0));
  __ CmpP(r2, r3);
  __ beq(&runtime);

  // For exception, throw the exception again.
  __ TailCallRuntime(Runtime::kRegExpExecReThrow);

  __ bind(&failure);
  // For failure and exception return null.
  __ mov(r2, Operand(isolate()->factory()->null_value()));
  __ la(sp, MemOperand(sp, (4 * kPointerSize)));
  __ Ret();

  // Process the result from the native regexp code.
  __ bind(&success);
  __ LoadP(r3,
           FieldMemOperand(regexp_data, JSRegExp::kIrregexpCaptureCountOffset));
  // Calculate number of capture registers (number_of_captures + 1) * 2.
  // SmiToShortArrayOffset accomplishes the multiplication by 2 and
  // SmiUntag (which is a nop for 32-bit).
  __ SmiToShortArrayOffset(r3, r3);
  __ AddP(r3, Operand(2));

  __ LoadP(r2, MemOperand(sp, kLastMatchInfoOffset));
  __ JumpIfSmi(r2, &runtime);
  __ CompareObjectType(r2, r4, r4, JS_ARRAY_TYPE);
  __ bne(&runtime);
  // Check that the JSArray is in fast case.
  __ LoadP(last_match_info_elements,
           FieldMemOperand(r2, JSArray::kElementsOffset));
  __ LoadP(r2,
           FieldMemOperand(last_match_info_elements, HeapObject::kMapOffset));
  __ CompareRoot(r2, Heap::kFixedArrayMapRootIndex);
  __ bne(&runtime);
  // Check that the last match info has space for the capture registers and the
  // additional information.
  __ LoadP(
      r2, FieldMemOperand(last_match_info_elements, FixedArray::kLengthOffset));
  __ AddP(r4, r3, Operand(RegExpImpl::kLastMatchOverhead));
  __ SmiUntag(r0, r2);
  __ CmpP(r4, r0);
  __ bgt(&runtime);

  // r3: number of capture registers
  // subject: subject string
  // Store the capture count.
  __ SmiTag(r4, r3);
  __ StoreP(r4, FieldMemOperand(last_match_info_elements,
                                RegExpImpl::kLastCaptureCountOffset));
  // Store last subject and last input.
  __ StoreP(subject, FieldMemOperand(last_match_info_elements,
                                     RegExpImpl::kLastSubjectOffset));
  __ LoadRR(r4, subject);
  __ RecordWriteField(last_match_info_elements, RegExpImpl::kLastSubjectOffset,
                      subject, r9, kLRHasNotBeenSaved, kDontSaveFPRegs);
  __ LoadRR(subject, r4);
  __ StoreP(subject, FieldMemOperand(last_match_info_elements,
                                     RegExpImpl::kLastInputOffset));
  __ RecordWriteField(last_match_info_elements, RegExpImpl::kLastInputOffset,
                      subject, r9, kLRHasNotBeenSaved, kDontSaveFPRegs);

  // Get the static offsets vector filled by the native regexp code.
  ExternalReference address_of_static_offsets_vector =
      ExternalReference::address_of_static_offsets_vector(isolate());
  __ mov(r4, Operand(address_of_static_offsets_vector));

  // r3: number of capture registers
  // r4: offsets vector
  Label next_capture;
  // Capture register counter starts from number of capture registers and
  // counts down until wraping after zero.
  __ AddP(
      r2, last_match_info_elements,
      Operand(RegExpImpl::kFirstCaptureOffset - kHeapObjectTag - kPointerSize));
  __ AddP(r4, Operand(-kIntSize));  // bias down for lwzu
  __ bind(&next_capture);
  // Read the value from the static offsets vector buffer.
  __ ly(r5, MemOperand(r4, kIntSize));
  __ lay(r4, MemOperand(r4, kIntSize));
  // Store the smi value in the last match info.
  __ SmiTag(r5);
  __ StoreP(r5, MemOperand(r2, kPointerSize));
  __ lay(r2, MemOperand(r2, kPointerSize));
  __ BranchOnCount(r3, &next_capture);

  // Return last match info.
  __ LoadP(r2, MemOperand(sp, kLastMatchInfoOffset));
  __ la(sp, MemOperand(sp, (4 * kPointerSize)));
  __ Ret();

  // Do the runtime call to execute the regexp.
  __ bind(&runtime);
  __ TailCallRuntime(Runtime::kRegExpExec);

  // Deferred code for string handling.
  // (5) Long external string? If not, go to (7).
  __ bind(&not_seq_nor_cons);
  // Compare flags are still set.
  __ bgt(&not_long_external, Label::kNear);  // Go to (7).

  // (6) External string.  Make it, offset-wise, look like a sequential string.
  __ bind(&external_string);
  __ LoadP(r2, FieldMemOperand(subject, HeapObject::kMapOffset));
  __ LoadlB(r2, FieldMemOperand(r2, Map::kInstanceTypeOffset));
  if (FLAG_debug_code) {
    // Assert that we do not have a cons or slice (indirect strings) here.
    // Sequential strings have already been ruled out.
    STATIC_ASSERT(kIsIndirectStringMask == 1);
    __ tmll(r2, Operand(kIsIndirectStringMask));
    __ Assert(eq, kExternalStringExpectedButNotFound, cr0);
  }
  __ LoadP(subject,
           FieldMemOperand(subject, ExternalString::kResourceDataOffset));
  // Move the pointer so that offset-wise, it looks like a sequential string.
  STATIC_ASSERT(SeqTwoByteString::kHeaderSize == SeqOneByteString::kHeaderSize);
  __ SubP(subject, subject,
          Operand(SeqTwoByteString::kHeaderSize - kHeapObjectTag));
  __ b(&seq_string);  // Go to (4).

  // (7) Short external string or not a string?  If yes, bail out to runtime.
  __ bind(&not_long_external);
  STATIC_ASSERT(kNotStringTag != 0 && kShortExternalStringTag != 0);
  __ mov(r0, Operand(kIsNotStringMask | kShortExternalStringMask));
  __ AndP(r0, r3);
  __ bne(&runtime);

  // (8) Sliced string.  Replace subject with parent.  Go to (4).
  // Load offset into ip and replace subject string with parent.
  __ LoadP(ip, FieldMemOperand(subject, SlicedString::kOffsetOffset));
  __ SmiUntag(ip);
  __ LoadP(subject, FieldMemOperand(subject, SlicedString::kParentOffset));
  __ b(&check_underlying);  // Go to (4).
#endif  // V8_INTERPRETED_REGEXP
}

static void CallStubInRecordCallTarget(MacroAssembler* masm, CodeStub* stub) {
  // r2 : number of arguments to the construct function
  // r3 : the function to call
  // r4 : feedback vector
  // r5 : slot in feedback vector (Smi)
  FrameScope scope(masm, StackFrame::INTERNAL);

  // Number-of-arguments register must be smi-tagged to call out.
  __ SmiTag(r2);
  __ Push(r5, r4, r3, r2);

  __ CallStub(stub);

  __ Pop(r5, r4, r3, r2);
  __ SmiUntag(r2);
}

static void GenerateRecordCallTarget(MacroAssembler* masm) {
  // Cache the called function in a feedback vector slot.  Cache states
  // are uninitialized, monomorphic (indicated by a JSFunction), and
  // megamorphic.
  // r2 : number of arguments to the construct function
  // r3 : the function to call
  // r4 : feedback vector
  // r5 : slot in feedback vector (Smi)
  Label initialize, done, miss, megamorphic, not_array_function;

  DCHECK_EQ(*TypeFeedbackVector::MegamorphicSentinel(masm->isolate()),
            masm->isolate()->heap()->megamorphic_symbol());
  DCHECK_EQ(*TypeFeedbackVector::UninitializedSentinel(masm->isolate()),
            masm->isolate()->heap()->uninitialized_symbol());

  // Load the cache state into r7.
  __ SmiToPtrArrayOffset(r7, r5);
  __ AddP(r7, r4, r7);
  __ LoadP(r7, FieldMemOperand(r7, FixedArray::kHeaderSize));

  // A monomorphic cache hit or an already megamorphic state: invoke the
  // function without changing the state.
  // We don't know if r7 is a WeakCell or a Symbol, but it's harmless to read at
  // this position in a symbol (see static asserts in type-feedback-vector.h).
  Label check_allocation_site;
  Register feedback_map = r8;
  Register weak_value = r9;
  __ LoadP(weak_value, FieldMemOperand(r7, WeakCell::kValueOffset));
  __ CmpP(r3, weak_value);
  __ beq(&done);
  __ CompareRoot(r7, Heap::kmegamorphic_symbolRootIndex);
  __ beq(&done);
  __ LoadP(feedback_map, FieldMemOperand(r7, HeapObject::kMapOffset));
  __ CompareRoot(feedback_map, Heap::kWeakCellMapRootIndex);
  __ bne(&check_allocation_site);

  // If the weak cell is cleared, we have a new chance to become monomorphic.
  __ JumpIfSmi(weak_value, &initialize);
  __ b(&megamorphic);

  __ bind(&check_allocation_site);
  // If we came here, we need to see if we are the array function.
  // If we didn't have a matching function, and we didn't find the megamorph
  // sentinel, then we have in the slot either some other function or an
  // AllocationSite.
  __ CompareRoot(feedback_map, Heap::kAllocationSiteMapRootIndex);
  __ bne(&miss);

  // Make sure the function is the Array() function
  __ LoadNativeContextSlot(Context::ARRAY_FUNCTION_INDEX, r7);
  __ CmpP(r3, r7);
  __ bne(&megamorphic);
  __ b(&done);

  __ bind(&miss);

  // A monomorphic miss (i.e, here the cache is not uninitialized) goes
  // megamorphic.
  __ CompareRoot(r7, Heap::kuninitialized_symbolRootIndex);
  __ beq(&initialize);
  // MegamorphicSentinel is an immortal immovable object (undefined) so no
  // write-barrier is needed.
  __ bind(&megamorphic);
  __ SmiToPtrArrayOffset(r7, r5);
  __ AddP(r7, r4, r7);
  __ LoadRoot(ip, Heap::kmegamorphic_symbolRootIndex);
  __ StoreP(ip, FieldMemOperand(r7, FixedArray::kHeaderSize), r0);
  __ jmp(&done);

  // An uninitialized cache is patched with the function
  __ bind(&initialize);

  // Make sure the function is the Array() function.
  __ LoadNativeContextSlot(Context::ARRAY_FUNCTION_INDEX, r7);
  __ CmpP(r3, r7);
  __ bne(&not_array_function);

  // The target function is the Array constructor,
  // Create an AllocationSite if we don't already have it, store it in the
  // slot.
  CreateAllocationSiteStub create_stub(masm->isolate());
  CallStubInRecordCallTarget(masm, &create_stub);
  __ b(&done);

  __ bind(&not_array_function);

  CreateWeakCellStub weak_cell_stub(masm->isolate());
  CallStubInRecordCallTarget(masm, &weak_cell_stub);
  __ bind(&done);
}

void CallConstructStub::Generate(MacroAssembler* masm) {
  // r2 : number of arguments
  // r3 : the function to call
  // r4 : feedback vector
  // r5 : slot in feedback vector (Smi, for RecordCallTarget)

  Label non_function;
  // Check that the function is not a smi.
  __ JumpIfSmi(r3, &non_function);
  // Check that the function is a JSFunction.
  __ CompareObjectType(r3, r7, r7, JS_FUNCTION_TYPE);
  __ bne(&non_function);

  GenerateRecordCallTarget(masm);

  __ SmiToPtrArrayOffset(r7, r5);
  __ AddP(r7, r4, r7);
  // Put the AllocationSite from the feedback vector into r4, or undefined.
  __ LoadP(r4, FieldMemOperand(r7, FixedArray::kHeaderSize));
  __ LoadP(r7, FieldMemOperand(r4, AllocationSite::kMapOffset));
  __ CompareRoot(r7, Heap::kAllocationSiteMapRootIndex);
  Label feedback_register_initialized;
  __ beq(&feedback_register_initialized);
  __ LoadRoot(r4, Heap::kUndefinedValueRootIndex);
  __ bind(&feedback_register_initialized);

  __ AssertUndefinedOrAllocationSite(r4, r7);

  // Pass function as new target.
  __ LoadRR(r5, r3);

  // Tail call to the function-specific construct stub (still in the caller
  // context at this point).
  __ LoadP(r6, FieldMemOperand(r3, JSFunction::kSharedFunctionInfoOffset));
  __ LoadP(r6, FieldMemOperand(r6, SharedFunctionInfo::kConstructStubOffset));
  __ AddP(ip, r6, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ JumpToJSEntry(ip);

  __ bind(&non_function);
  __ LoadRR(r5, r3);
  __ Jump(isolate()->builtins()->Construct(), RelocInfo::CODE_TARGET);
}

void CallICStub::HandleArrayCase(MacroAssembler* masm, Label* miss) {
  // r3 - function
  // r5 - slot id
  // r4 - vector
  // r6 - allocation site (loaded from vector[slot])
  __ LoadNativeContextSlot(Context::ARRAY_FUNCTION_INDEX, r7);
  __ CmpP(r3, r7);
  __ bne(miss);

  __ mov(r2, Operand(arg_count()));

  // Increment the call count for monomorphic function calls.
  const int count_offset = FixedArray::kHeaderSize + kPointerSize;
  __ SmiToPtrArrayOffset(r7, r5);
  __ AddP(r4, r4, r7);
  __ LoadP(r5, FieldMemOperand(r4, count_offset));
  __ AddSmiLiteral(r5, r5, Smi::FromInt(CallICNexus::kCallCountIncrement), r0);
  __ StoreP(r5, FieldMemOperand(r4, count_offset), r0);

  __ LoadRR(r4, r6);
  __ LoadRR(r5, r3);
  ArrayConstructorStub stub(masm->isolate(), arg_count());
  __ TailCallStub(&stub);
}

void CallICStub::Generate(MacroAssembler* masm) {
  // r3 - function
  // r5 - slot id (Smi)
  // r4 - vector
  Label extra_checks_or_miss, call, call_function;
  int argc = arg_count();
  ParameterCount actual(argc);

  // The checks. First, does r3 match the recorded monomorphic target?
  __ SmiToPtrArrayOffset(r8, r5);
  __ AddP(r8, r4, r8);
  __ LoadP(r6, FieldMemOperand(r8, FixedArray::kHeaderSize));

  // We don't know that we have a weak cell. We might have a private symbol
  // or an AllocationSite, but the memory is safe to examine.
  // AllocationSite::kTransitionInfoOffset - contains a Smi or pointer to
  // FixedArray.
  // WeakCell::kValueOffset - contains a JSFunction or Smi(0)
  // Symbol::kHashFieldSlot - if the low bit is 1, then the hash is not
  // computed, meaning that it can't appear to be a pointer. If the low bit is
  // 0, then hash is computed, but the 0 bit prevents the field from appearing
  // to be a pointer.
  STATIC_ASSERT(WeakCell::kSize >= kPointerSize);
  STATIC_ASSERT(AllocationSite::kTransitionInfoOffset ==
                    WeakCell::kValueOffset &&
                WeakCell::kValueOffset == Symbol::kHashFieldSlot);

  __ LoadP(r7, FieldMemOperand(r6, WeakCell::kValueOffset));
  __ CmpP(r3, r7);
  __ bne(&extra_checks_or_miss, Label::kNear);

  // The compare above could have been a SMI/SMI comparison. Guard against this
  // convincing us that we have a monomorphic JSFunction.
  __ JumpIfSmi(r3, &extra_checks_or_miss);

  // Increment the call count for monomorphic function calls.
  const int count_offset = FixedArray::kHeaderSize + kPointerSize;
  __ LoadP(r5, FieldMemOperand(r8, count_offset));
  __ AddSmiLiteral(r5, r5, Smi::FromInt(CallICNexus::kCallCountIncrement), r0);
  __ StoreP(r5, FieldMemOperand(r8, count_offset), r0);

  __ bind(&call_function);
  __ mov(r2, Operand(argc));
  __ Jump(masm->isolate()->builtins()->CallFunction(convert_mode(),
                                                    tail_call_mode()),
          RelocInfo::CODE_TARGET);

  __ bind(&extra_checks_or_miss);
  Label uninitialized, miss, not_allocation_site;

  __ CompareRoot(r6, Heap::kmegamorphic_symbolRootIndex);
  __ beq(&call);

  // Verify that r6 contains an AllocationSite
  __ LoadP(r7, FieldMemOperand(r6, HeapObject::kMapOffset));
  __ CompareRoot(r7, Heap::kAllocationSiteMapRootIndex);
  __ bne(&not_allocation_site);

  // We have an allocation site.
  HandleArrayCase(masm, &miss);

  __ bind(&not_allocation_site);

  // The following cases attempt to handle MISS cases without going to the
  // runtime.
  if (FLAG_trace_ic) {
    __ b(&miss);
  }

  __ CompareRoot(r6, Heap::kuninitialized_symbolRootIndex);
  __ beq(&uninitialized);

  // We are going megamorphic. If the feedback is a JSFunction, it is fine
  // to handle it here. More complex cases are dealt with in the runtime.
  __ AssertNotSmi(r6);
  __ CompareObjectType(r6, r7, r7, JS_FUNCTION_TYPE);
  __ bne(&miss);
  __ LoadRoot(ip, Heap::kmegamorphic_symbolRootIndex);
  __ StoreP(ip, FieldMemOperand(r8, FixedArray::kHeaderSize), r0);

  __ bind(&call);
  __ mov(r2, Operand(argc));
  __ Jump(masm->isolate()->builtins()->Call(convert_mode(), tail_call_mode()),
          RelocInfo::CODE_TARGET);

  __ bind(&uninitialized);

  // We are going monomorphic, provided we actually have a JSFunction.
  __ JumpIfSmi(r3, &miss);

  // Goto miss case if we do not have a function.
  __ CompareObjectType(r3, r6, r6, JS_FUNCTION_TYPE);
  __ bne(&miss);

  // Make sure the function is not the Array() function, which requires special
  // behavior on MISS.
  __ LoadNativeContextSlot(Context::ARRAY_FUNCTION_INDEX, r6);
  __ CmpP(r3, r6);
  __ beq(&miss);

  // Make sure the function belongs to the same native context.
  __ LoadP(r6, FieldMemOperand(r3, JSFunction::kContextOffset));
  __ LoadP(r6, ContextMemOperand(r6, Context::NATIVE_CONTEXT_INDEX));
  __ LoadP(ip, NativeContextMemOperand());
  __ CmpP(r6, ip);
  __ bne(&miss);

  // Initialize the call counter.
  __ LoadSmiLiteral(r7, Smi::FromInt(CallICNexus::kCallCountIncrement));
  __ StoreP(r7, FieldMemOperand(r8, count_offset), r0);

  // Store the function. Use a stub since we need a frame for allocation.
  // r4 - vector
  // r5 - slot
  // r3 - function
  {
    FrameScope scope(masm, StackFrame::INTERNAL);
    CreateWeakCellStub create_stub(masm->isolate());
    __ Push(r3);
    __ CallStub(&create_stub);
    __ Pop(r3);
  }

  __ b(&call_function);

  // We are here because tracing is on or we encountered a MISS case we can't
  // handle here.
  __ bind(&miss);
  GenerateMiss(masm);

  __ b(&call);
}

void CallICStub::GenerateMiss(MacroAssembler* masm) {
  FrameScope scope(masm, StackFrame::INTERNAL);

  // Push the function and feedback info.
  __ Push(r3, r4, r5);

  // Call the entry.
  __ CallRuntime(Runtime::kCallIC_Miss);

  // Move result to r3 and exit the internal frame.
  __ LoadRR(r3, r2);
}

// StringCharCodeAtGenerator
void StringCharCodeAtGenerator::GenerateFast(MacroAssembler* masm) {
  // If the receiver is a smi trigger the non-string case.
  if (check_mode_ == RECEIVER_IS_UNKNOWN) {
    __ JumpIfSmi(object_, receiver_not_string_);

    // Fetch the instance type of the receiver into result register.
    __ LoadP(result_, FieldMemOperand(object_, HeapObject::kMapOffset));
    __ LoadlB(result_, FieldMemOperand(result_, Map::kInstanceTypeOffset));
    // If the receiver is not a string trigger the non-string case.
    __ mov(r0, Operand(kIsNotStringMask));
    __ AndP(r0, result_);
    __ bne(receiver_not_string_);
  }

  // If the index is non-smi trigger the non-smi case.
  __ JumpIfNotSmi(index_, &index_not_smi_);
  __ bind(&got_smi_index_);

  // Check for index out of range.
  __ LoadP(ip, FieldMemOperand(object_, String::kLengthOffset));
  __ CmpLogicalP(ip, index_);
  __ ble(index_out_of_range_);

  __ SmiUntag(index_);

  StringCharLoadGenerator::Generate(masm, object_, index_, result_,
                                    &call_runtime_);

  __ SmiTag(result_);
  __ bind(&exit_);
}

void StringCharCodeAtGenerator::GenerateSlow(
    MacroAssembler* masm, EmbedMode embed_mode,
    const RuntimeCallHelper& call_helper) {
  __ Abort(kUnexpectedFallthroughToCharCodeAtSlowCase);

  // Index is not a smi.
  __ bind(&index_not_smi_);
  // If index is a heap number, try converting it to an integer.
  __ CheckMap(index_, result_, Heap::kHeapNumberMapRootIndex, index_not_number_,
              DONT_DO_SMI_CHECK);
  call_helper.BeforeCall(masm);
  if (embed_mode == PART_OF_IC_HANDLER) {
    __ Push(LoadWithVectorDescriptor::VectorRegister(),
            LoadWithVectorDescriptor::SlotRegister(), object_, index_);
  } else {
    // index_ is consumed by runtime conversion function.
    __ Push(object_, index_);
  }
  if (index_flags_ == STRING_INDEX_IS_NUMBER) {
    __ CallRuntime(Runtime::kNumberToIntegerMapMinusZero);
  } else {
    DCHECK(index_flags_ == STRING_INDEX_IS_ARRAY_INDEX);
    // NumberToSmi discards numbers that are not exact integers.
    __ CallRuntime(Runtime::kNumberToSmi);
  }
  // Save the conversion result before the pop instructions below
  // have a chance to overwrite it.
  __ Move(index_, r2);
  if (embed_mode == PART_OF_IC_HANDLER) {
    __ Pop(LoadWithVectorDescriptor::VectorRegister(),
           LoadWithVectorDescriptor::SlotRegister(), object_);
  } else {
    __ pop(object_);
  }
  // Reload the instance type.
  __ LoadP(result_, FieldMemOperand(object_, HeapObject::kMapOffset));
  __ LoadlB(result_, FieldMemOperand(result_, Map::kInstanceTypeOffset));
  call_helper.AfterCall(masm);
  // If index is still not a smi, it must be out of range.
  __ JumpIfNotSmi(index_, index_out_of_range_);
  // Otherwise, return to the fast path.
  __ b(&got_smi_index_);

  // Call runtime. We get here when the receiver is a string and the
  // index is a number, but the code of getting the actual character
  // is too complex (e.g., when the string needs to be flattened).
  __ bind(&call_runtime_);
  call_helper.BeforeCall(masm);
  __ SmiTag(index_);
  __ Push(object_, index_);
  __ CallRuntime(Runtime::kStringCharCodeAtRT);
  __ Move(result_, r2);
  call_helper.AfterCall(masm);
  __ b(&exit_);

  __ Abort(kUnexpectedFallthroughFromCharCodeAtSlowCase);
}

// -------------------------------------------------------------------------
// StringCharFromCodeGenerator

void StringCharFromCodeGenerator::GenerateFast(MacroAssembler* masm) {
  // Fast case of Heap::LookupSingleCharacterStringFromCode.
  DCHECK(base::bits::IsPowerOfTwo32(String::kMaxOneByteCharCodeU + 1));
  __ LoadSmiLiteral(r0, Smi::FromInt(~String::kMaxOneByteCharCodeU));
  __ OrP(r0, r0, Operand(kSmiTagMask));
  __ AndP(r0, code_, r0);
  __ bne(&slow_case_);

  __ LoadRoot(result_, Heap::kSingleCharacterStringCacheRootIndex);
  // At this point code register contains smi tagged one-byte char code.
  __ LoadRR(r0, code_);
  __ SmiToPtrArrayOffset(code_, code_);
  __ AddP(result_, code_);
  __ LoadRR(code_, r0);
  __ LoadP(result_, FieldMemOperand(result_, FixedArray::kHeaderSize));
  __ CompareRoot(result_, Heap::kUndefinedValueRootIndex);
  __ beq(&slow_case_);
  __ bind(&exit_);
}

void StringCharFromCodeGenerator::GenerateSlow(
    MacroAssembler* masm, const RuntimeCallHelper& call_helper) {
  __ Abort(kUnexpectedFallthroughToCharFromCodeSlowCase);

  __ bind(&slow_case_);
  call_helper.BeforeCall(masm);
  __ push(code_);
  __ CallRuntime(Runtime::kStringCharFromCode);
  __ Move(result_, r2);
  call_helper.AfterCall(masm);
  __ b(&exit_);

  __ Abort(kUnexpectedFallthroughFromCharFromCodeSlowCase);
}

enum CopyCharactersFlags { COPY_ASCII = 1, DEST_ALWAYS_ALIGNED = 2 };

void StringHelper::GenerateCopyCharacters(MacroAssembler* masm, Register dest,
                                          Register src, Register count,
                                          Register scratch,
                                          String::Encoding encoding) {
  if (FLAG_debug_code) {
    // Check that destination is word aligned.
    __ mov(r0, Operand(kPointerAlignmentMask));
    __ AndP(r0, dest);
    __ Check(eq, kDestinationOfCopyNotAligned, cr0);
  }

  // Nothing to do for zero characters.
  Label done;
  if (encoding == String::TWO_BYTE_ENCODING) {
    // double the length
    __ AddP(count, count, count);
    __ beq(&done, Label::kNear);
  } else {
    __ CmpP(count, Operand::Zero());
    __ beq(&done, Label::kNear);
  }

  // Copy count bytes from src to dst.
  Label byte_loop;
  // TODO(joransiu): Convert into MVC loop
  __ bind(&byte_loop);
  __ LoadlB(scratch, MemOperand(src));
  __ la(src, MemOperand(src, 1));
  __ stc(scratch, MemOperand(dest));
  __ la(dest, MemOperand(dest, 1));
  __ BranchOnCount(count, &byte_loop);

  __ bind(&done);
}

void SubStringStub::Generate(MacroAssembler* masm) {
  Label runtime;

  // Stack frame on entry.
  //  lr: return address
  //  sp[0]: to
  //  sp[4]: from
  //  sp[8]: string

  // This stub is called from the native-call %_SubString(...), so
  // nothing can be assumed about the arguments. It is tested that:
  //  "string" is a sequential string,
  //  both "from" and "to" are smis, and
  //  0 <= from <= to <= string.length.
  // If any of these assumptions fail, we call the runtime system.

  const int kToOffset = 0 * kPointerSize;
  const int kFromOffset = 1 * kPointerSize;
  const int kStringOffset = 2 * kPointerSize;

  __ LoadP(r4, MemOperand(sp, kToOffset));
  __ LoadP(r5, MemOperand(sp, kFromOffset));

  // If either to or from had the smi tag bit set, then fail to generic runtime
  __ JumpIfNotSmi(r4, &runtime);
  __ JumpIfNotSmi(r5, &runtime);
  __ SmiUntag(r4);
  __ SmiUntag(r5);
  // Both r4 and r5 are untagged integers.

  // We want to bailout to runtime here if From is negative.
  __ blt(&runtime);  // From < 0.

  __ CmpLogicalP(r5, r4);
  __ bgt(&runtime);  // Fail if from > to.
  __ SubP(r4, r4, r5);

  // Make sure first argument is a string.
  __ LoadP(r2, MemOperand(sp, kStringOffset));
  __ JumpIfSmi(r2, &runtime);
  Condition is_string = masm->IsObjectStringType(r2, r3);
  __ b(NegateCondition(is_string), &runtime);

  Label single_char;
  __ CmpP(r4, Operand(1));
  __ b(eq, &single_char);

  // Short-cut for the case of trivial substring.
  Label return_r2;
  // r2: original string
  // r4: result string length
  __ LoadP(r6, FieldMemOperand(r2, String::kLengthOffset));
  __ SmiUntag(r0, r6);
  __ CmpLogicalP(r4, r0);
  // Return original string.
  __ beq(&return_r2);
  // Longer than original string's length or negative: unsafe arguments.
  __ bgt(&runtime);
  // Shorter than original string's length: an actual substring.

  // Deal with different string types: update the index if necessary
  // and put the underlying string into r7.
  // r2: original string
  // r3: instance type
  // r4: length
  // r5: from index (untagged)
  Label underlying_unpacked, sliced_string, seq_or_external_string;
  // If the string is not indirect, it can only be sequential or external.
  STATIC_ASSERT(kIsIndirectStringMask == (kSlicedStringTag & kConsStringTag));
  STATIC_ASSERT(kIsIndirectStringMask != 0);
  __ mov(r0, Operand(kIsIndirectStringMask));
  __ AndP(r0, r3);
  __ beq(&seq_or_external_string);

  __ mov(r0, Operand(kSlicedNotConsMask));
  __ AndP(r0, r3);
  __ bne(&sliced_string);
  // Cons string.  Check whether it is flat, then fetch first part.
  __ LoadP(r7, FieldMemOperand(r2, ConsString::kSecondOffset));
  __ CompareRoot(r7, Heap::kempty_stringRootIndex);
  __ bne(&runtime);
  __ LoadP(r7, FieldMemOperand(r2, ConsString::kFirstOffset));
  // Update instance type.
  __ LoadP(r3, FieldMemOperand(r7, HeapObject::kMapOffset));
  __ LoadlB(r3, FieldMemOperand(r3, Map::kInstanceTypeOffset));
  __ b(&underlying_unpacked);

  __ bind(&sliced_string);
  // Sliced string.  Fetch parent and correct start index by offset.
  __ LoadP(r7, FieldMemOperand(r2, SlicedString::kParentOffset));
  __ LoadP(r6, FieldMemOperand(r2, SlicedString::kOffsetOffset));
  __ SmiUntag(r3, r6);
  __ AddP(r5, r3);  // Add offset to index.
  // Update instance type.
  __ LoadP(r3, FieldMemOperand(r7, HeapObject::kMapOffset));
  __ LoadlB(r3, FieldMemOperand(r3, Map::kInstanceTypeOffset));
  __ b(&underlying_unpacked);

  __ bind(&seq_or_external_string);
  // Sequential or external string.  Just move string to the expected register.
  __ LoadRR(r7, r2);

  __ bind(&underlying_unpacked);

  if (FLAG_string_slices) {
    Label copy_routine;
    // r7: underlying subject string
    // r3: instance type of underlying subject string
    // r4: length
    // r5: adjusted start index (untagged)
    __ CmpP(r4, Operand(SlicedString::kMinLength));
    // Short slice.  Copy instead of slicing.
    __ blt(&copy_routine);
    // Allocate new sliced string.  At this point we do not reload the instance
    // type including the string encoding because we simply rely on the info
    // provided by the original string.  It does not matter if the original
    // string's encoding is wrong because we always have to recheck encoding of
    // the newly created string's parent anyways due to externalized strings.
    Label two_byte_slice, set_slice_header;
    STATIC_ASSERT((kStringEncodingMask & kOneByteStringTag) != 0);
    STATIC_ASSERT((kStringEncodingMask & kTwoByteStringTag) == 0);
    __ mov(r0, Operand(kStringEncodingMask));
    __ AndP(r0, r3);
    __ beq(&two_byte_slice);
    __ AllocateOneByteSlicedString(r2, r4, r8, r9, &runtime);
    __ b(&set_slice_header);
    __ bind(&two_byte_slice);
    __ AllocateTwoByteSlicedString(r2, r4, r8, r9, &runtime);
    __ bind(&set_slice_header);
    __ SmiTag(r5);
    __ StoreP(r7, FieldMemOperand(r2, SlicedString::kParentOffset));
    __ StoreP(r5, FieldMemOperand(r2, SlicedString::kOffsetOffset));
    __ b(&return_r2);

    __ bind(&copy_routine);
  }

  // r7: underlying subject string
  // r3: instance type of underlying subject string
  // r4: length
  // r5: adjusted start index (untagged)
  Label two_byte_sequential, sequential_string, allocate_result;
  STATIC_ASSERT(kExternalStringTag != 0);
  STATIC_ASSERT(kSeqStringTag == 0);
  __ mov(r0, Operand(kExternalStringTag));
  __ AndP(r0, r3);
  __ beq(&sequential_string);

  // Handle external string.
  // Rule out short external strings.
  STATIC_ASSERT(kShortExternalStringTag != 0);
  __ mov(r0, Operand(kShortExternalStringTag));
  __ AndP(r0, r3);
  __ bne(&runtime);
  __ LoadP(r7, FieldMemOperand(r7, ExternalString::kResourceDataOffset));
  // r7 already points to the first character of underlying string.
  __ b(&allocate_result);

  __ bind(&sequential_string);
  // Locate first character of underlying subject string.
  STATIC_ASSERT(SeqTwoByteString::kHeaderSize == SeqOneByteString::kHeaderSize);
  __ AddP(r7, Operand(SeqOneByteString::kHeaderSize - kHeapObjectTag));

  __ bind(&allocate_result);
  // Sequential acii string.  Allocate the result.
  STATIC_ASSERT((kOneByteStringTag & kStringEncodingMask) != 0);
  __ mov(r0, Operand(kStringEncodingMask));
  __ AndP(r0, r3);
  __ beq(&two_byte_sequential);

  // Allocate and copy the resulting one-byte string.
  __ AllocateOneByteString(r2, r4, r6, r8, r9, &runtime);

  // Locate first character of substring to copy.
  __ AddP(r7, r5);
  // Locate first character of result.
  __ AddP(r3, r2, Operand(SeqOneByteString::kHeaderSize - kHeapObjectTag));

  // r2: result string
  // r3: first character of result string
  // r4: result string length
  // r7: first character of substring to copy
  STATIC_ASSERT((SeqOneByteString::kHeaderSize & kObjectAlignmentMask) == 0);
  StringHelper::GenerateCopyCharacters(masm, r3, r7, r4, r5,
                                       String::ONE_BYTE_ENCODING);
  __ b(&return_r2);

  // Allocate and copy the resulting two-byte string.
  __ bind(&two_byte_sequential);
  __ AllocateTwoByteString(r2, r4, r6, r8, r9, &runtime);

  // Locate first character of substring to copy.
  __ ShiftLeftP(r3, r5, Operand(1));
  __ AddP(r7, r3);
  // Locate first character of result.
  __ AddP(r3, r2, Operand(SeqTwoByteString::kHeaderSize - kHeapObjectTag));

  // r2: result string.
  // r3: first character of result.
  // r4: result length.
  // r7: first character of substring to copy.
  STATIC_ASSERT((SeqTwoByteString::kHeaderSize & kObjectAlignmentMask) == 0);
  StringHelper::GenerateCopyCharacters(masm, r3, r7, r4, r5,
                                       String::TWO_BYTE_ENCODING);

  __ bind(&return_r2);
  Counters* counters = isolate()->counters();
  __ IncrementCounter(counters->sub_string_native(), 1, r5, r6);
  __ Drop(3);
  __ Ret();

  // Just jump to runtime to create the sub string.
  __ bind(&runtime);
  __ TailCallRuntime(Runtime::kSubString);

  __ bind(&single_char);
  // r2: original string
  // r3: instance type
  // r4: length
  // r5: from index (untagged)
  __ SmiTag(r5, r5);
  StringCharAtGenerator generator(r2, r5, r4, r2, &runtime, &runtime, &runtime,
                                  STRING_INDEX_IS_NUMBER, RECEIVER_IS_STRING);
  generator.GenerateFast(masm);
  __ Drop(3);
  __ Ret();
  generator.SkipSlow(masm, &runtime);
}

void ToNumberStub::Generate(MacroAssembler* masm) {
  // The ToNumber stub takes one argument in r2.
  STATIC_ASSERT(kSmiTag == 0);
  __ TestIfSmi(r2);
  __ Ret(eq);

  __ CompareObjectType(r2, r3, r3, HEAP_NUMBER_TYPE);
  // r2: receiver
  // r3: receiver instance type
  Label not_heap_number;
  __ bne(&not_heap_number);
  __ Ret();
  __ bind(&not_heap_number);

  NonNumberToNumberStub stub(masm->isolate());
  __ TailCallStub(&stub);
}

void NonNumberToNumberStub::Generate(MacroAssembler* masm) {
  // The NonNumberToNumber stub takes one argument in r2.
  __ AssertNotNumber(r2);

  __ CompareObjectType(r2, r3, r3, FIRST_NONSTRING_TYPE);
  // r2: receiver
  // r3: receiver instance type
  StringToNumberStub stub(masm->isolate());
  __ TailCallStub(&stub, lt);

  Label not_oddball;
  __ CmpP(r3, Operand(ODDBALL_TYPE));
  __ bne(&not_oddball, Label::kNear);
  __ LoadP(r2, FieldMemOperand(r2, Oddball::kToNumberOffset));
  __ b(r14);
  __ bind(&not_oddball);

  __ push(r2);  // Push argument.
  __ TailCallRuntime(Runtime::kToNumber);
}

void StringToNumberStub::Generate(MacroAssembler* masm) {
  // The StringToNumber stub takes one argument in r2.
  __ AssertString(r2);

  // Check if string has a cached array index.
  Label runtime;
  __ LoadlW(r4, FieldMemOperand(r2, String::kHashFieldOffset));
  __ And(r0, r4, Operand(String::kContainsCachedArrayIndexMask));
  __ bne(&runtime);
  __ IndexFromHash(r4, r2);
  __ Ret();

  __ bind(&runtime);
  __ push(r2);  // Push argument.
  __ TailCallRuntime(Runtime::kStringToNumber);
}

void ToStringStub::Generate(MacroAssembler* masm) {
  // The ToString stub takes one argument in r2.
  Label done;
  Label is_number;
  __ JumpIfSmi(r2, &is_number);

  __ CompareObjectType(r2, r3, r3, FIRST_NONSTRING_TYPE);
  // r2: receiver
  // r3: receiver instance type
  __ blt(&done);

  Label not_heap_number;
  __ CmpP(r3, Operand(HEAP_NUMBER_TYPE));
  __ bne(&not_heap_number);
  __ bind(&is_number);
  NumberToStringStub stub(isolate());
  __ TailCallStub(&stub);
  __ bind(&not_heap_number);

  Label not_oddball;
  __ CmpP(r3, Operand(ODDBALL_TYPE));
  __ bne(&not_oddball);
  __ LoadP(r2, FieldMemOperand(r2, Oddball::kToStringOffset));
  __ Ret();
  __ bind(&not_oddball);

  __ push(r2);  // Push argument.
  __ TailCallRuntime(Runtime::kToString);

  __ bind(&done);
  __ Ret();
}

void ToNameStub::Generate(MacroAssembler* masm) {
  // The ToName stub takes one argument in r2.
  Label is_number;
  __ JumpIfSmi(r2, &is_number);

  STATIC_ASSERT(FIRST_NAME_TYPE == FIRST_TYPE);
  __ CompareObjectType(r2, r3, r3, LAST_NAME_TYPE);
  // r2: receiver
  // r3: receiver instance type
  __ Ret(le);

  Label not_heap_number;
  __ CmpP(r3, Operand(HEAP_NUMBER_TYPE));
  __ bne(&not_heap_number);
  __ bind(&is_number);
  NumberToStringStub stub(isolate());
  __ TailCallStub(&stub);
  __ bind(&not_heap_number);

  Label not_oddball;
  __ CmpP(r3, Operand(ODDBALL_TYPE));
  __ bne(&not_oddball);
  __ LoadP(r2, FieldMemOperand(r2, Oddball::kToStringOffset));
  __ Ret();
  __ bind(&not_oddball);

  __ push(r2);  // Push argument.
  __ TailCallRuntime(Runtime::kToName);
}

void StringHelper::GenerateFlatOneByteStringEquals(MacroAssembler* masm,
                                                   Register left,
                                                   Register right,
                                                   Register scratch1,
                                                   Register scratch2) {
  Register length = scratch1;

  // Compare lengths.
  Label strings_not_equal, check_zero_length;
  __ LoadP(length, FieldMemOperand(left, String::kLengthOffset));
  __ LoadP(scratch2, FieldMemOperand(right, String::kLengthOffset));
  __ CmpP(length, scratch2);
  __ beq(&check_zero_length);
  __ bind(&strings_not_equal);
  __ LoadSmiLiteral(r2, Smi::FromInt(NOT_EQUAL));
  __ Ret();

  // Check if the length is zero.
  Label compare_chars;
  __ bind(&check_zero_length);
  STATIC_ASSERT(kSmiTag == 0);
  __ CmpP(length, Operand::Zero());
  __ bne(&compare_chars);
  __ LoadSmiLiteral(r2, Smi::FromInt(EQUAL));
  __ Ret();

  // Compare characters.
  __ bind(&compare_chars);
  GenerateOneByteCharsCompareLoop(masm, left, right, length, scratch2,
                                  &strings_not_equal);

  // Characters are equal.
  __ LoadSmiLiteral(r2, Smi::FromInt(EQUAL));
  __ Ret();
}

void StringHelper::GenerateCompareFlatOneByteStrings(
    MacroAssembler* masm, Register left, Register right, Register scratch1,
    Register scratch2, Register scratch3) {
  Label skip, result_not_equal, compare_lengths;
  // Find minimum length and length difference.
  __ LoadP(scratch1, FieldMemOperand(left, String::kLengthOffset));
  __ LoadP(scratch2, FieldMemOperand(right, String::kLengthOffset));
  __ SubP(scratch3, scratch1, scratch2 /*, LeaveOE, SetRC*/);
  // Removing RC looks okay here.
  Register length_delta = scratch3;
  __ ble(&skip, Label::kNear);
  __ LoadRR(scratch1, scratch2);
  __ bind(&skip);
  Register min_length = scratch1;
  STATIC_ASSERT(kSmiTag == 0);
  __ CmpP(min_length, Operand::Zero());
  __ beq(&compare_lengths);

  // Compare loop.
  GenerateOneByteCharsCompareLoop(masm, left, right, min_length, scratch2,
                                  &result_not_equal);

  // Compare lengths - strings up to min-length are equal.
  __ bind(&compare_lengths);
  DCHECK(Smi::FromInt(EQUAL) == static_cast<Smi*>(0));
  // Use length_delta as result if it's zero.
  __ LoadRR(r2, length_delta);
  __ CmpP(length_delta, Operand::Zero());
  __ bind(&result_not_equal);
  // Conditionally update the result based either on length_delta or
  // the last comparion performed in the loop above.
  Label less_equal, equal;
  __ ble(&less_equal);
  __ LoadSmiLiteral(r2, Smi::FromInt(GREATER));
  __ Ret();
  __ bind(&less_equal);
  __ beq(&equal);
  __ LoadSmiLiteral(r2, Smi::FromInt(LESS));
  __ bind(&equal);
  __ Ret();
}

void StringHelper::GenerateOneByteCharsCompareLoop(
    MacroAssembler* masm, Register left, Register right, Register length,
    Register scratch1, Label* chars_not_equal) {
  // Change index to run from -length to -1 by adding length to string
  // start. This means that loop ends when index reaches zero, which
  // doesn't need an additional compare.
  __ SmiUntag(length);
  __ AddP(scratch1, length,
          Operand(SeqOneByteString::kHeaderSize - kHeapObjectTag));
  __ AddP(left, scratch1);
  __ AddP(right, scratch1);
  __ LoadComplementRR(length, length);
  Register index = length;  // index = -length;

  // Compare loop.
  Label loop;
  __ bind(&loop);
  __ LoadlB(scratch1, MemOperand(left, index));
  __ LoadlB(r0, MemOperand(right, index));
  __ CmpP(scratch1, r0);
  __ bne(chars_not_equal);
  __ AddP(index, Operand(1));
  __ CmpP(index, Operand::Zero());
  __ bne(&loop);
}

void BinaryOpICWithAllocationSiteStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r3    : left
  //  -- r2    : right
  // r3: second string
  // -----------------------------------

  // Load r4 with the allocation site.  We stick an undefined dummy value here
  // and replace it with the real allocation site later when we instantiate this
  // stub in BinaryOpICWithAllocationSiteStub::GetCodeCopyFromTemplate().
  __ Move(r4, handle(isolate()->heap()->undefined_value()));

  // Make sure that we actually patched the allocation site.
  if (FLAG_debug_code) {
    __ TestIfSmi(r4);
    __ Assert(ne, kExpectedAllocationSite, cr0);
    __ push(r4);
    __ LoadP(r4, FieldMemOperand(r4, HeapObject::kMapOffset));
    __ CompareRoot(r4, Heap::kAllocationSiteMapRootIndex);
    __ pop(r4);
    __ Assert(eq, kExpectedAllocationSite);
  }

  // Tail call into the stub that handles binary operations with allocation
  // sites.
  BinaryOpWithAllocationSiteStub stub(isolate(), state());
  __ TailCallStub(&stub);
}

void CompareICStub::GenerateBooleans(MacroAssembler* masm) {
  DCHECK_EQ(CompareICState::BOOLEAN, state());
  Label miss;

  __ CheckMap(r3, r4, Heap::kBooleanMapRootIndex, &miss, DO_SMI_CHECK);
  __ CheckMap(r2, r5, Heap::kBooleanMapRootIndex, &miss, DO_SMI_CHECK);
  if (!Token::IsEqualityOp(op())) {
    __ LoadP(r3, FieldMemOperand(r3, Oddball::kToNumberOffset));
    __ AssertSmi(r3);
    __ LoadP(r2, FieldMemOperand(r2, Oddball::kToNumberOffset));
    __ AssertSmi(r2);
  }
  __ SubP(r2, r3, r2);
  __ Ret();

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateSmis(MacroAssembler* masm) {
  DCHECK(state() == CompareICState::SMI);
  Label miss;
  __ OrP(r4, r3, r2);
  __ JumpIfNotSmi(r4, &miss);

  if (GetCondition() == eq) {
    // For equality we do not care about the sign of the result.
    // __ sub(r2, r2, r3, SetCC);
    __ SubP(r2, r2, r3);
  } else {
    // Untag before subtracting to avoid handling overflow.
    __ SmiUntag(r3);
    __ SmiUntag(r2);
    __ SubP(r2, r3, r2);
  }
  __ Ret();

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateNumbers(MacroAssembler* masm) {
  DCHECK(state() == CompareICState::NUMBER);

  Label generic_stub;
  Label unordered, maybe_undefined1, maybe_undefined2;
  Label miss;
  Label equal, less_than;

  if (left() == CompareICState::SMI) {
    __ JumpIfNotSmi(r3, &miss);
  }
  if (right() == CompareICState::SMI) {
    __ JumpIfNotSmi(r2, &miss);
  }

  // Inlining the double comparison and falling back to the general compare
  // stub if NaN is involved.
  // Load left and right operand.
  Label done, left, left_smi, right_smi;
  __ JumpIfSmi(r2, &right_smi);
  __ CheckMap(r2, r4, Heap::kHeapNumberMapRootIndex, &maybe_undefined1,
              DONT_DO_SMI_CHECK);
  __ LoadDouble(d1, FieldMemOperand(r2, HeapNumber::kValueOffset));
  __ b(&left);
  __ bind(&right_smi);
  __ SmiToDouble(d1, r2);

  __ bind(&left);
  __ JumpIfSmi(r3, &left_smi);
  __ CheckMap(r3, r4, Heap::kHeapNumberMapRootIndex, &maybe_undefined2,
              DONT_DO_SMI_CHECK);
  __ LoadDouble(d0, FieldMemOperand(r3, HeapNumber::kValueOffset));
  __ b(&done);
  __ bind(&left_smi);
  __ SmiToDouble(d0, r3);

  __ bind(&done);

  // Compare operands
  __ cdbr(d0, d1);

  // Don't base result on status bits when a NaN is involved.
  __ bunordered(&unordered);

  // Return a result of -1, 0, or 1, based on status bits.
  __ beq(&equal);
  __ blt(&less_than);
  //  assume greater than
  __ LoadImmP(r2, Operand(GREATER));
  __ Ret();
  __ bind(&equal);
  __ LoadImmP(r2, Operand(EQUAL));
  __ Ret();
  __ bind(&less_than);
  __ LoadImmP(r2, Operand(LESS));
  __ Ret();

  __ bind(&unordered);
  __ bind(&generic_stub);
  CompareICStub stub(isolate(), op(), CompareICState::GENERIC,
                     CompareICState::GENERIC, CompareICState::GENERIC);
  __ Jump(stub.GetCode(), RelocInfo::CODE_TARGET);

  __ bind(&maybe_undefined1);
  if (Token::IsOrderedRelationalCompareOp(op())) {
    __ CompareRoot(r2, Heap::kUndefinedValueRootIndex);
    __ bne(&miss);
    __ JumpIfSmi(r3, &unordered);
    __ CompareObjectType(r3, r4, r4, HEAP_NUMBER_TYPE);
    __ bne(&maybe_undefined2);
    __ b(&unordered);
  }

  __ bind(&maybe_undefined2);
  if (Token::IsOrderedRelationalCompareOp(op())) {
    __ CompareRoot(r3, Heap::kUndefinedValueRootIndex);
    __ beq(&unordered);
  }

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateInternalizedStrings(MacroAssembler* masm) {
  DCHECK(state() == CompareICState::INTERNALIZED_STRING);
  Label miss, not_equal;

  // Registers containing left and right operands respectively.
  Register left = r3;
  Register right = r2;
  Register tmp1 = r4;
  Register tmp2 = r5;

  // Check that both operands are heap objects.
  __ JumpIfEitherSmi(left, right, &miss);

  // Check that both operands are symbols.
  __ LoadP(tmp1, FieldMemOperand(left, HeapObject::kMapOffset));
  __ LoadP(tmp2, FieldMemOperand(right, HeapObject::kMapOffset));
  __ LoadlB(tmp1, FieldMemOperand(tmp1, Map::kInstanceTypeOffset));
  __ LoadlB(tmp2, FieldMemOperand(tmp2, Map::kInstanceTypeOffset));
  STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0);
  __ OrP(tmp1, tmp1, tmp2);
  __ AndP(r0, tmp1, Operand(kIsNotStringMask | kIsNotInternalizedMask));
  __ bne(&miss);

  // Internalized strings are compared by identity.
  __ CmpP(left, right);
  __ bne(&not_equal);
  // Make sure r2 is non-zero. At this point input operands are
  // guaranteed to be non-zero.
  DCHECK(right.is(r2));
  STATIC_ASSERT(EQUAL == 0);
  STATIC_ASSERT(kSmiTag == 0);
  __ LoadSmiLiteral(r2, Smi::FromInt(EQUAL));
  __ bind(&not_equal);
  __ Ret();

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateUniqueNames(MacroAssembler* masm) {
  DCHECK(state() == CompareICState::UNIQUE_NAME);
  DCHECK(GetCondition() == eq);
  Label miss;

  // Registers containing left and right operands respectively.
  Register left = r3;
  Register right = r2;
  Register tmp1 = r4;
  Register tmp2 = r5;

  // Check that both operands are heap objects.
  __ JumpIfEitherSmi(left, right, &miss);

  // Check that both operands are unique names. This leaves the instance
  // types loaded in tmp1 and tmp2.
  __ LoadP(tmp1, FieldMemOperand(left, HeapObject::kMapOffset));
  __ LoadP(tmp2, FieldMemOperand(right, HeapObject::kMapOffset));
  __ LoadlB(tmp1, FieldMemOperand(tmp1, Map::kInstanceTypeOffset));
  __ LoadlB(tmp2, FieldMemOperand(tmp2, Map::kInstanceTypeOffset));

  __ JumpIfNotUniqueNameInstanceType(tmp1, &miss);
  __ JumpIfNotUniqueNameInstanceType(tmp2, &miss);

  // Unique names are compared by identity.
  __ CmpP(left, right);
  __ bne(&miss);
  // Make sure r2 is non-zero. At this point input operands are
  // guaranteed to be non-zero.
  DCHECK(right.is(r2));
  STATIC_ASSERT(EQUAL == 0);
  STATIC_ASSERT(kSmiTag == 0);
  __ LoadSmiLiteral(r2, Smi::FromInt(EQUAL));
  __ Ret();

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateStrings(MacroAssembler* masm) {
  DCHECK(state() == CompareICState::STRING);
  Label miss, not_identical, is_symbol;

  bool equality = Token::IsEqualityOp(op());

  // Registers containing left and right operands respectively.
  Register left = r3;
  Register right = r2;
  Register tmp1 = r4;
  Register tmp2 = r5;
  Register tmp3 = r6;
  Register tmp4 = r7;

  // Check that both operands are heap objects.
  __ JumpIfEitherSmi(left, right, &miss);

  // Check that both operands are strings. This leaves the instance
  // types loaded in tmp1 and tmp2.
  __ LoadP(tmp1, FieldMemOperand(left, HeapObject::kMapOffset));
  __ LoadP(tmp2, FieldMemOperand(right, HeapObject::kMapOffset));
  __ LoadlB(tmp1, FieldMemOperand(tmp1, Map::kInstanceTypeOffset));
  __ LoadlB(tmp2, FieldMemOperand(tmp2, Map::kInstanceTypeOffset));
  STATIC_ASSERT(kNotStringTag != 0);
  __ OrP(tmp3, tmp1, tmp2);
  __ AndP(r0, tmp3, Operand(kIsNotStringMask));
  __ bne(&miss);

  // Fast check for identical strings.
  __ CmpP(left, right);
  STATIC_ASSERT(EQUAL == 0);
  STATIC_ASSERT(kSmiTag == 0);
  __ bne(&not_identical);
  __ LoadSmiLiteral(r2, Smi::FromInt(EQUAL));
  __ Ret();
  __ bind(&not_identical);

  // Handle not identical strings.

  // Check that both strings are internalized strings. If they are, we're done
  // because we already know they are not identical. We know they are both
  // strings.
  if (equality) {
    DCHECK(GetCondition() == eq);
    STATIC_ASSERT(kInternalizedTag == 0);
    __ OrP(tmp3, tmp1, tmp2);
    __ AndP(r0, tmp3, Operand(kIsNotInternalizedMask));
    __ bne(&is_symbol);
    // Make sure r2 is non-zero. At this point input operands are
    // guaranteed to be non-zero.
    DCHECK(right.is(r2));
    __ Ret();
    __ bind(&is_symbol);
  }

  // Check that both strings are sequential one-byte.
  Label runtime;
  __ JumpIfBothInstanceTypesAreNotSequentialOneByte(tmp1, tmp2, tmp3, tmp4,
                                                    &runtime);

  // Compare flat one-byte strings. Returns when done.
  if (equality) {
    StringHelper::GenerateFlatOneByteStringEquals(masm, left, right, tmp1,
                                                  tmp2);
  } else {
    StringHelper::GenerateCompareFlatOneByteStrings(masm, left, right, tmp1,
                                                    tmp2, tmp3);
  }

  // Handle more complex cases in runtime.
  __ bind(&runtime);
  if (equality) {
    {
      FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
      __ Push(left, right);
      __ CallRuntime(Runtime::kStringEqual);
    }
    __ LoadRoot(r3, Heap::kTrueValueRootIndex);
    __ SubP(r2, r2, r3);
    __ Ret();
  } else {
    __ Push(left, right);
    __ TailCallRuntime(Runtime::kStringCompare);
  }

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateReceivers(MacroAssembler* masm) {
  DCHECK_EQ(CompareICState::RECEIVER, state());
  Label miss;
  __ AndP(r4, r3, r2);
  __ JumpIfSmi(r4, &miss);

  STATIC_ASSERT(LAST_TYPE == LAST_JS_RECEIVER_TYPE);
  __ CompareObjectType(r2, r4, r4, FIRST_JS_RECEIVER_TYPE);
  __ blt(&miss);
  __ CompareObjectType(r3, r4, r4, FIRST_JS_RECEIVER_TYPE);
  __ blt(&miss);

  DCHECK(GetCondition() == eq);
  __ SubP(r2, r2, r3);
  __ Ret();

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateKnownReceivers(MacroAssembler* masm) {
  Label miss;
  Handle<WeakCell> cell = Map::WeakCellForMap(known_map_);
  __ AndP(r4, r3, r2);
  __ JumpIfSmi(r4, &miss);
  __ GetWeakValue(r6, cell);
  __ LoadP(r4, FieldMemOperand(r2, HeapObject::kMapOffset));
  __ LoadP(r5, FieldMemOperand(r3, HeapObject::kMapOffset));
  __ CmpP(r4, r6);
  __ bne(&miss);
  __ CmpP(r5, r6);
  __ bne(&miss);

  if (Token::IsEqualityOp(op())) {
    __ SubP(r2, r2, r3);
    __ Ret();
  } else {
    if (op() == Token::LT || op() == Token::LTE) {
      __ LoadSmiLiteral(r4, Smi::FromInt(GREATER));
    } else {
      __ LoadSmiLiteral(r4, Smi::FromInt(LESS));
    }
    __ Push(r3, r2, r4);
    __ TailCallRuntime(Runtime::kCompare);
  }

  __ bind(&miss);
  GenerateMiss(masm);
}

void CompareICStub::GenerateMiss(MacroAssembler* masm) {
  {
    // Call the runtime system in a fresh internal frame.
    FrameScope scope(masm, StackFrame::INTERNAL);
    __ Push(r3, r2);
    __ Push(r3, r2);
    __ LoadSmiLiteral(r0, Smi::FromInt(op()));
    __ push(r0);
    __ CallRuntime(Runtime::kCompareIC_Miss);
    // Compute the entry point of the rewritten stub.
    __ AddP(r4, r2, Operand(Code::kHeaderSize - kHeapObjectTag));
    // Restore registers.
    __ Pop(r3, r2);
  }

  __ JumpToJSEntry(r4);
}

// This stub is paired with DirectCEntryStub::GenerateCall
void DirectCEntryStub::Generate(MacroAssembler* masm) {
  __ CleanseP(r14);

  // Statement positions are expected to be recorded when the target
  // address is loaded.
  __ positions_recorder()->WriteRecordedPositions();

  __ b(ip);  // Callee will return to R14 directly
}

void DirectCEntryStub::GenerateCall(MacroAssembler* masm, Register target) {
#if ABI_USES_FUNCTION_DESCRIPTORS && !defined(USE_SIMULATOR)
  // Native AIX/S390X Linux use a function descriptor.
  __ LoadP(ToRegister(ABI_TOC_REGISTER), MemOperand(target, kPointerSize));
  __ LoadP(target, MemOperand(target, 0));  // Instruction address
#else
  // ip needs to be set for DirectCEentryStub::Generate, and also
  // for ABI_CALL_VIA_IP.
  __ Move(ip, target);
#endif

  __ call(GetCode(), RelocInfo::CODE_TARGET);  // Call the stub.
}

void NameDictionaryLookupStub::GenerateNegativeLookup(
    MacroAssembler* masm, Label* miss, Label* done, Register receiver,
    Register properties, Handle<Name> name, Register scratch0) {
  DCHECK(name->IsUniqueName());
  // If names of slots in range from 1 to kProbes - 1 for the hash value are
  // not equal to the name and kProbes-th slot is not used (its name is the
  // undefined value), it guarantees the hash table doesn't contain the
  // property. It's true even if some slots represent deleted properties
  // (their names are the hole value).
  for (int i = 0; i < kInlinedProbes; i++) {
    // scratch0 points to properties hash.
    // Compute the masked index: (hash + i + i * i) & mask.
    Register index = scratch0;
    // Capacity is smi 2^n.
    __ LoadP(index, FieldMemOperand(properties, kCapacityOffset));
    __ SubP(index, Operand(1));
    __ LoadSmiLiteral(
        ip, Smi::FromInt(name->Hash() + NameDictionary::GetProbeOffset(i)));
    __ AndP(index, ip);

    // Scale the index by multiplying by the entry size.
    STATIC_ASSERT(NameDictionary::kEntrySize == 3);
    __ ShiftLeftP(ip, index, Operand(1));
    __ AddP(index, ip);  // index *= 3.

    Register entity_name = scratch0;
    // Having undefined at this place means the name is not contained.
    Register tmp = properties;
    __ SmiToPtrArrayOffset(ip, index);
    __ AddP(tmp, properties, ip);
    __ LoadP(entity_name, FieldMemOperand(tmp, kElementsStartOffset));

    DCHECK(!tmp.is(entity_name));
    __ CompareRoot(entity_name, Heap::kUndefinedValueRootIndex);
    __ beq(done);

    // Stop if found the property.
    __ CmpP(entity_name, Operand(Handle<Name>(name)));
    __ beq(miss);

    Label good;
    __ CompareRoot(entity_name, Heap::kTheHoleValueRootIndex);
    __ beq(&good);

    // Check if the entry name is not a unique name.
    __ LoadP(entity_name, FieldMemOperand(entity_name, HeapObject::kMapOffset));
    __ LoadlB(entity_name,
              FieldMemOperand(entity_name, Map::kInstanceTypeOffset));
    __ JumpIfNotUniqueNameInstanceType(entity_name, miss);
    __ bind(&good);

    // Restore the properties.
    __ LoadP(properties,
             FieldMemOperand(receiver, JSObject::kPropertiesOffset));
  }

  const int spill_mask = (r0.bit() | r8.bit() | r7.bit() | r6.bit() | r5.bit() |
                          r4.bit() | r3.bit() | r2.bit());

  __ LoadRR(r0, r14);
  __ MultiPush(spill_mask);

  __ LoadP(r2, FieldMemOperand(receiver, JSObject::kPropertiesOffset));
  __ mov(r3, Operand(Handle<Name>(name)));
  NameDictionaryLookupStub stub(masm->isolate(), NEGATIVE_LOOKUP);
  __ CallStub(&stub);
  __ CmpP(r2, Operand::Zero());

  __ MultiPop(spill_mask);  // MultiPop does not touch condition flags
  __ LoadRR(r14, r0);

  __ beq(done);
  __ bne(miss);
}

// Probe the name dictionary in the |elements| register. Jump to the
// |done| label if a property with the given name is found. Jump to
// the |miss| label otherwise.
// If lookup was successful |scratch2| will be equal to elements + 4 * index.
void NameDictionaryLookupStub::GeneratePositiveLookup(
    MacroAssembler* masm, Label* miss, Label* done, Register elements,
    Register name, Register scratch1, Register scratch2) {
  DCHECK(!elements.is(scratch1));
  DCHECK(!elements.is(scratch2));
  DCHECK(!name.is(scratch1));
  DCHECK(!name.is(scratch2));

  __ AssertName(name);

  // Compute the capacity mask.
  __ LoadP(scratch1, FieldMemOperand(elements, kCapacityOffset));
  __ SmiUntag(scratch1);  // convert smi to int
  __ SubP(scratch1, Operand(1));

  // Generate an unrolled loop that performs a few probes before
  // giving up. Measurements done on Gmail indicate that 2 probes
  // cover ~93% of loads from dictionaries.
  for (int i = 0; i < kInlinedProbes; i++) {
    // Compute the masked index: (hash + i + i * i) & mask.
    __ LoadlW(scratch2, FieldMemOperand(name, String::kHashFieldOffset));
    if (i > 0) {
      // Add the probe offset (i + i * i) left shifted to avoid right shifting
      // the hash in a separate instruction. The value hash + i + i * i is right
      // shifted in the following and instruction.
      DCHECK(NameDictionary::GetProbeOffset(i) <
             1 << (32 - Name::kHashFieldOffset));
      __ AddP(scratch2,
              Operand(NameDictionary::GetProbeOffset(i) << Name::kHashShift));
    }
    __ srl(scratch2, Operand(String::kHashShift));
    __ AndP(scratch2, scratch1);

    // Scale the index by multiplying by the entry size.
    STATIC_ASSERT(NameDictionary::kEntrySize == 3);
    // scratch2 = scratch2 * 3.
    __ ShiftLeftP(ip, scratch2, Operand(1));
    __ AddP(scratch2, ip);

    // Check if the key is identical to the name.
    __ ShiftLeftP(ip, scratch2, Operand(kPointerSizeLog2));
    __ AddP(scratch2, elements, ip);
    __ LoadP(ip, FieldMemOperand(scratch2, kElementsStartOffset));
    __ CmpP(name, ip);
    __ beq(done);
  }

  const int spill_mask = (r0.bit() | r8.bit() | r7.bit() | r6.bit() | r5.bit() |
                          r4.bit() | r3.bit() | r2.bit()) &
                         ~(scratch1.bit() | scratch2.bit());

  __ LoadRR(r0, r14);
  __ MultiPush(spill_mask);
  if (name.is(r2)) {
    DCHECK(!elements.is(r3));
    __ LoadRR(r3, name);
    __ LoadRR(r2, elements);
  } else {
    __ LoadRR(r2, elements);
    __ LoadRR(r3, name);
  }
  NameDictionaryLookupStub stub(masm->isolate(), POSITIVE_LOOKUP);
  __ CallStub(&stub);
  __ LoadRR(r1, r2);
  __ LoadRR(scratch2, r4);
  __ MultiPop(spill_mask);
  __ LoadRR(r14, r0);

  __ CmpP(r1, Operand::Zero());
  __ bne(done);
  __ beq(miss);
}

void NameDictionaryLookupStub::Generate(MacroAssembler* masm) {
  // This stub overrides SometimesSetsUpAFrame() to return false.  That means
  // we cannot call anything that could cause a GC from this stub.
  // Registers:
  //  result: NameDictionary to probe
  //  r3: key
  //  dictionary: NameDictionary to probe.
  //  index: will hold an index of entry if lookup is successful.
  //         might alias with result_.
  // Returns:
  //  result_ is zero if lookup failed, non zero otherwise.

  Register result = r2;
  Register dictionary = r2;
  Register key = r3;
  Register index = r4;
  Register mask = r5;
  Register hash = r6;
  Register undefined = r7;
  Register entry_key = r8;
  Register scratch = r8;

  Label in_dictionary, maybe_in_dictionary, not_in_dictionary;

  __ LoadP(mask, FieldMemOperand(dictionary, kCapacityOffset));
  __ SmiUntag(mask);
  __ SubP(mask, Operand(1));

  __ LoadlW(hash, FieldMemOperand(key, String::kHashFieldOffset));

  __ LoadRoot(undefined, Heap::kUndefinedValueRootIndex);

  for (int i = kInlinedProbes; i < kTotalProbes; i++) {
    // Compute the masked index: (hash + i + i * i) & mask.
    // Capacity is smi 2^n.
    if (i > 0) {
      // Add the probe offset (i + i * i) left shifted to avoid right shifting
      // the hash in a separate instruction. The value hash + i + i * i is right
      // shifted in the following and instruction.
      DCHECK(NameDictionary::GetProbeOffset(i) <
             1 << (32 - Name::kHashFieldOffset));
      __ AddP(index, hash,
              Operand(NameDictionary::GetProbeOffset(i) << Name::kHashShift));
    } else {
      __ LoadRR(index, hash);
    }
    __ ShiftRight(r0, index, Operand(String::kHashShift));
    __ AndP(index, r0, mask);

    // Scale the index by multiplying by the entry size.
    STATIC_ASSERT(NameDictionary::kEntrySize == 3);
    __ ShiftLeftP(scratch, index, Operand(1));
    __ AddP(index, scratch);  // index *= 3.

    __ ShiftLeftP(scratch, index, Operand(kPointerSizeLog2));
    __ AddP(index, dictionary, scratch);
    __ LoadP(entry_key, FieldMemOperand(index, kElementsStartOffset));

    // Having undefined at this place means the name is not contained.
    __ CmpP(entry_key, undefined);
    __ beq(&not_in_dictionary);

    // Stop if found the property.
    __ CmpP(entry_key, key);
    __ beq(&in_dictionary);

    if (i != kTotalProbes - 1 && mode() == NEGATIVE_LOOKUP) {
      // Check if the entry name is not a unique name.
      __ LoadP(entry_key, FieldMemOperand(entry_key, HeapObject::kMapOffset));
      __ LoadlB(entry_key,
                FieldMemOperand(entry_key, Map::kInstanceTypeOffset));
      __ JumpIfNotUniqueNameInstanceType(entry_key, &maybe_in_dictionary);
    }
  }

  __ bind(&maybe_in_dictionary);
  // If we are doing negative lookup then probing failure should be
  // treated as a lookup success. For positive lookup probing failure
  // should be treated as lookup failure.
  if (mode() == POSITIVE_LOOKUP) {
    __ LoadImmP(result, Operand::Zero());
    __ Ret();
  }

  __ bind(&in_dictionary);
  __ LoadImmP(result, Operand(1));
  __ Ret();

  __ bind(&not_in_dictionary);
  __ LoadImmP(result, Operand::Zero());
  __ Ret();
}

void StoreBufferOverflowStub::GenerateFixedRegStubsAheadOfTime(
    Isolate* isolate) {
  StoreBufferOverflowStub stub1(isolate, kDontSaveFPRegs);
  stub1.GetCode();
  // Hydrogen code stubs need stub2 at snapshot time.
  StoreBufferOverflowStub stub2(isolate, kSaveFPRegs);
  stub2.GetCode();
}

// Takes the input in 3 registers: address_ value_ and object_.  A pointer to
// the value has just been written into the object, now this stub makes sure
// we keep the GC informed.  The word in the object where the value has been
// written is in the address register.
void RecordWriteStub::Generate(MacroAssembler* masm) {
  Label skip_to_incremental_noncompacting;
  Label skip_to_incremental_compacting;

  // The first two branch instructions are generated with labels so as to
  // get the offset fixed up correctly by the bind(Label*) call.  We patch
  // it back and forth between branch condition True and False
  // when we start and stop incremental heap marking.
  // See RecordWriteStub::Patch for details.

  // Clear the bit, branch on True for NOP action initially
  __ b(CC_NOP, &skip_to_incremental_noncompacting);
  __ b(CC_NOP, &skip_to_incremental_compacting);

  if (remembered_set_action() == EMIT_REMEMBERED_SET) {
    __ RememberedSetHelper(object(), address(), value(), save_fp_regs_mode(),
                           MacroAssembler::kReturnAtEnd);
  }
  __ Ret();

  __ bind(&skip_to_incremental_noncompacting);
  GenerateIncremental(masm, INCREMENTAL);

  __ bind(&skip_to_incremental_compacting);
  GenerateIncremental(masm, INCREMENTAL_COMPACTION);

  // Initial mode of the stub is expected to be STORE_BUFFER_ONLY.
  // Will be checked in IncrementalMarking::ActivateGeneratedStub.
  // patching not required on S390 as the initial path is effectively NOP
}

void RecordWriteStub::GenerateIncremental(MacroAssembler* masm, Mode mode) {
  regs_.Save(masm);

  if (remembered_set_action() == EMIT_REMEMBERED_SET) {
    Label dont_need_remembered_set;

    __ LoadP(regs_.scratch0(), MemOperand(regs_.address(), 0));
    __ JumpIfNotInNewSpace(regs_.scratch0(),  // Value.
                           regs_.scratch0(), &dont_need_remembered_set);

    __ JumpIfInNewSpace(regs_.object(), regs_.scratch0(),
                        &dont_need_remembered_set);

    // First notify the incremental marker if necessary, then update the
    // remembered set.
    CheckNeedsToInformIncrementalMarker(
        masm, kUpdateRememberedSetOnNoNeedToInformIncrementalMarker, mode);
    InformIncrementalMarker(masm);
    regs_.Restore(masm);
    __ RememberedSetHelper(object(), address(), value(), save_fp_regs_mode(),
                           MacroAssembler::kReturnAtEnd);

    __ bind(&dont_need_remembered_set);
  }

  CheckNeedsToInformIncrementalMarker(
      masm, kReturnOnNoNeedToInformIncrementalMarker, mode);
  InformIncrementalMarker(masm);
  regs_.Restore(masm);
  __ Ret();
}

void RecordWriteStub::InformIncrementalMarker(MacroAssembler* masm) {
  regs_.SaveCallerSaveRegisters(masm, save_fp_regs_mode());
  int argument_count = 3;
  __ PrepareCallCFunction(argument_count, regs_.scratch0());
  Register address =
      r2.is(regs_.address()) ? regs_.scratch0() : regs_.address();
  DCHECK(!address.is(regs_.object()));
  DCHECK(!address.is(r2));
  __ LoadRR(address, regs_.address());
  __ LoadRR(r2, regs_.object());
  __ LoadRR(r3, address);
  __ mov(r4, Operand(ExternalReference::isolate_address(isolate())));

  AllowExternalCallThatCantCauseGC scope(masm);
  __ CallCFunction(
      ExternalReference::incremental_marking_record_write_function(isolate()),
      argument_count);
  regs_.RestoreCallerSaveRegisters(masm, save_fp_regs_mode());
}

void RecordWriteStub::CheckNeedsToInformIncrementalMarker(
    MacroAssembler* masm, OnNoNeedToInformIncrementalMarker on_no_need,
    Mode mode) {
  Label on_black;
  Label need_incremental;
  Label need_incremental_pop_scratch;

  DCHECK((~Page::kPageAlignmentMask & 0xffff) == 0);
  __ AndP(regs_.scratch0(), regs_.object(), Operand(~Page::kPageAlignmentMask));
  __ LoadP(
      regs_.scratch1(),
      MemOperand(regs_.scratch0(), MemoryChunk::kWriteBarrierCounterOffset));
  __ SubP(regs_.scratch1(), regs_.scratch1(), Operand(1));
  __ StoreP(
      regs_.scratch1(),
      MemOperand(regs_.scratch0(), MemoryChunk::kWriteBarrierCounterOffset));
  __ CmpP(regs_.scratch1(), Operand::Zero());  // S390, we could do better here
  __ blt(&need_incremental);

  // Let's look at the color of the object:  If it is not black we don't have
  // to inform the incremental marker.
  __ JumpIfBlack(regs_.object(), regs_.scratch0(), regs_.scratch1(), &on_black);

  regs_.Restore(masm);
  if (on_no_need == kUpdateRememberedSetOnNoNeedToInformIncrementalMarker) {
    __ RememberedSetHelper(object(), address(), value(), save_fp_regs_mode(),
                           MacroAssembler::kReturnAtEnd);
  } else {
    __ Ret();
  }

  __ bind(&on_black);

  // Get the value from the slot.
  __ LoadP(regs_.scratch0(), MemOperand(regs_.address(), 0));

  if (mode == INCREMENTAL_COMPACTION) {
    Label ensure_not_white;

    __ CheckPageFlag(regs_.scratch0(),  // Contains value.
                     regs_.scratch1(),  // Scratch.
                     MemoryChunk::kEvacuationCandidateMask, eq,
                     &ensure_not_white);

    __ CheckPageFlag(regs_.object(),
                     regs_.scratch1(),  // Scratch.
                     MemoryChunk::kSkipEvacuationSlotsRecordingMask, eq,
                     &need_incremental);

    __ bind(&ensure_not_white);
  }

  // We need extra registers for this, so we push the object and the address
  // register temporarily.
  __ Push(regs_.object(), regs_.address());
  __ JumpIfWhite(regs_.scratch0(),  // The value.
                 regs_.scratch1(),  // Scratch.
                 regs_.object(),    // Scratch.
                 regs_.address(),   // Scratch.
                 &need_incremental_pop_scratch);
  __ Pop(regs_.object(), regs_.address());

  regs_.Restore(masm);
  if (on_no_need == kUpdateRememberedSetOnNoNeedToInformIncrementalMarker) {
    __ RememberedSetHelper(object(), address(), value(), save_fp_regs_mode(),
                           MacroAssembler::kReturnAtEnd);
  } else {
    __ Ret();
  }

  __ bind(&need_incremental_pop_scratch);
  __ Pop(regs_.object(), regs_.address());

  __ bind(&need_incremental);

  // Fall through when we need to inform the incremental marker.
}

void StubFailureTrampolineStub::Generate(MacroAssembler* masm) {
  CEntryStub ces(isolate(), 1, kSaveFPRegs);
  __ Call(ces.GetCode(), RelocInfo::CODE_TARGET);
  int parameter_count_offset =
      StubFailureTrampolineFrameConstants::kArgumentsLengthOffset;
  __ LoadP(r3, MemOperand(fp, parameter_count_offset));
  if (function_mode() == JS_FUNCTION_STUB_MODE) {
    __ AddP(r3, Operand(1));
  }
  masm->LeaveFrame(StackFrame::STUB_FAILURE_TRAMPOLINE);
  __ ShiftLeftP(r3, r3, Operand(kPointerSizeLog2));
  __ la(sp, MemOperand(r3, sp));
  __ Ret();
}

void LoadICTrampolineStub::Generate(MacroAssembler* masm) {
  __ EmitLoadTypeFeedbackVector(LoadWithVectorDescriptor::VectorRegister());
  LoadICStub stub(isolate(), state());
  stub.GenerateForTrampoline(masm);
}

void KeyedLoadICTrampolineStub::Generate(MacroAssembler* masm) {
  __ EmitLoadTypeFeedbackVector(LoadWithVectorDescriptor::VectorRegister());
  KeyedLoadICStub stub(isolate(), state());
  stub.GenerateForTrampoline(masm);
}

void CallICTrampolineStub::Generate(MacroAssembler* masm) {
  __ EmitLoadTypeFeedbackVector(r4);
  CallICStub stub(isolate(), state());
  __ Jump(stub.GetCode(), RelocInfo::CODE_TARGET);
}

void LoadICStub::Generate(MacroAssembler* masm) { GenerateImpl(masm, false); }

void LoadICStub::GenerateForTrampoline(MacroAssembler* masm) {
  GenerateImpl(masm, true);
}

static void HandleArrayCases(MacroAssembler* masm, Register feedback,
                             Register receiver_map, Register scratch1,
                             Register scratch2, bool is_polymorphic,
                             Label* miss) {
  // feedback initially contains the feedback array
  Label next_loop, prepare_next;
  Label start_polymorphic;

  Register cached_map = scratch1;

  __ LoadP(cached_map,
           FieldMemOperand(feedback, FixedArray::OffsetOfElementAt(0)));
  __ LoadP(cached_map, FieldMemOperand(cached_map, WeakCell::kValueOffset));
  __ CmpP(receiver_map, cached_map);
  __ bne(&start_polymorphic, Label::kNear);
  // found, now call handler.
  Register handler = feedback;
  __ LoadP(handler,
           FieldMemOperand(feedback, FixedArray::OffsetOfElementAt(1)));
  __ AddP(ip, handler, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ Jump(ip);

  Register length = scratch2;
  __ bind(&start_polymorphic);
  __ LoadP(length, FieldMemOperand(feedback, FixedArray::kLengthOffset));
  if (!is_polymorphic) {
    // If the IC could be monomorphic we have to make sure we don't go past the
    // end of the feedback array.
    __ CmpSmiLiteral(length, Smi::FromInt(2), r0);
    __ beq(miss);
  }

  Register too_far = length;
  Register pointer_reg = feedback;

  // +-----+------+------+-----+-----+ ... ----+
  // | map | len  | wm0  | h0  | wm1 |      hN |
  // +-----+------+------+-----+-----+ ... ----+
  //                 0      1     2        len-1
  //                              ^              ^
  //                              |              |
  //                         pointer_reg      too_far
  //                         aka feedback     scratch2
  // also need receiver_map
  // use cached_map (scratch1) to look in the weak map values.
  __ SmiToPtrArrayOffset(r0, length);
  __ AddP(too_far, feedback, r0);
  __ AddP(too_far, Operand(FixedArray::kHeaderSize - kHeapObjectTag));
  __ AddP(pointer_reg, feedback,
          Operand(FixedArray::OffsetOfElementAt(2) - kHeapObjectTag));

  __ bind(&next_loop);
  __ LoadP(cached_map, MemOperand(pointer_reg));
  __ LoadP(cached_map, FieldMemOperand(cached_map, WeakCell::kValueOffset));
  __ CmpP(receiver_map, cached_map);
  __ bne(&prepare_next, Label::kNear);
  __ LoadP(handler, MemOperand(pointer_reg, kPointerSize));
  __ AddP(ip, handler, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ Jump(ip);

  __ bind(&prepare_next);
  __ AddP(pointer_reg, Operand(kPointerSize * 2));
  __ CmpP(pointer_reg, too_far);
  __ blt(&next_loop, Label::kNear);

  // We exhausted our array of map handler pairs.
  __ b(miss);
}

static void HandleMonomorphicCase(MacroAssembler* masm, Register receiver,
                                  Register receiver_map, Register feedback,
                                  Register vector, Register slot,
                                  Register scratch, Label* compare_map,
                                  Label* load_smi_map, Label* try_array) {
  __ JumpIfSmi(receiver, load_smi_map);
  __ LoadP(receiver_map, FieldMemOperand(receiver, HeapObject::kMapOffset));
  __ bind(compare_map);
  Register cached_map = scratch;
  // Move the weak map into the weak_cell register.
  __ LoadP(cached_map, FieldMemOperand(feedback, WeakCell::kValueOffset));
  __ CmpP(cached_map, receiver_map);
  __ bne(try_array);
  Register handler = feedback;
  __ SmiToPtrArrayOffset(r1, slot);
  __ LoadP(handler,
           FieldMemOperand(r1, vector, FixedArray::kHeaderSize + kPointerSize));
  __ AddP(ip, handler, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ Jump(ip);
}

void LoadICStub::GenerateImpl(MacroAssembler* masm, bool in_frame) {
  Register receiver = LoadWithVectorDescriptor::ReceiverRegister();  // r3
  Register name = LoadWithVectorDescriptor::NameRegister();          // r4
  Register vector = LoadWithVectorDescriptor::VectorRegister();      // r5
  Register slot = LoadWithVectorDescriptor::SlotRegister();          // r2
  Register feedback = r6;
  Register receiver_map = r7;
  Register scratch1 = r8;

  __ SmiToPtrArrayOffset(r1, slot);
  __ LoadP(feedback, FieldMemOperand(r1, vector, FixedArray::kHeaderSize));

  // Try to quickly handle the monomorphic case without knowing for sure
  // if we have a weak cell in feedback. We do know it's safe to look
  // at WeakCell::kValueOffset.
  Label try_array, load_smi_map, compare_map;
  Label not_array, miss;
  HandleMonomorphicCase(masm, receiver, receiver_map, feedback, vector, slot,
                        scratch1, &compare_map, &load_smi_map, &try_array);

  // Is it a fixed array?
  __ bind(&try_array);
  __ LoadP(scratch1, FieldMemOperand(feedback, HeapObject::kMapOffset));
  __ CompareRoot(scratch1, Heap::kFixedArrayMapRootIndex);
  __ bne(&not_array, Label::kNear);
  HandleArrayCases(masm, feedback, receiver_map, scratch1, r9, true, &miss);

  __ bind(&not_array);
  __ CompareRoot(feedback, Heap::kmegamorphic_symbolRootIndex);
  __ bne(&miss);
  Code::Flags code_flags = Code::RemoveTypeAndHolderFromFlags(
      Code::ComputeHandlerFlags(Code::LOAD_IC));
  masm->isolate()->stub_cache()->GenerateProbe(masm, Code::LOAD_IC, code_flags,
                                               receiver, name, feedback,
                                               receiver_map, scratch1, r9);

  __ bind(&miss);
  LoadIC::GenerateMiss(masm);

  __ bind(&load_smi_map);
  __ LoadRoot(receiver_map, Heap::kHeapNumberMapRootIndex);
  __ b(&compare_map);
}

void KeyedLoadICStub::Generate(MacroAssembler* masm) {
  GenerateImpl(masm, false);
}

void KeyedLoadICStub::GenerateForTrampoline(MacroAssembler* masm) {
  GenerateImpl(masm, true);
}

void KeyedLoadICStub::GenerateImpl(MacroAssembler* masm, bool in_frame) {
  Register receiver = LoadWithVectorDescriptor::ReceiverRegister();  // r3
  Register key = LoadWithVectorDescriptor::NameRegister();           // r4
  Register vector = LoadWithVectorDescriptor::VectorRegister();      // r5
  Register slot = LoadWithVectorDescriptor::SlotRegister();          // r2
  Register feedback = r6;
  Register receiver_map = r7;
  Register scratch1 = r8;

  __ SmiToPtrArrayOffset(r1, slot);
  __ LoadP(feedback, FieldMemOperand(r1, vector, FixedArray::kHeaderSize));

  // Try to quickly handle the monomorphic case without knowing for sure
  // if we have a weak cell in feedback. We do know it's safe to look
  // at WeakCell::kValueOffset.
  Label try_array, load_smi_map, compare_map;
  Label not_array, miss;
  HandleMonomorphicCase(masm, receiver, receiver_map, feedback, vector, slot,
                        scratch1, &compare_map, &load_smi_map, &try_array);

  __ bind(&try_array);
  // Is it a fixed array?
  __ LoadP(scratch1, FieldMemOperand(feedback, HeapObject::kMapOffset));
  __ CompareRoot(scratch1, Heap::kFixedArrayMapRootIndex);
  __ bne(&not_array);

  // We have a polymorphic element handler.
  Label polymorphic, try_poly_name;
  __ bind(&polymorphic);
  HandleArrayCases(masm, feedback, receiver_map, scratch1, r9, true, &miss);

  __ bind(&not_array);
  // Is it generic?
  __ CompareRoot(feedback, Heap::kmegamorphic_symbolRootIndex);
  __ bne(&try_poly_name);
  Handle<Code> megamorphic_stub =
      KeyedLoadIC::ChooseMegamorphicStub(masm->isolate(), GetExtraICState());
  __ Jump(megamorphic_stub, RelocInfo::CODE_TARGET);

  __ bind(&try_poly_name);
  // We might have a name in feedback, and a fixed array in the next slot.
  __ CmpP(key, feedback);
  __ bne(&miss);
  // If the name comparison succeeded, we know we have a fixed array with
  // at least one map/handler pair.
  __ SmiToPtrArrayOffset(r1, slot);
  __ LoadP(feedback,
           FieldMemOperand(r1, vector, FixedArray::kHeaderSize + kPointerSize));
  HandleArrayCases(masm, feedback, receiver_map, scratch1, r9, false, &miss);

  __ bind(&miss);
  KeyedLoadIC::GenerateMiss(masm);

  __ bind(&load_smi_map);
  __ LoadRoot(receiver_map, Heap::kHeapNumberMapRootIndex);
  __ b(&compare_map);
}

void VectorStoreICTrampolineStub::Generate(MacroAssembler* masm) {
  __ EmitLoadTypeFeedbackVector(VectorStoreICDescriptor::VectorRegister());
  VectorStoreICStub stub(isolate(), state());
  stub.GenerateForTrampoline(masm);
}

void VectorKeyedStoreICTrampolineStub::Generate(MacroAssembler* masm) {
  __ EmitLoadTypeFeedbackVector(VectorStoreICDescriptor::VectorRegister());
  VectorKeyedStoreICStub stub(isolate(), state());
  stub.GenerateForTrampoline(masm);
}

void VectorStoreICStub::Generate(MacroAssembler* masm) {
  GenerateImpl(masm, false);
}

void VectorStoreICStub::GenerateForTrampoline(MacroAssembler* masm) {
  GenerateImpl(masm, true);
}

void VectorStoreICStub::GenerateImpl(MacroAssembler* masm, bool in_frame) {
  Register receiver = VectorStoreICDescriptor::ReceiverRegister();  // r3
  Register key = VectorStoreICDescriptor::NameRegister();           // r4
  Register vector = VectorStoreICDescriptor::VectorRegister();      // r5
  Register slot = VectorStoreICDescriptor::SlotRegister();          // r6
  DCHECK(VectorStoreICDescriptor::ValueRegister().is(r2));          // r2
  Register feedback = r7;
  Register receiver_map = r8;
  Register scratch1 = r9;

  __ SmiToPtrArrayOffset(r0, slot);
  __ AddP(feedback, vector, r0);
  __ LoadP(feedback, FieldMemOperand(feedback, FixedArray::kHeaderSize));

  // Try to quickly handle the monomorphic case without knowing for sure
  // if we have a weak cell in feedback. We do know it's safe to look
  // at WeakCell::kValueOffset.
  Label try_array, load_smi_map, compare_map;
  Label not_array, miss;
  HandleMonomorphicCase(masm, receiver, receiver_map, feedback, vector, slot,
                        scratch1, &compare_map, &load_smi_map, &try_array);

  // Is it a fixed array?
  __ bind(&try_array);
  __ LoadP(scratch1, FieldMemOperand(feedback, HeapObject::kMapOffset));
  __ CompareRoot(scratch1, Heap::kFixedArrayMapRootIndex);
  __ bne(&not_array);

  Register scratch2 = ip;
  HandleArrayCases(masm, feedback, receiver_map, scratch1, scratch2, true,
                   &miss);

  __ bind(&not_array);
  __ CompareRoot(feedback, Heap::kmegamorphic_symbolRootIndex);
  __ bne(&miss);
  Code::Flags code_flags = Code::RemoveTypeAndHolderFromFlags(
      Code::ComputeHandlerFlags(Code::STORE_IC));
  masm->isolate()->stub_cache()->GenerateProbe(
      masm, Code::STORE_IC, code_flags, receiver, key, feedback, receiver_map,
      scratch1, scratch2);

  __ bind(&miss);
  StoreIC::GenerateMiss(masm);

  __ bind(&load_smi_map);
  __ LoadRoot(receiver_map, Heap::kHeapNumberMapRootIndex);
  __ b(&compare_map);
}

void VectorKeyedStoreICStub::Generate(MacroAssembler* masm) {
  GenerateImpl(masm, false);
}

void VectorKeyedStoreICStub::GenerateForTrampoline(MacroAssembler* masm) {
  GenerateImpl(masm, true);
}

static void HandlePolymorphicStoreCase(MacroAssembler* masm, Register feedback,
                                       Register receiver_map, Register scratch1,
                                       Register scratch2, Label* miss) {
  // feedback initially contains the feedback array
  Label next_loop, prepare_next;
  Label start_polymorphic;
  Label transition_call;

  Register cached_map = scratch1;
  Register too_far = scratch2;
  Register pointer_reg = feedback;
  __ LoadP(too_far, FieldMemOperand(feedback, FixedArray::kLengthOffset));

  // +-----+------+------+-----+-----+-----+ ... ----+
  // | map | len  | wm0  | wt0 | h0  | wm1 |      hN |
  // +-----+------+------+-----+-----+ ----+ ... ----+
  //                 0      1     2              len-1
  //                 ^                                 ^
  //                 |                                 |
  //             pointer_reg                        too_far
  //             aka feedback                       scratch2
  // also need receiver_map
  // use cached_map (scratch1) to look in the weak map values.
  __ SmiToPtrArrayOffset(r0, too_far);
  __ AddP(too_far, feedback, r0);
  __ AddP(too_far, too_far, Operand(FixedArray::kHeaderSize - kHeapObjectTag));
  __ AddP(pointer_reg, feedback,
          Operand(FixedArray::OffsetOfElementAt(0) - kHeapObjectTag));

  __ bind(&next_loop);
  __ LoadP(cached_map, MemOperand(pointer_reg));
  __ LoadP(cached_map, FieldMemOperand(cached_map, WeakCell::kValueOffset));
  __ CmpP(receiver_map, cached_map);
  __ bne(&prepare_next);
  // Is it a transitioning store?
  __ LoadP(too_far, MemOperand(pointer_reg, kPointerSize));
  __ CompareRoot(too_far, Heap::kUndefinedValueRootIndex);
  __ bne(&transition_call);
  __ LoadP(pointer_reg, MemOperand(pointer_reg, kPointerSize * 2));
  __ AddP(ip, pointer_reg, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ Jump(ip);

  __ bind(&transition_call);
  __ LoadP(too_far, FieldMemOperand(too_far, WeakCell::kValueOffset));
  __ JumpIfSmi(too_far, miss);

  __ LoadP(receiver_map, MemOperand(pointer_reg, kPointerSize * 2));

  // Load the map into the correct register.
  DCHECK(feedback.is(VectorStoreTransitionDescriptor::MapRegister()));
  __ LoadRR(feedback, too_far);

  __ AddP(ip, receiver_map, Operand(Code::kHeaderSize - kHeapObjectTag));
  __ Jump(ip);

  __ bind(&prepare_next);
  __ AddP(pointer_reg, pointer_reg, Operand(kPointerSize * 3));
  __ CmpLogicalP(pointer_reg, too_far);
  __ blt(&next_loop);

  // We exhausted our array of map handler pairs.
  __ b(miss);
}

void VectorKeyedStoreICStub::GenerateImpl(MacroAssembler* masm, bool in_frame) {
  Register receiver = VectorStoreICDescriptor::ReceiverRegister();  // r3
  Register key = VectorStoreICDescriptor::NameRegister();           // r4
  Register vector = VectorStoreICDescriptor::VectorRegister();      // r5
  Register slot = VectorStoreICDescriptor::SlotRegister();          // r6
  DCHECK(VectorStoreICDescriptor::ValueRegister().is(r2));          // r2
  Register feedback = r7;
  Register receiver_map = r8;
  Register scratch1 = r9;

  __ SmiToPtrArrayOffset(r0, slot);
  __ AddP(feedback, vector, r0);
  __ LoadP(feedback, FieldMemOperand(feedback, FixedArray::kHeaderSize));

  // Try to quickly handle the monomorphic case without knowing for sure
  // if we have a weak cell in feedback. We do know it's safe to look
  // at WeakCell::kValueOffset.
  Label try_array, load_smi_map, compare_map;
  Label not_array, miss;
  HandleMonomorphicCase(masm, receiver, receiver_map, feedback, vector, slot,
                        scratch1, &compare_map, &load_smi_map, &try_array);

  __ bind(&try_array);
  // Is it a fixed array?
  __ LoadP(scratch1, FieldMemOperand(feedback, HeapObject::kMapOffset));
  __ CompareRoot(scratch1, Heap::kFixedArrayMapRootIndex);
  __ bne(&not_array);

  // We have a polymorphic element handler.
  Label polymorphic, try_poly_name;
  __ bind(&polymorphic);

  Register scratch2 = ip;

  HandlePolymorphicStoreCase(masm, feedback, receiver_map, scratch1, scratch2,
                             &miss);

  __ bind(&not_array);
  // Is it generic?
  __ CompareRoot(feedback, Heap::kmegamorphic_symbolRootIndex);
  __ bne(&try_poly_name);
  Handle<Code> megamorphic_stub =
      KeyedStoreIC::ChooseMegamorphicStub(masm->isolate(), GetExtraICState());
  __ Jump(megamorphic_stub, RelocInfo::CODE_TARGET);

  __ bind(&try_poly_name);
  // We might have a name in feedback, and a fixed array in the next slot.
  __ CmpP(key, feedback);
  __ bne(&miss);
  // If the name comparison succeeded, we know we have a fixed array with
  // at least one map/handler pair.
  __ SmiToPtrArrayOffset(r0, slot);
  __ AddP(feedback, vector, r0);
  __ LoadP(feedback,
           FieldMemOperand(feedback, FixedArray::kHeaderSize + kPointerSize));
  HandleArrayCases(masm, feedback, receiver_map, scratch1, scratch2, false,
                   &miss);

  __ bind(&miss);
  KeyedStoreIC::GenerateMiss(masm);

  __ bind(&load_smi_map);
  __ LoadRoot(receiver_map, Heap::kHeapNumberMapRootIndex);
  __ b(&compare_map);
}

void ProfileEntryHookStub::MaybeCallEntryHook(MacroAssembler* masm) {
  if (masm->isolate()->function_entry_hook() != NULL) {
    PredictableCodeSizeScope predictable(masm,
#if V8_TARGET_ARCH_S390X
                                         40);
#elif V8_HOST_ARCH_S390
                                         36);
#else
                                         32);
#endif
    ProfileEntryHookStub stub(masm->isolate());
    __ CleanseP(r14);
    __ Push(r14, ip);
    __ CallStub(&stub);  // BRASL
    __ Pop(r14, ip);
  }
}

void ProfileEntryHookStub::Generate(MacroAssembler* masm) {
// The entry hook is a "push lr" instruction (LAY+ST/STG), followed by a call.
#if V8_TARGET_ARCH_S390X
  const int32_t kReturnAddressDistanceFromFunctionStart =
      Assembler::kCallTargetAddressOffset + 18;  // LAY + STG * 2
#elif V8_HOST_ARCH_S390
  const int32_t kReturnAddressDistanceFromFunctionStart =
      Assembler::kCallTargetAddressOffset + 18;  // NILH + LAY + ST * 2
#else
  const int32_t kReturnAddressDistanceFromFunctionStart =
      Assembler::kCallTargetAddressOffset + 14;  // LAY + ST * 2
#endif

  // This should contain all kJSCallerSaved registers.
  const RegList kSavedRegs = kJSCallerSaved |  // Caller saved registers.
                             r7.bit();         // Saved stack pointer.

  // We also save r14+ip, so count here is one higher than the mask indicates.
  const int32_t kNumSavedRegs = kNumJSCallerSaved + 3;

  // Save all caller-save registers as this may be called from anywhere.
  __ CleanseP(r14);
  __ LoadRR(ip, r14);
  __ MultiPush(kSavedRegs | ip.bit());

  // Compute the function's address for the first argument.

  __ SubP(r2, ip, Operand(kReturnAddressDistanceFromFunctionStart));

  // The caller's return address is two slots above the saved temporaries.
  // Grab that for the second argument to the hook.
  __ lay(r3, MemOperand(sp, kNumSavedRegs * kPointerSize));

  // Align the stack if necessary.
  int frame_alignment = masm->ActivationFrameAlignment();
  if (frame_alignment > kPointerSize) {
    __ LoadRR(r7, sp);
    DCHECK(base::bits::IsPowerOfTwo32(frame_alignment));
    __ ClearRightImm(sp, sp, Operand(WhichPowerOf2(frame_alignment)));
  }

#if !defined(USE_SIMULATOR)
  uintptr_t entry_hook =
      reinterpret_cast<uintptr_t>(isolate()->function_entry_hook());
  __ mov(ip, Operand(entry_hook));

#if ABI_USES_FUNCTION_DESCRIPTORS
  // Function descriptor
  __ LoadP(ToRegister(ABI_TOC_REGISTER), MemOperand(ip, kPointerSize));
  __ LoadP(ip, MemOperand(ip, 0));
// ip already set.
#endif
#endif

  // zLinux ABI requires caller's frame to have sufficient space for callee
  // preserved regsiter save area.
  __ LoadImmP(r0, Operand::Zero());
  __ lay(sp, MemOperand(sp, -kCalleeRegisterSaveAreaSize -
                                kNumRequiredStackFrameSlots * kPointerSize));
  __ StoreP(r0, MemOperand(sp));
#if defined(USE_SIMULATOR)
  // Under the simulator we need to indirect the entry hook through a
  // trampoline function at a known address.
  // It additionally takes an isolate as a third parameter
  __ mov(r4, Operand(ExternalReference::isolate_address(isolate())));

  ApiFunction dispatcher(FUNCTION_ADDR(EntryHookTrampoline));
  __ mov(ip, Operand(ExternalReference(
                 &dispatcher, ExternalReference::BUILTIN_CALL, isolate())));
#endif
  __ Call(ip);

  // zLinux ABI requires caller's frame to have sufficient space for callee
  // preserved regsiter save area.
  __ la(sp, MemOperand(sp, kCalleeRegisterSaveAreaSize +
                               kNumRequiredStackFrameSlots * kPointerSize));

  // Restore the stack pointer if needed.
  if (frame_alignment > kPointerSize) {
    __ LoadRR(sp, r7);
  }

  // Also pop lr to get Ret(0).
  __ MultiPop(kSavedRegs | ip.bit());
  __ LoadRR(r14, ip);
  __ Ret();
}

template <class T>
static void CreateArrayDispatch(MacroAssembler* masm,
                                AllocationSiteOverrideMode mode) {
  if (mode == DISABLE_ALLOCATION_SITES) {
    T stub(masm->isolate(), GetInitialFastElementsKind(), mode);
    __ TailCallStub(&stub);
  } else if (mode == DONT_OVERRIDE) {
    int last_index =
        GetSequenceIndexFromFastElementsKind(TERMINAL_FAST_ELEMENTS_KIND);
    for (int i = 0; i <= last_index; ++i) {
      ElementsKind kind = GetFastElementsKindFromSequenceIndex(i);
      __ CmpP(r5, Operand(kind));
      T stub(masm->isolate(), kind);
      __ TailCallStub(&stub, eq);
    }

    // If we reached this point there is a problem.
    __ Abort(kUnexpectedElementsKindInArrayConstructor);
  } else {
    UNREACHABLE();
  }
}

static void CreateArrayDispatchOneArgument(MacroAssembler* masm,
                                           AllocationSiteOverrideMode mode) {
  // r4 - allocation site (if mode != DISABLE_ALLOCATION_SITES)
  // r5 - kind (if mode != DISABLE_ALLOCATION_SITES)
  // r2 - number of arguments
  // r3 - constructor?
  // sp[0] - last argument
  Label normal_sequence;
  if (mode == DONT_OVERRIDE) {
    STATIC_ASSERT(FAST_SMI_ELEMENTS == 0);
    STATIC_ASSERT(FAST_HOLEY_SMI_ELEMENTS == 1);
    STATIC_ASSERT(FAST_ELEMENTS == 2);
    STATIC_ASSERT(FAST_HOLEY_ELEMENTS == 3);
    STATIC_ASSERT(FAST_DOUBLE_ELEMENTS == 4);
    STATIC_ASSERT(FAST_HOLEY_DOUBLE_ELEMENTS == 5);

    // is the low bit set? If so, we are holey and that is good.
    __ AndP(r0, r5, Operand(1));
    __ bne(&normal_sequence);
  }

  // look at the first argument
  __ LoadP(r7, MemOperand(sp, 0));
  __ CmpP(r7, Operand::Zero());
  __ beq(&normal_sequence);

  if (mode == DISABLE_ALLOCATION_SITES) {
    ElementsKind initial = GetInitialFastElementsKind();
    ElementsKind holey_initial = GetHoleyElementsKind(initial);

    ArraySingleArgumentConstructorStub stub_holey(
        masm->isolate(), holey_initial, DISABLE_ALLOCATION_SITES);
    __ TailCallStub(&stub_holey);

    __ bind(&normal_sequence);
    ArraySingleArgumentConstructorStub stub(masm->isolate(), initial,
                                            DISABLE_ALLOCATION_SITES);
    __ TailCallStub(&stub);
  } else if (mode == DONT_OVERRIDE) {
    // We are going to create a holey array, but our kind is non-holey.
    // Fix kind and retry (only if we have an allocation site in the slot).
    __ AddP(r5, r5, Operand(1));
    if (FLAG_debug_code) {
      __ LoadP(r7, FieldMemOperand(r4, 0));
      __ CompareRoot(r7, Heap::kAllocationSiteMapRootIndex);
      __ Assert(eq, kExpectedAllocationSite);
    }

    // Save the resulting elements kind in type info. We can't just store r5
    // in the AllocationSite::transition_info field because elements kind is
    // restricted to a portion of the field...upper bits need to be left alone.
    STATIC_ASSERT(AllocationSite::ElementsKindBits::kShift == 0);
    __ LoadP(r6, FieldMemOperand(r4, AllocationSite::kTransitionInfoOffset));
    __ AddSmiLiteral(r6, r6, Smi::FromInt(kFastElementsKindPackedToHoley), r0);
    __ StoreP(r6, FieldMemOperand(r4, AllocationSite::kTransitionInfoOffset));

    __ bind(&normal_sequence);
    int last_index =
        GetSequenceIndexFromFastElementsKind(TERMINAL_FAST_ELEMENTS_KIND);
    for (int i = 0; i <= last_index; ++i) {
      ElementsKind kind = GetFastElementsKindFromSequenceIndex(i);
      __ CmpP(r5, Operand(kind));
      ArraySingleArgumentConstructorStub stub(masm->isolate(), kind);
      __ TailCallStub(&stub, eq);
    }

    // If we reached this point there is a problem.
    __ Abort(kUnexpectedElementsKindInArrayConstructor);
  } else {
    UNREACHABLE();
  }
}

template <class T>
static void ArrayConstructorStubAheadOfTimeHelper(Isolate* isolate) {
  int to_index =
      GetSequenceIndexFromFastElementsKind(TERMINAL_FAST_ELEMENTS_KIND);
  for (int i = 0; i <= to_index; ++i) {
    ElementsKind kind = GetFastElementsKindFromSequenceIndex(i);
    T stub(isolate, kind);
    stub.GetCode();
    if (AllocationSite::GetMode(kind) != DONT_TRACK_ALLOCATION_SITE) {
      T stub1(isolate, kind, DISABLE_ALLOCATION_SITES);
      stub1.GetCode();
    }
  }
}

void ArrayConstructorStubBase::GenerateStubsAheadOfTime(Isolate* isolate) {
  ArrayConstructorStubAheadOfTimeHelper<ArrayNoArgumentConstructorStub>(
      isolate);
  ArrayConstructorStubAheadOfTimeHelper<ArraySingleArgumentConstructorStub>(
      isolate);
  ArrayConstructorStubAheadOfTimeHelper<ArrayNArgumentsConstructorStub>(
      isolate);
}

void InternalArrayConstructorStubBase::GenerateStubsAheadOfTime(
    Isolate* isolate) {
  ElementsKind kinds[2] = {FAST_ELEMENTS, FAST_HOLEY_ELEMENTS};
  for (int i = 0; i < 2; i++) {
    // For internal arrays we only need a few things
    InternalArrayNoArgumentConstructorStub stubh1(isolate, kinds[i]);
    stubh1.GetCode();
    InternalArraySingleArgumentConstructorStub stubh2(isolate, kinds[i]);
    stubh2.GetCode();
    InternalArrayNArgumentsConstructorStub stubh3(isolate, kinds[i]);
    stubh3.GetCode();
  }
}

void ArrayConstructorStub::GenerateDispatchToArrayStub(
    MacroAssembler* masm, AllocationSiteOverrideMode mode) {
  if (argument_count() == ANY) {
    Label not_zero_case, not_one_case;
    __ CmpP(r2, Operand::Zero());
    __ bne(&not_zero_case);
    CreateArrayDispatch<ArrayNoArgumentConstructorStub>(masm, mode);

    __ bind(&not_zero_case);
    __ CmpP(r2, Operand(1));
    __ bgt(&not_one_case);
    CreateArrayDispatchOneArgument(masm, mode);

    __ bind(&not_one_case);
    CreateArrayDispatch<ArrayNArgumentsConstructorStub>(masm, mode);
  } else if (argument_count() == NONE) {
    CreateArrayDispatch<ArrayNoArgumentConstructorStub>(masm, mode);
  } else if (argument_count() == ONE) {
    CreateArrayDispatchOneArgument(masm, mode);
  } else if (argument_count() == MORE_THAN_ONE) {
    CreateArrayDispatch<ArrayNArgumentsConstructorStub>(masm, mode);
  } else {
    UNREACHABLE();
  }
}

void ArrayConstructorStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r2 : argc (only if argument_count() == ANY)
  //  -- r3 : constructor
  //  -- r4 : AllocationSite or undefined
  //  -- r5 : new target
  //  -- sp[0] : return address
  //  -- sp[4] : last argument
  // -----------------------------------

  if (FLAG_debug_code) {
    // The array construct code is only set for the global and natives
    // builtin Array functions which always have maps.

    // Initial map for the builtin Array function should be a map.
    __ LoadP(r6, FieldMemOperand(r3, JSFunction::kPrototypeOrInitialMapOffset));
    // Will both indicate a NULL and a Smi.
    __ TestIfSmi(r6);
    __ Assert(ne, kUnexpectedInitialMapForArrayFunction, cr0);
    __ CompareObjectType(r6, r6, r7, MAP_TYPE);
    __ Assert(eq, kUnexpectedInitialMapForArrayFunction);

    // We should either have undefined in r4 or a valid AllocationSite
    __ AssertUndefinedOrAllocationSite(r4, r6);
  }

  // Enter the context of the Array function.
  __ LoadP(cp, FieldMemOperand(r3, JSFunction::kContextOffset));

  Label subclassing;
  __ CmpP(r5, r3);
  __ bne(&subclassing, Label::kNear);

  Label no_info;
  // Get the elements kind and case on that.
  __ CompareRoot(r4, Heap::kUndefinedValueRootIndex);
  __ beq(&no_info);

  __ LoadP(r5, FieldMemOperand(r4, AllocationSite::kTransitionInfoOffset));
  __ SmiUntag(r5);
  STATIC_ASSERT(AllocationSite::ElementsKindBits::kShift == 0);
  __ AndP(r5, Operand(AllocationSite::ElementsKindBits::kMask));
  GenerateDispatchToArrayStub(masm, DONT_OVERRIDE);

  __ bind(&no_info);
  GenerateDispatchToArrayStub(masm, DISABLE_ALLOCATION_SITES);

  __ bind(&subclassing);
  switch (argument_count()) {
    case ANY:
    case MORE_THAN_ONE:
      __ ShiftLeftP(r1, r2, Operand(kPointerSizeLog2));
      __ StoreP(r3, MemOperand(sp, r1));
      __ AddP(r2, r2, Operand(3));
      break;
    case NONE:
      __ StoreP(r3, MemOperand(sp, 0 * kPointerSize));
      __ LoadImmP(r2, Operand(3));
      break;
    case ONE:
      __ StoreP(r3, MemOperand(sp, 1 * kPointerSize));
      __ LoadImmP(r2, Operand(4));
      break;
  }

  __ Push(r5, r4);
  __ JumpToExternalReference(ExternalReference(Runtime::kNewArray, isolate()));
}

void InternalArrayConstructorStub::GenerateCase(MacroAssembler* masm,
                                                ElementsKind kind) {
  __ CmpLogicalP(r2, Operand(1));

  InternalArrayNoArgumentConstructorStub stub0(isolate(), kind);
  __ TailCallStub(&stub0, lt);

  InternalArrayNArgumentsConstructorStub stubN(isolate(), kind);
  __ TailCallStub(&stubN, gt);

  if (IsFastPackedElementsKind(kind)) {
    // We might need to create a holey array
    // look at the first argument
    __ LoadP(r5, MemOperand(sp, 0));
    __ CmpP(r5, Operand::Zero());

    InternalArraySingleArgumentConstructorStub stub1_holey(
        isolate(), GetHoleyElementsKind(kind));
    __ TailCallStub(&stub1_holey, ne);
  }

  InternalArraySingleArgumentConstructorStub stub1(isolate(), kind);
  __ TailCallStub(&stub1);
}

void InternalArrayConstructorStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r2 : argc
  //  -- r3 : constructor
  //  -- sp[0] : return address
  //  -- sp[4] : last argument
  // -----------------------------------

  if (FLAG_debug_code) {
    // The array construct code is only set for the global and natives
    // builtin Array functions which always have maps.

    // Initial map for the builtin Array function should be a map.
    __ LoadP(r5, FieldMemOperand(r3, JSFunction::kPrototypeOrInitialMapOffset));
    // Will both indicate a NULL and a Smi.
    __ TestIfSmi(r5);
    __ Assert(ne, kUnexpectedInitialMapForArrayFunction, cr0);
    __ CompareObjectType(r5, r5, r6, MAP_TYPE);
    __ Assert(eq, kUnexpectedInitialMapForArrayFunction);
  }

  // Figure out the right elements kind
  __ LoadP(r5, FieldMemOperand(r3, JSFunction::kPrototypeOrInitialMapOffset));
  // Load the map's "bit field 2" into |result|.
  __ LoadlB(r5, FieldMemOperand(r5, Map::kBitField2Offset));
  // Retrieve elements_kind from bit field 2.
  __ DecodeField<Map::ElementsKindBits>(r5);

  if (FLAG_debug_code) {
    Label done;
    __ CmpP(r5, Operand(FAST_ELEMENTS));
    __ beq(&done);
    __ CmpP(r5, Operand(FAST_HOLEY_ELEMENTS));
    __ Assert(eq, kInvalidElementsKindForInternalArrayOrInternalPackedArray);
    __ bind(&done);
  }

  Label fast_elements_case;
  __ CmpP(r5, Operand(FAST_ELEMENTS));
  __ beq(&fast_elements_case);
  GenerateCase(masm, FAST_HOLEY_ELEMENTS);

  __ bind(&fast_elements_case);
  GenerateCase(masm, FAST_ELEMENTS);
}

void FastNewObjectStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r3 : target
  //  -- r5 : new target
  //  -- cp : context
  //  -- lr : return address
  // -----------------------------------
  __ AssertFunction(r3);
  __ AssertReceiver(r5);

  // Verify that the new target is a JSFunction.
  Label new_object;
  __ CompareObjectType(r5, r4, r4, JS_FUNCTION_TYPE);
  __ bne(&new_object);

  // Load the initial map and verify that it's in fact a map.
  __ LoadP(r4, FieldMemOperand(r5, JSFunction::kPrototypeOrInitialMapOffset));
  __ JumpIfSmi(r4, &new_object);
  __ CompareObjectType(r4, r2, r2, MAP_TYPE);
  __ bne(&new_object);

  // Fall back to runtime if the target differs from the new target's
  // initial map constructor.
  __ LoadP(r2, FieldMemOperand(r4, Map::kConstructorOrBackPointerOffset));
  __ CmpP(r2, r3);
  __ bne(&new_object);

  // Allocate the JSObject on the heap.
  Label allocate, done_allocate;
  __ LoadlB(r6, FieldMemOperand(r4, Map::kInstanceSizeOffset));
  __ Allocate(r6, r2, r7, r8, &allocate, SIZE_IN_WORDS);
  __ bind(&done_allocate);

  // Initialize the JSObject fields.
  __ StoreP(r4, MemOperand(r2, JSObject::kMapOffset));
  __ LoadRoot(r5, Heap::kEmptyFixedArrayRootIndex);
  __ StoreP(r5, MemOperand(r2, JSObject::kPropertiesOffset));
  __ StoreP(r5, MemOperand(r2, JSObject::kElementsOffset));
  STATIC_ASSERT(JSObject::kHeaderSize == 3 * kPointerSize);
  __ AddP(r3, r2, Operand(JSObject::kHeaderSize));

  // ----------- S t a t e -------------
  //  -- r2 : result (untagged)
  //  -- r3 : result fields (untagged)
  //  -- r7 : result end (untagged)
  //  -- r4 : initial map
  //  -- cp : context
  //  -- lr : return address
  // -----------------------------------

  // Perform in-object slack tracking if requested.
  Label slack_tracking;
  STATIC_ASSERT(Map::kNoSlackTracking == 0);
  __ LoadRoot(r8, Heap::kUndefinedValueRootIndex);
  __ LoadlW(r5, FieldMemOperand(r4, Map::kBitField3Offset));
  __ DecodeField<Map::ConstructionCounter>(r9, r5);
  __ LoadAndTestP(r9, r9);
  __ bne(&slack_tracking);
  {
    // Initialize all in-object fields with undefined.
    __ InitializeFieldsWithFiller(r3, r7, r8);

    // Add the object tag to make the JSObject real.
    __ AddP(r2, r2, Operand(kHeapObjectTag));
    __ Ret();
  }
  __ bind(&slack_tracking);
  {
    // Decrease generous allocation count.
    STATIC_ASSERT(Map::ConstructionCounter::kNext == 32);
    __ Add32(r5, r5, Operand(-(1 << Map::ConstructionCounter::kShift)));
    __ StoreW(r5, FieldMemOperand(r4, Map::kBitField3Offset));

    // Initialize the in-object fields with undefined.
    __ LoadlB(r6, FieldMemOperand(r4, Map::kUnusedPropertyFieldsOffset));
    __ ShiftLeftP(r6, r6, Operand(kPointerSizeLog2));
    __ SubP(r6, r7, r6);
    __ InitializeFieldsWithFiller(r3, r6, r8);

    // Initialize the remaining (reserved) fields with one pointer filler map.
    __ LoadRoot(r8, Heap::kOnePointerFillerMapRootIndex);
    __ InitializeFieldsWithFiller(r3, r7, r8);

    // Add the object tag to make the JSObject real.
    __ AddP(r2, r2, Operand(kHeapObjectTag));

    // Check if we can finalize the instance size.
    __ CmpP(r9, Operand(Map::kSlackTrackingCounterEnd));
    __ Ret(ne);

    // Finalize the instance size.
    {
      FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
      __ Push(r2, r4);
      __ CallRuntime(Runtime::kFinalizeInstanceSize);
      __ Pop(r2);
    }
    __ Ret();
  }

  // Fall back to %AllocateInNewSpace.
  __ bind(&allocate);
  {
    FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
    STATIC_ASSERT(kSmiTag == 0);
    __ ShiftLeftP(r6, r6,
                  Operand(kPointerSizeLog2 + kSmiTagSize + kSmiShiftSize));
    __ Push(r4, r6);
    __ CallRuntime(Runtime::kAllocateInNewSpace);
    __ Pop(r4);
  }
  __ SubP(r2, r2, Operand(kHeapObjectTag));
  __ LoadlB(r7, FieldMemOperand(r4, Map::kInstanceSizeOffset));
  __ ShiftLeftP(r7, r7, Operand(kPointerSizeLog2));
  __ AddP(r7, r2, r7);
  __ b(&done_allocate);

  // Fall back to %NewObject.
  __ bind(&new_object);
  __ Push(r3, r5);
  __ TailCallRuntime(Runtime::kNewObject);
}

void FastNewRestParameterStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r3 : function
  //  -- cp : context
  //  -- fp : frame pointer
  //  -- lr : return address
  // -----------------------------------
  __ AssertFunction(r3);

  // For Ignition we need to skip all possible handler/stub frames until
  // we reach the JavaScript frame for the function (similar to what the
  // runtime fallback implementation does). So make r4 point to that
  // JavaScript frame.
  {
    Label loop, loop_entry;
    __ LoadRR(r4, fp);
    __ b(&loop_entry);
    __ bind(&loop);
    __ LoadP(r4, MemOperand(r4, StandardFrameConstants::kCallerFPOffset));
    __ bind(&loop_entry);
    __ LoadP(ip, MemOperand(r4, StandardFrameConstants::kFunctionOffset));
    __ CmpP(ip, r3);
    __ bne(&loop);
  }

  // Check if we have rest parameters (only possible if we have an
  // arguments adaptor frame below the function frame).
  Label no_rest_parameters;
  __ LoadP(r4, MemOperand(r4, StandardFrameConstants::kCallerFPOffset));
  __ LoadP(ip, MemOperand(r4, CommonFrameConstants::kContextOrFrameTypeOffset));
  __ CmpSmiLiteral(ip, Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR), r0);
  __ bne(&no_rest_parameters);

  // Check if the arguments adaptor frame contains more arguments than
  // specified by the function's internal formal parameter count.
  Label rest_parameters;
  __ LoadP(r2, MemOperand(r4, ArgumentsAdaptorFrameConstants::kLengthOffset));
  __ LoadP(r3, FieldMemOperand(r3, JSFunction::kSharedFunctionInfoOffset));
  __ LoadW(
      r3, FieldMemOperand(r3, SharedFunctionInfo::kFormalParameterCountOffset));
#if V8_TARGET_ARCH_S390X
  __ SmiTag(r3);
#endif
  __ SubP(r2, r2, r3);
  __ bgt(&rest_parameters);

  // Return an empty rest parameter array.
  __ bind(&no_rest_parameters);
  {
    // ----------- S t a t e -------------
    //  -- cp : context
    //  -- lr : return address
    // -----------------------------------

    // Allocate an empty rest parameter array.
    Label allocate, done_allocate;
    __ Allocate(JSArray::kSize, r2, r3, r4, &allocate, TAG_OBJECT);
    __ bind(&done_allocate);

    // Setup the rest parameter array in r0.
    __ LoadNativeContextSlot(Context::JS_ARRAY_FAST_ELEMENTS_MAP_INDEX, r3);
    __ StoreP(r3, FieldMemOperand(r2, JSArray::kMapOffset), r0);
    __ LoadRoot(r3, Heap::kEmptyFixedArrayRootIndex);
    __ StoreP(r3, FieldMemOperand(r2, JSArray::kPropertiesOffset), r0);
    __ StoreP(r3, FieldMemOperand(r2, JSArray::kElementsOffset), r0);
    __ LoadImmP(r3, Operand::Zero());
    __ StoreP(r3, FieldMemOperand(r2, JSArray::kLengthOffset), r0);
    STATIC_ASSERT(JSArray::kSize == 4 * kPointerSize);
    __ Ret();

    // Fall back to %AllocateInNewSpace.
    __ bind(&allocate);
    {
      FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
      __ Push(Smi::FromInt(JSArray::kSize));
      __ CallRuntime(Runtime::kAllocateInNewSpace);
    }
    __ b(&done_allocate);
  }

  __ bind(&rest_parameters);
  {
    // Compute the pointer to the first rest parameter (skippping the receiver).
    __ SmiToPtrArrayOffset(r8, r2);
    __ AddP(r4, r4, r8);
    __ AddP(r4, r4, Operand(StandardFrameConstants::kCallerSPOffset));

    // ----------- S t a t e -------------
    //  -- cp : context
    //  -- r2 : number of rest parameters (tagged)
    //  -- r4 : pointer just past first rest parameters
    //  -- r8 : size of rest parameters
    //  -- lr : return address
    // -----------------------------------

    // Allocate space for the rest parameter array plus the backing store.
    Label allocate, done_allocate;
    __ mov(r3, Operand(JSArray::kSize + FixedArray::kHeaderSize));
    __ AddP(r3, r3, r8);
    __ Allocate(r3, r5, r6, r7, &allocate, TAG_OBJECT);
    __ bind(&done_allocate);

    // Setup the elements array in r5.
    __ LoadRoot(r3, Heap::kFixedArrayMapRootIndex);
    __ StoreP(r3, FieldMemOperand(r5, FixedArray::kMapOffset), r0);
    __ StoreP(r2, FieldMemOperand(r5, FixedArray::kLengthOffset), r0);
    __ AddP(r6, r5,
            Operand(FixedArray::kHeaderSize - kHeapObjectTag - kPointerSize));
    {
      Label loop;
      __ SmiUntag(r1, r2);
      // __ mtctr(r0);
      __ bind(&loop);
      __ lay(r4, MemOperand(r4, -kPointerSize));
      __ LoadP(ip, MemOperand(r4));
      __ la(r6, MemOperand(r6, kPointerSize));
      __ StoreP(ip, MemOperand(r6));
      // __ bdnz(&loop);
      __ BranchOnCount(r1, &loop);
      __ AddP(r6, r6, Operand(kPointerSize));
    }

    // Setup the rest parameter array in r6.
    __ LoadNativeContextSlot(Context::JS_ARRAY_FAST_ELEMENTS_MAP_INDEX, r3);
    __ StoreP(r3, MemOperand(r6, JSArray::kMapOffset));
    __ LoadRoot(r3, Heap::kEmptyFixedArrayRootIndex);
    __ StoreP(r3, MemOperand(r6, JSArray::kPropertiesOffset));
    __ StoreP(r5, MemOperand(r6, JSArray::kElementsOffset));
    __ StoreP(r2, MemOperand(r6, JSArray::kLengthOffset));
    STATIC_ASSERT(JSArray::kSize == 4 * kPointerSize);
    __ AddP(r2, r6, Operand(kHeapObjectTag));
    __ Ret();

    // Fall back to %AllocateInNewSpace.
    __ bind(&allocate);
    {
      FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
      __ SmiTag(r3);
      __ Push(r2, r4, r3);
      __ CallRuntime(Runtime::kAllocateInNewSpace);
      __ LoadRR(r5, r2);
      __ Pop(r2, r4);
    }
    __ b(&done_allocate);
  }
}

void FastNewSloppyArgumentsStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r3 : function
  //  -- cp : context
  //  -- fp : frame pointer
  //  -- lr : return address
  // -----------------------------------
  __ AssertFunction(r3);

  // TODO(bmeurer): Cleanup to match the FastNewStrictArgumentsStub.
  __ LoadP(r4, FieldMemOperand(r3, JSFunction::kSharedFunctionInfoOffset));
  __ LoadW(
      r4, FieldMemOperand(r4, SharedFunctionInfo::kFormalParameterCountOffset));
#if V8_TARGET_ARCH_S390X
  __ SmiTag(r4);
#endif
  __ SmiToPtrArrayOffset(r5, r4);
  __ AddP(r5, fp, r5);
  __ AddP(r5, r5, Operand(StandardFrameConstants::kCallerSPOffset));

  // r3 : function
  // r4 : number of parameters (tagged)
  // r5 : parameters pointer
  // Registers used over whole function:
  // r7 : arguments count (tagged)
  // r8 : mapped parameter count (tagged)

  // Check if the calling frame is an arguments adaptor frame.
  Label adaptor_frame, try_allocate, runtime;
  __ LoadP(r6, MemOperand(fp, StandardFrameConstants::kCallerFPOffset));
  __ LoadP(r2, MemOperand(r6, CommonFrameConstants::kContextOrFrameTypeOffset));
  __ CmpSmiLiteral(r2, Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR), r0);
  __ beq(&adaptor_frame);

  // No adaptor, parameter count = argument count.
  __ LoadRR(r7, r4);
  __ LoadRR(r8, r4);
  __ b(&try_allocate);

  // We have an adaptor frame. Patch the parameters pointer.
  __ bind(&adaptor_frame);
  __ LoadP(r7, MemOperand(r6, ArgumentsAdaptorFrameConstants::kLengthOffset));
  __ SmiToPtrArrayOffset(r5, r7);
  __ AddP(r5, r5, r6);
  __ AddP(r5, r5, Operand(StandardFrameConstants::kCallerSPOffset));

  // r7 = argument count (tagged)
  // r8 = parameter count (tagged)
  // Compute the mapped parameter count = min(r4, r7) in r8.
  __ CmpP(r4, r7);
  Label skip;
  __ LoadRR(r8, r4);
  __ blt(&skip);
  __ LoadRR(r8, r7);
  __ bind(&skip);

  __ bind(&try_allocate);

  // Compute the sizes of backing store, parameter map, and arguments object.
  // 1. Parameter map, has 2 extra words containing context and backing store.
  const int kParameterMapHeaderSize =
      FixedArray::kHeaderSize + 2 * kPointerSize;
  // If there are no mapped parameters, we do not need the parameter_map.
  __ CmpSmiLiteral(r8, Smi::FromInt(0), r0);
  Label skip2, skip3;
  __ bne(&skip2);
  __ LoadImmP(r1, Operand::Zero());
  __ b(&skip3);
  __ bind(&skip2);
  __ SmiToPtrArrayOffset(r1, r8);
  __ AddP(r1, r1, Operand(kParameterMapHeaderSize));
  __ bind(&skip3);

  // 2. Backing store.
  __ SmiToPtrArrayOffset(r6, r7);
  __ AddP(r1, r1, r6);
  __ AddP(r1, r1, Operand(FixedArray::kHeaderSize));

  // 3. Arguments object.
  __ AddP(r1, r1, Operand(JSSloppyArgumentsObject::kSize));

  // Do the allocation of all three objects in one go.
  __ Allocate(r1, r2, r1, r6, &runtime, TAG_OBJECT);

  // r2 = address of new object(s) (tagged)
  // r4 = argument count (smi-tagged)
  // Get the arguments boilerplate from the current native context into r3.
  const int kNormalOffset =
      Context::SlotOffset(Context::SLOPPY_ARGUMENTS_MAP_INDEX);
  const int kAliasedOffset =
      Context::SlotOffset(Context::FAST_ALIASED_ARGUMENTS_MAP_INDEX);

  __ LoadP(r6, NativeContextMemOperand());
  __ CmpP(r8, Operand::Zero());
  Label skip4, skip5;
  __ bne(&skip4);
  __ LoadP(r6, MemOperand(r6, kNormalOffset));
  __ b(&skip5);
  __ bind(&skip4);
  __ LoadP(r6, MemOperand(r6, kAliasedOffset));
  __ bind(&skip5);

  // r2 = address of new object (tagged)
  // r4 = argument count (smi-tagged)
  // r6 = address of arguments map (tagged)
  // r8 = mapped parameter count (tagged)
  __ StoreP(r6, FieldMemOperand(r2, JSObject::kMapOffset), r0);
  __ LoadRoot(r1, Heap::kEmptyFixedArrayRootIndex);
  __ StoreP(r1, FieldMemOperand(r2, JSObject::kPropertiesOffset), r0);
  __ StoreP(r1, FieldMemOperand(r2, JSObject::kElementsOffset), r0);

  // Set up the callee in-object property.
  __ AssertNotSmi(r3);
  __ StoreP(r3, FieldMemOperand(r2, JSSloppyArgumentsObject::kCalleeOffset),
            r0);

  // Use the length (smi tagged) and set that as an in-object property too.
  __ AssertSmi(r7);
  __ StoreP(r7, FieldMemOperand(r2, JSSloppyArgumentsObject::kLengthOffset),
            r0);

  // Set up the elements pointer in the allocated arguments object.
  // If we allocated a parameter map, r6 will point there, otherwise
  // it will point to the backing store.
  __ AddP(r6, r2, Operand(JSSloppyArgumentsObject::kSize));
  __ StoreP(r6, FieldMemOperand(r2, JSObject::kElementsOffset), r0);

  // r2 = address of new object (tagged)
  // r4 = argument count (tagged)
  // r6 = address of parameter map or backing store (tagged)
  // r8 = mapped parameter count (tagged)
  // Initialize parameter map. If there are no mapped arguments, we're done.
  Label skip_parameter_map;
  __ CmpSmiLiteral(r8, Smi::FromInt(0), r0);
  Label skip6;
  __ bne(&skip6);
  // Move backing store address to r3, because it is
  // expected there when filling in the unmapped arguments.
  __ LoadRR(r3, r6);
  __ b(&skip_parameter_map);
  __ bind(&skip6);

  __ LoadRoot(r7, Heap::kSloppyArgumentsElementsMapRootIndex);
  __ StoreP(r7, FieldMemOperand(r6, FixedArray::kMapOffset), r0);
  __ AddSmiLiteral(r7, r8, Smi::FromInt(2), r0);
  __ StoreP(r7, FieldMemOperand(r6, FixedArray::kLengthOffset), r0);
  __ StoreP(cp, FieldMemOperand(r6, FixedArray::kHeaderSize + 0 * kPointerSize),
            r0);
  __ SmiToPtrArrayOffset(r7, r8);
  __ AddP(r7, r7, r6);
  __ AddP(r7, r7, Operand(kParameterMapHeaderSize));
  __ StoreP(r7, FieldMemOperand(r6, FixedArray::kHeaderSize + 1 * kPointerSize),
            r0);

  // Copy the parameter slots and the holes in the arguments.
  // We need to fill in mapped_parameter_count slots. They index the context,
  // where parameters are stored in reverse order, at
  //   MIN_CONTEXT_SLOTS .. MIN_CONTEXT_SLOTS+parameter_count-1
  // The mapped parameter thus need to get indices
  //   MIN_CONTEXT_SLOTS+parameter_count-1 ..
  //       MIN_CONTEXT_SLOTS+parameter_count-mapped_parameter_count
  // We loop from right to left.
  Label parameters_loop;
  __ LoadRR(r7, r8);
  __ AddSmiLiteral(r1, r4, Smi::FromInt(Context::MIN_CONTEXT_SLOTS), r0);
  __ SubP(r1, r1, r8);
  __ LoadRoot(ip, Heap::kTheHoleValueRootIndex);
  __ SmiToPtrArrayOffset(r3, r7);
  __ AddP(r3, r3, r6);
  __ AddP(r3, r3, Operand(kParameterMapHeaderSize));

  // r3 = address of backing store (tagged)
  // r6 = address of parameter map (tagged)
  // r7 = temporary scratch (a.o., for address calculation)
  // r9 = temporary scratch (a.o., for address calculation)
  // ip = the hole value
  __ SmiUntag(r7);
  __ push(r4);
  __ LoadRR(r4, r7);
  __ ShiftLeftP(r7, r7, Operand(kPointerSizeLog2));
  __ AddP(r9, r3, r7);
  __ AddP(r7, r6, r7);
  __ AddP(r9, r9, Operand(FixedArray::kHeaderSize - kHeapObjectTag));
  __ AddP(r7, r7, Operand(kParameterMapHeaderSize - kHeapObjectTag));

  __ bind(&parameters_loop);
  __ StoreP(r1, MemOperand(r7, -kPointerSize));
  __ lay(r7, MemOperand(r7, -kPointerSize));
  __ StoreP(ip, MemOperand(r9, -kPointerSize));
  __ lay(r9, MemOperand(r9, -kPointerSize));
  __ AddSmiLiteral(r1, r1, Smi::FromInt(1), r0);
  __ BranchOnCount(r4, &parameters_loop);
  __ pop(r4);

  // Restore r7 = argument count (tagged).
  __ LoadP(r7, FieldMemOperand(r2, JSSloppyArgumentsObject::kLengthOffset));

  __ bind(&skip_parameter_map);
  // r2 = address of new object (tagged)
  // r3 = address of backing store (tagged)
  // r7 = argument count (tagged)
  // r8 = mapped parameter count (tagged)
  // r1 = scratch
  // Copy arguments header and remaining slots (if there are any).
  __ LoadRoot(r1, Heap::kFixedArrayMapRootIndex);
  __ StoreP(r1, FieldMemOperand(r3, FixedArray::kMapOffset), r0);
  __ StoreP(r7, FieldMemOperand(r3, FixedArray::kLengthOffset), r0);
  __ SubP(r1, r7, r8);
  __ Ret(eq);

  Label arguments_loop;
  __ SmiUntag(r1);
  __ LoadRR(r4, r1);

  __ SmiToPtrArrayOffset(r0, r8);
  __ SubP(r5, r5, r0);
  __ AddP(r1, r3, r0);
  __ AddP(r1, r1,
          Operand(FixedArray::kHeaderSize - kHeapObjectTag - kPointerSize));

  __ bind(&arguments_loop);
  __ LoadP(r6, MemOperand(r5, -kPointerSize));
  __ lay(r5, MemOperand(r5, -kPointerSize));
  __ StoreP(r6, MemOperand(r1, kPointerSize));
  __ la(r1, MemOperand(r1, kPointerSize));
  __ BranchOnCount(r4, &arguments_loop);

  // Return.
  __ Ret();

  // Do the runtime call to allocate the arguments object.
  // r7 = argument count (tagged)
  __ bind(&runtime);
  __ Push(r3, r5, r7);
  __ TailCallRuntime(Runtime::kNewSloppyArguments);
}

void FastNewStrictArgumentsStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r3 : function
  //  -- cp : context
  //  -- fp : frame pointer
  //  -- lr : return address
  // -----------------------------------
  __ AssertFunction(r3);

  // For Ignition we need to skip all possible handler/stub frames until
  // we reach the JavaScript frame for the function (similar to what the
  // runtime fallback implementation does). So make r4 point to that
  // JavaScript frame.
  {
    Label loop, loop_entry;
    __ LoadRR(r4, fp);
    __ b(&loop_entry);
    __ bind(&loop);
    __ LoadP(r4, MemOperand(r4, StandardFrameConstants::kCallerFPOffset));
    __ bind(&loop_entry);
    __ LoadP(ip, MemOperand(r4, StandardFrameConstants::kFunctionOffset));
    __ CmpP(ip, r3);
    __ bne(&loop);
  }

  // Check if we have an arguments adaptor frame below the function frame.
  Label arguments_adaptor, arguments_done;
  __ LoadP(r5, MemOperand(r4, StandardFrameConstants::kCallerFPOffset));
  __ LoadP(ip, MemOperand(r5, CommonFrameConstants::kContextOrFrameTypeOffset));
  __ CmpSmiLiteral(ip, Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR), r0);
  __ beq(&arguments_adaptor);
  {
    __ LoadP(r3, FieldMemOperand(r3, JSFunction::kSharedFunctionInfoOffset));
    __ LoadW(r2, FieldMemOperand(
                     r3, SharedFunctionInfo::kFormalParameterCountOffset));
#if V8_TARGET_ARCH_S390X
    __ SmiTag(r2);
#endif
    __ SmiToPtrArrayOffset(r8, r2);
    __ AddP(r4, r4, r8);
  }
  __ b(&arguments_done);
  __ bind(&arguments_adaptor);
  {
    __ LoadP(r2, MemOperand(r5, ArgumentsAdaptorFrameConstants::kLengthOffset));
    __ SmiToPtrArrayOffset(r8, r2);
    __ AddP(r4, r5, r8);
  }
  __ bind(&arguments_done);
  __ AddP(r4, r4, Operand(StandardFrameConstants::kCallerSPOffset));

  // ----------- S t a t e -------------
  //  -- cp : context
  //  -- r2 : number of rest parameters (tagged)
  //  -- r4 : pointer just past first rest parameters
  //  -- r8 : size of rest parameters
  //  -- lr : return address
  // -----------------------------------

  // Allocate space for the strict arguments object plus the backing store.
  Label allocate, done_allocate;
  __ mov(r3, Operand(JSStrictArgumentsObject::kSize + FixedArray::kHeaderSize));
  __ AddP(r3, r3, r8);
  __ Allocate(r3, r5, r6, r7, &allocate, TAG_OBJECT);
  __ bind(&done_allocate);

  // Setup the elements array in r5.
  __ LoadRoot(r3, Heap::kFixedArrayMapRootIndex);
  __ StoreP(r3, FieldMemOperand(r5, FixedArray::kMapOffset), r0);
  __ StoreP(r2, FieldMemOperand(r5, FixedArray::kLengthOffset), r0);
  __ AddP(r6, r5,
          Operand(FixedArray::kHeaderSize - kHeapObjectTag - kPointerSize));
  {
    Label loop, done_loop;
    __ SmiUntag(r1, r2);
    __ LoadAndTestP(r1, r1);
    __ beq(&done_loop);
    __ bind(&loop);
    __ lay(r4, MemOperand(r4, -kPointerSize));
    __ LoadP(ip, MemOperand(r4));
    __ la(r6, MemOperand(r6, kPointerSize));
    __ StoreP(ip, MemOperand(r6));
    __ BranchOnCount(r1, &loop);
    __ bind(&done_loop);
    __ AddP(r6, r6, Operand(kPointerSize));
  }

  // Setup the rest parameter array in r6.
  __ LoadNativeContextSlot(Context::STRICT_ARGUMENTS_MAP_INDEX, r3);
  __ StoreP(r3, MemOperand(r6, JSStrictArgumentsObject::kMapOffset));
  __ LoadRoot(r3, Heap::kEmptyFixedArrayRootIndex);
  __ StoreP(r3, MemOperand(r6, JSStrictArgumentsObject::kPropertiesOffset));
  __ StoreP(r5, MemOperand(r6, JSStrictArgumentsObject::kElementsOffset));
  __ StoreP(r2, MemOperand(r6, JSStrictArgumentsObject::kLengthOffset));
  STATIC_ASSERT(JSStrictArgumentsObject::kSize == 4 * kPointerSize);
  __ AddP(r2, r6, Operand(kHeapObjectTag));
  __ Ret();

  // Fall back to %AllocateInNewSpace.
  __ bind(&allocate);
  {
    FrameAndConstantPoolScope scope(masm, StackFrame::INTERNAL);
    __ SmiTag(r3);
    __ Push(r2, r4, r3);
    __ CallRuntime(Runtime::kAllocateInNewSpace);
    __ LoadRR(r5, r2);
    __ Pop(r2, r4);
  }
  __ b(&done_allocate);
}

void LoadGlobalViaContextStub::Generate(MacroAssembler* masm) {
  Register context = cp;
  Register result = r2;
  Register slot = r4;

  // Go up the context chain to the script context.
  for (int i = 0; i < depth(); ++i) {
    __ LoadP(result, ContextMemOperand(context, Context::PREVIOUS_INDEX));
    context = result;
  }

  // Load the PropertyCell value at the specified slot.
  __ ShiftLeftP(r0, slot, Operand(kPointerSizeLog2));
  __ AddP(result, context, r0);
  __ LoadP(result, ContextMemOperand(result));
  __ LoadP(result, FieldMemOperand(result, PropertyCell::kValueOffset));

  // If the result is not the_hole, return. Otherwise, handle in the runtime.
  __ CompareRoot(result, Heap::kTheHoleValueRootIndex);
  Label runtime;
  __ beq(&runtime);
  __ Ret();
  __ bind(&runtime);

  // Fallback to runtime.
  __ SmiTag(slot);
  __ Push(slot);
  __ TailCallRuntime(Runtime::kLoadGlobalViaContext);
}

void StoreGlobalViaContextStub::Generate(MacroAssembler* masm) {
  Register value = r2;
  Register slot = r4;

  Register cell = r3;
  Register cell_details = r5;
  Register cell_value = r6;
  Register cell_value_map = r7;
  Register scratch = r8;

  Register context = cp;
  Register context_temp = cell;

  Label fast_heapobject_case, fast_smi_case, slow_case;

  if (FLAG_debug_code) {
    __ CompareRoot(value, Heap::kTheHoleValueRootIndex);
    __ Check(ne, kUnexpectedValue);
  }

  // Go up the context chain to the script context.
  for (int i = 0; i < depth(); i++) {
    __ LoadP(context_temp, ContextMemOperand(context, Context::PREVIOUS_INDEX));
    context = context_temp;
  }

  // Load the PropertyCell at the specified slot.
  __ ShiftLeftP(r0, slot, Operand(kPointerSizeLog2));
  __ AddP(cell, context, r0);
  __ LoadP(cell, ContextMemOperand(cell));

  // Load PropertyDetails for the cell (actually only the cell_type and kind).
  __ LoadP(cell_details, FieldMemOperand(cell, PropertyCell::kDetailsOffset));
  __ SmiUntag(cell_details);
  __ AndP(cell_details, cell_details,
          Operand(PropertyDetails::PropertyCellTypeField::kMask |
                  PropertyDetails::KindField::kMask |
                  PropertyDetails::kAttributesReadOnlyMask));

  // Check if PropertyCell holds mutable data.
  Label not_mutable_data;
  __ CmpP(cell_details, Operand(PropertyDetails::PropertyCellTypeField::encode(
                                    PropertyCellType::kMutable) |
                                PropertyDetails::KindField::encode(kData)));
  __ bne(&not_mutable_data);
  __ JumpIfSmi(value, &fast_smi_case);

  __ bind(&fast_heapobject_case);
  __ StoreP(value, FieldMemOperand(cell, PropertyCell::kValueOffset), r0);
  // RecordWriteField clobbers the value register, so we copy it before the
  // call.
  __ LoadRR(r5, value);
  __ RecordWriteField(cell, PropertyCell::kValueOffset, r5, scratch,
                      kLRHasNotBeenSaved, kDontSaveFPRegs, EMIT_REMEMBERED_SET,
                      OMIT_SMI_CHECK);
  __ Ret();

  __ bind(&not_mutable_data);
  // Check if PropertyCell value matches the new value (relevant for Constant,
  // ConstantType and Undefined cells).
  Label not_same_value;
  __ LoadP(cell_value, FieldMemOperand(cell, PropertyCell::kValueOffset));
  __ CmpP(cell_value, value);
  __ bne(&not_same_value);

  // Make sure the PropertyCell is not marked READ_ONLY.
  __ AndP(r0, cell_details, Operand(PropertyDetails::kAttributesReadOnlyMask));
  __ bne(&slow_case);

  if (FLAG_debug_code) {
    Label done;
    // This can only be true for Constant, ConstantType and Undefined cells,
    // because we never store the_hole via this stub.
    __ CmpP(cell_details,
            Operand(PropertyDetails::PropertyCellTypeField::encode(
                        PropertyCellType::kConstant) |
                    PropertyDetails::KindField::encode(kData)));
    __ beq(&done);
    __ CmpP(cell_details,
            Operand(PropertyDetails::PropertyCellTypeField::encode(
                        PropertyCellType::kConstantType) |
                    PropertyDetails::KindField::encode(kData)));
    __ beq(&done);
    __ CmpP(cell_details,
            Operand(PropertyDetails::PropertyCellTypeField::encode(
                        PropertyCellType::kUndefined) |
                    PropertyDetails::KindField::encode(kData)));
    __ Check(eq, kUnexpectedValue);
    __ bind(&done);
  }
  __ Ret();
  __ bind(&not_same_value);

  // Check if PropertyCell contains data with constant type (and is not
  // READ_ONLY).
  __ CmpP(cell_details, Operand(PropertyDetails::PropertyCellTypeField::encode(
                                    PropertyCellType::kConstantType) |
                                PropertyDetails::KindField::encode(kData)));
  __ bne(&slow_case);

  // Now either both old and new values must be smis or both must be heap
  // objects with same map.
  Label value_is_heap_object;
  __ JumpIfNotSmi(value, &value_is_heap_object);
  __ JumpIfNotSmi(cell_value, &slow_case);
  // Old and new values are smis, no need for a write barrier here.
  __ bind(&fast_smi_case);
  __ StoreP(value, FieldMemOperand(cell, PropertyCell::kValueOffset), r0);
  __ Ret();

  __ bind(&value_is_heap_object);
  __ JumpIfSmi(cell_value, &slow_case);

  __ LoadP(cell_value_map, FieldMemOperand(cell_value, HeapObject::kMapOffset));
  __ LoadP(scratch, FieldMemOperand(value, HeapObject::kMapOffset));
  __ CmpP(cell_value_map, scratch);
  __ beq(&fast_heapobject_case);

  // Fallback to runtime.
  __ bind(&slow_case);
  __ SmiTag(slot);
  __ Push(slot, value);
  __ TailCallRuntime(is_strict(language_mode())
                         ? Runtime::kStoreGlobalViaContext_Strict
                         : Runtime::kStoreGlobalViaContext_Sloppy);
}

static int AddressOffset(ExternalReference ref0, ExternalReference ref1) {
  return ref0.address() - ref1.address();
}

// Calls an API function.  Allocates HandleScope, extracts returned value
// from handle and propagates exceptions.  Restores context.  stack_space
// - space to be unwound on exit (includes the call JS arguments space and
// the additional space allocated for the fast call).
static void CallApiFunctionAndReturn(MacroAssembler* masm,
                                     Register function_address,
                                     ExternalReference thunk_ref,
                                     int stack_space,
                                     MemOperand* stack_space_operand,
                                     MemOperand return_value_operand,
                                     MemOperand* context_restore_operand) {
  Isolate* isolate = masm->isolate();
  ExternalReference next_address =
      ExternalReference::handle_scope_next_address(isolate);
  const int kNextOffset = 0;
  const int kLimitOffset = AddressOffset(
      ExternalReference::handle_scope_limit_address(isolate), next_address);
  const int kLevelOffset = AddressOffset(
      ExternalReference::handle_scope_level_address(isolate), next_address);

  // Additional parameter is the address of the actual callback.
  DCHECK(function_address.is(r3) || function_address.is(r4));
  Register scratch = r5;

  __ mov(scratch, Operand(ExternalReference::is_profiling_address(isolate)));
  __ LoadlB(scratch, MemOperand(scratch, 0));
  __ CmpP(scratch, Operand::Zero());

  Label profiler_disabled;
  Label end_profiler_check;
  __ beq(&profiler_disabled, Label::kNear);
  __ mov(scratch, Operand(thunk_ref));
  __ b(&end_profiler_check, Label::kNear);
  __ bind(&profiler_disabled);
  __ LoadRR(scratch, function_address);
  __ bind(&end_profiler_check);

  // Allocate HandleScope in callee-save registers.
  // r9 - next_address
  // r6 - next_address->kNextOffset
  // r7 - next_address->kLimitOffset
  // r8 - next_address->kLevelOffset
  __ mov(r9, Operand(next_address));
  __ LoadP(r6, MemOperand(r9, kNextOffset));
  __ LoadP(r7, MemOperand(r9, kLimitOffset));
  __ LoadlW(r8, MemOperand(r9, kLevelOffset));
  __ AddP(r8, Operand(1));
  __ StoreW(r8, MemOperand(r9, kLevelOffset));

  if (FLAG_log_timer_events) {
    FrameScope frame(masm, StackFrame::MANUAL);
    __ PushSafepointRegisters();
    __ PrepareCallCFunction(1, r2);
    __ mov(r2, Operand(ExternalReference::isolate_address(isolate)));
    __ CallCFunction(ExternalReference::log_enter_external_function(isolate),
                     1);
    __ PopSafepointRegisters();
  }

  // Native call returns to the DirectCEntry stub which redirects to the
  // return address pushed on stack (could have moved after GC).
  // DirectCEntry stub itself is generated early and never moves.
  DirectCEntryStub stub(isolate);
  stub.GenerateCall(masm, scratch);

  if (FLAG_log_timer_events) {
    FrameScope frame(masm, StackFrame::MANUAL);
    __ PushSafepointRegisters();
    __ PrepareCallCFunction(1, r2);
    __ mov(r2, Operand(ExternalReference::isolate_address(isolate)));
    __ CallCFunction(ExternalReference::log_leave_external_function(isolate),
                     1);
    __ PopSafepointRegisters();
  }

  Label promote_scheduled_exception;
  Label delete_allocated_handles;
  Label leave_exit_frame;
  Label return_value_loaded;

  // load value from ReturnValue
  __ LoadP(r2, return_value_operand);
  __ bind(&return_value_loaded);
  // No more valid handles (the result handle was the last one). Restore
  // previous handle scope.
  __ StoreP(r6, MemOperand(r9, kNextOffset));
  if (__ emit_debug_code()) {
    __ LoadlW(r3, MemOperand(r9, kLevelOffset));
    __ CmpP(r3, r8);
    __ Check(eq, kUnexpectedLevelAfterReturnFromApiCall);
  }
  __ SubP(r8, Operand(1));
  __ StoreW(r8, MemOperand(r9, kLevelOffset));
  __ CmpP(r7, MemOperand(r9, kLimitOffset));
  __ bne(&delete_allocated_handles, Label::kNear);

  // Leave the API exit frame.
  __ bind(&leave_exit_frame);
  bool restore_context = context_restore_operand != NULL;
  if (restore_context) {
    __ LoadP(cp, *context_restore_operand);
  }
  // LeaveExitFrame expects unwind space to be in a register.
  if (stack_space_operand != NULL) {
    __ l(r6, *stack_space_operand);
  } else {
    __ mov(r6, Operand(stack_space));
  }
  __ LeaveExitFrame(false, r6, !restore_context, stack_space_operand != NULL);

  // Check if the function scheduled an exception.
  __ mov(r7, Operand(ExternalReference::scheduled_exception_address(isolate)));
  __ LoadP(r7, MemOperand(r7));
  __ CompareRoot(r7, Heap::kTheHoleValueRootIndex);
  __ bne(&promote_scheduled_exception, Label::kNear);

  __ b(r14);

  // Re-throw by promoting a scheduled exception.
  __ bind(&promote_scheduled_exception);
  __ TailCallRuntime(Runtime::kPromoteScheduledException);

  // HandleScope limit has changed. Delete allocated extensions.
  __ bind(&delete_allocated_handles);
  __ StoreP(r7, MemOperand(r9, kLimitOffset));
  __ LoadRR(r6, r2);
  __ PrepareCallCFunction(1, r7);
  __ mov(r2, Operand(ExternalReference::isolate_address(isolate)));
  __ CallCFunction(ExternalReference::delete_handle_scope_extensions(isolate),
                   1);
  __ LoadRR(r2, r6);
  __ b(&leave_exit_frame, Label::kNear);
}

void CallApiCallbackStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- r2                  : callee
  //  -- r6                  : call_data
  //  -- r4                  : holder
  //  -- r3                  : api_function_address
  //  -- cp                  : context
  //  --
  //  -- sp[0]               : last argument
  //  -- ...
  //  -- sp[(argc - 1)* 4]   : first argument
  //  -- sp[argc * 4]        : receiver
  // -----------------------------------

  Register callee = r2;
  Register call_data = r6;
  Register holder = r4;
  Register api_function_address = r3;
  Register context = cp;

  typedef FunctionCallbackArguments FCA;

  STATIC_ASSERT(FCA::kContextSaveIndex == 6);
  STATIC_ASSERT(FCA::kCalleeIndex == 5);
  STATIC_ASSERT(FCA::kDataIndex == 4);
  STATIC_ASSERT(FCA::kReturnValueOffset == 3);
  STATIC_ASSERT(FCA::kReturnValueDefaultValueIndex == 2);
  STATIC_ASSERT(FCA::kIsolateIndex == 1);
  STATIC_ASSERT(FCA::kHolderIndex == 0);
  STATIC_ASSERT(FCA::kArgsLength == 7);

  // context save
  __ push(context);
  if (!is_lazy()) {
    // load context from callee
    __ LoadP(context, FieldMemOperand(callee, JSFunction::kContextOffset));
  }

  // callee
  __ push(callee);

  // call data
  __ push(call_data);

  Register scratch = call_data;
  if (!call_data_undefined()) {
    __ LoadRoot(scratch, Heap::kUndefinedValueRootIndex);
  }
  // return value
  __ push(scratch);
  // return value default
  __ push(scratch);
  // isolate
  __ mov(scratch, Operand(ExternalReference::isolate_address(masm->isolate())));
  __ push(scratch);
  // holder
  __ push(holder);

  // Prepare arguments.
  __ LoadRR(scratch, sp);

  // Allocate the v8::Arguments structure in the arguments' space since
  // it's not controlled by GC.
  // S390 LINUX ABI:
  //
  // Create 5 extra slots on stack:
  //    [0] space for DirectCEntryStub's LR save
  //    [1-4] FunctionCallbackInfo
  const int kApiStackSpace = 5;
  const int kFunctionCallbackInfoOffset =
      (kStackFrameExtraParamSlot + 1) * kPointerSize;

  FrameScope frame_scope(masm, StackFrame::MANUAL);
  __ EnterExitFrame(false, kApiStackSpace);

  DCHECK(!api_function_address.is(r2) && !scratch.is(r2));
  // r2 = FunctionCallbackInfo&
  // Arguments is after the return address.
  __ AddP(r2, sp, Operand(kFunctionCallbackInfoOffset));
  // FunctionCallbackInfo::implicit_args_
  __ StoreP(scratch, MemOperand(r2, 0 * kPointerSize));
  // FunctionCallbackInfo::values_
  __ AddP(ip, scratch, Operand((FCA::kArgsLength - 1 + argc()) * kPointerSize));
  __ StoreP(ip, MemOperand(r2, 1 * kPointerSize));
  // FunctionCallbackInfo::length_ = argc
  __ LoadImmP(ip, Operand(argc()));
  __ StoreW(ip, MemOperand(r2, 2 * kPointerSize));
  // FunctionCallbackInfo::is_construct_call_ = 0
  __ LoadImmP(ip, Operand::Zero());
  __ StoreW(ip, MemOperand(r2, 2 * kPointerSize + kIntSize));

  ExternalReference thunk_ref =
      ExternalReference::invoke_function_callback(masm->isolate());

  AllowExternalCallThatCantCauseGC scope(masm);
  MemOperand context_restore_operand(
      fp, (2 + FCA::kContextSaveIndex) * kPointerSize);
  // Stores return the first js argument
  int return_value_offset = 0;
  if (is_store()) {
    return_value_offset = 2 + FCA::kArgsLength;
  } else {
    return_value_offset = 2 + FCA::kReturnValueOffset;
  }
  MemOperand return_value_operand(fp, return_value_offset * kPointerSize);
  int stack_space = 0;
  MemOperand is_construct_call_operand =
      MemOperand(sp, kFunctionCallbackInfoOffset + 2 * kPointerSize + kIntSize);
  MemOperand* stack_space_operand = &is_construct_call_operand;
  stack_space = argc() + FCA::kArgsLength + 1;
  stack_space_operand = NULL;
  CallApiFunctionAndReturn(masm, api_function_address, thunk_ref, stack_space,
                           stack_space_operand, return_value_operand,
                           &context_restore_operand);
}

void CallApiGetterStub::Generate(MacroAssembler* masm) {
  // ----------- S t a t e -------------
  //  -- sp[0]                        : name
  //  -- sp[4 .. (4 + kArgsLength*4)] : v8::PropertyCallbackInfo::args_
  //  -- ...
  //  -- r4                           : api_function_address
  // -----------------------------------

  Register api_function_address = ApiGetterDescriptor::function_address();
  int arg0Slot = 0;
  int accessorInfoSlot = 0;
  int apiStackSpace = 0;
  DCHECK(api_function_address.is(r4));

  // v8::PropertyCallbackInfo::args_ array and name handle.
  const int kStackUnwindSpace = PropertyCallbackArguments::kArgsLength + 1;

  // Load address of v8::PropertyAccessorInfo::args_ array and name handle.
  __ LoadRR(r2, sp);                           // r2 = Handle<Name>
  __ AddP(r3, r2, Operand(1 * kPointerSize));  // r3 = v8::PCI::args_

  // If ABI passes Handles (pointer-sized struct) in a register:
  //
  // Create 2 extra slots on stack:
  //    [0] space for DirectCEntryStub's LR save
  //    [1] AccessorInfo&
  //
  // Otherwise:
  //
  // Create 3 extra slots on stack:
  //    [0] space for DirectCEntryStub's LR save
  //    [1] copy of Handle (first arg)
  //    [2] AccessorInfo&
  if (ABI_PASSES_HANDLES_IN_REGS) {
    accessorInfoSlot = kStackFrameExtraParamSlot + 1;
    apiStackSpace = 2;
  } else {
    arg0Slot = kStackFrameExtraParamSlot + 1;
    accessorInfoSlot = arg0Slot + 1;
    apiStackSpace = 3;
  }

  FrameScope frame_scope(masm, StackFrame::MANUAL);
  __ EnterExitFrame(false, apiStackSpace);

  if (!ABI_PASSES_HANDLES_IN_REGS) {
    // pass 1st arg by reference
    __ StoreP(r2, MemOperand(sp, arg0Slot * kPointerSize));
    __ AddP(r2, sp, Operand(arg0Slot * kPointerSize));
  }

  // Create v8::PropertyCallbackInfo object on the stack and initialize
  // it's args_ field.
  __ StoreP(r3, MemOperand(sp, accessorInfoSlot * kPointerSize));
  __ AddP(r3, sp, Operand(accessorInfoSlot * kPointerSize));
  // r3 = v8::PropertyCallbackInfo&

  ExternalReference thunk_ref =
      ExternalReference::invoke_accessor_getter_callback(isolate());

  // +3 is to skip prolog, return address and name handle.
  MemOperand return_value_operand(
      fp, (PropertyCallbackArguments::kReturnValueOffset + 3) * kPointerSize);
  CallApiFunctionAndReturn(masm, api_function_address, thunk_ref,
                           kStackUnwindSpace, NULL, return_value_operand, NULL);
}

#undef __

}  // namespace internal
}  // namespace v8

#endif  // V8_TARGET_ARCH_S390
