1014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Copyright 2015 the V8 project authors. All rights reserved.
2014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Use of this source code is governed by a BSD-style license that can be
3014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// found in the LICENSE file.
4014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
5014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/assembler.h"
6014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/codegen.h"
7014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/compiler/linkage.h"
8014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/compiler/raw-machine-assembler.h"
9014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/machine-type.h"
10014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/register-configuration.h"
11014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
12014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "test/cctest/cctest.h"
13014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "test/cctest/compiler/codegen-tester.h"
14014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "test/cctest/compiler/graph-builder-tester.h"
15014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "test/cctest/compiler/value-helper.h"
16014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
17014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace v8 {
18014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace internal {
19014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace compiler {
20014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
2121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdochconst auto GetRegConfig = RegisterConfiguration::Turbofan;
2221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch
23014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace {
24014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtypedef float float32;
25014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtypedef double float64;
26014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
27014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Picks a representative pair of integers from the given range.
28014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// If there are less than {max_pairs} possible pairs, do them all, otherwise try
29014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// to select a representative set.
30014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Pairs {
31014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
32014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Pairs(int max_pairs, int range, const int* codes)
33014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      : range_(range),
34014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        codes_(codes),
35014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        max_pairs_(std::min(max_pairs, range_ * range_)),
36014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        counter_(0) {}
37014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
38014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  bool More() { return counter_ < max_pairs_; }
39014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
40014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  void Next(int* r0, int* r1, bool same_is_ok) {
41014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    do {
42014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Find the next pair.
43014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      if (exhaustive()) {
44014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        *r0 = codes_[counter_ % range_];
45014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        *r1 = codes_[counter_ / range_];
46014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      } else {
47014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        // Try each integer at least once for both r0 and r1.
48014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        int index = counter_ / 2;
49014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        if (counter_ & 1) {
50014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          *r0 = codes_[index % range_];
51014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          *r1 = codes_[index / range_];
52014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        } else {
53014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          *r1 = codes_[index % range_];
54014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          *r0 = codes_[index / range_];
55014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        }
56014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
57014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      counter_++;
58014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      if ((same_is_ok) || (*r0 != *r1)) break;
59014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      if (counter_ == max_pairs_) {
60014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        // For the last hurrah, reg#0 with reg#n-1
61014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        *r0 = codes_[0];
62014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        *r1 = codes_[range_ - 1];
63014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        break;
64014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
65014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    } while (true);
66014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
67014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
68014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch private:
69014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int range_;
70014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  const int* codes_;
71014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int max_pairs_;
72014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int counter_;
73014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  bool exhaustive() { return max_pairs_ == (range_ * range_); }
74014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
75014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
76014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
77014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Pairs of general purpose registers.
78014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass RegisterPairs : public Pairs {
79014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
80014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterPairs()
8121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch      : Pairs(100, GetRegConfig()->num_allocatable_general_registers(),
8221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch              GetRegConfig()->allocatable_general_codes()) {}
83014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
84014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
85014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
86014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Pairs of double registers.
87014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Float32RegisterPairs : public Pairs {
88014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
89014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Float32RegisterPairs()
90014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      : Pairs(
91014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            100,
9221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#if V8_TARGET_ARCH_ARM
9321efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch            // TODO(bbudge) Modify wasm linkage to allow use of all float regs.
9421efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch            GetRegConfig()->num_allocatable_double_registers() / 2 - 2,
9521efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#else
9621efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch            GetRegConfig()->num_allocatable_double_registers(),
9721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#endif
9821efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch            GetRegConfig()->allocatable_double_codes()) {
9921efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  }
100014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
101014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
102014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
103014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Pairs of double registers.
104014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Float64RegisterPairs : public Pairs {
105014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
106014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Float64RegisterPairs()
10721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch      : Pairs(100, GetRegConfig()->num_allocatable_double_registers(),
10821efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch              GetRegConfig()->allocatable_double_codes()) {}
109014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
110014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
111014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
112014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Helper for allocating either an GP or FP reg, or the next stack slot.
113014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstruct Allocator {
114014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator(int* gp, int gpc, int* fp, int fpc)
115014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      : gp_count(gpc),
116014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        gp_offset(0),
117014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        gp_regs(gp),
118014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        fp_count(fpc),
119014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        fp_offset(0),
120014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        fp_regs(fp),
121014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        stack_offset(0) {}
122014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
123014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int gp_count;
124014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int gp_offset;
125014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int* gp_regs;
126014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
127014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int fp_count;
128014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int fp_offset;
129014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int* fp_regs;
130014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
131014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int stack_offset;
132014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
133014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  LinkageLocation Next(MachineType type) {
134014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    if (IsFloatingPoint(type.representation())) {
135014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Allocate a floating point register/stack location.
136014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      if (fp_offset < fp_count) {
13721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch        int code = fp_regs[fp_offset++];
13821efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#if V8_TARGET_ARCH_ARM
13921efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch        // TODO(bbudge) Modify wasm linkage to allow use of all float regs.
14021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch        if (type.representation() == MachineRepresentation::kFloat32) code *= 2;
14121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#endif
14221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch        return LinkageLocation::ForRegister(code);
143014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      } else {
144014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        int offset = -1 - stack_offset;
145014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        stack_offset += StackWords(type);
146014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        return LinkageLocation::ForCallerFrameSlot(offset);
147014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
148014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    } else {
149014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Allocate a general purpose register/stack location.
150014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      if (gp_offset < gp_count) {
151014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        return LinkageLocation::ForRegister(gp_regs[gp_offset++]);
152014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      } else {
153014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        int offset = -1 - stack_offset;
154014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        stack_offset += StackWords(type);
155014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        return LinkageLocation::ForCallerFrameSlot(offset);
156014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
157014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
158014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
159014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int StackWords(MachineType type) {
16021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch    int size = 1 << ElementSizeLog2Of(type.representation());
161014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return size <= kPointerSize ? 1 : size / kPointerSize;
162014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
163014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  void Reset() {
164014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    fp_offset = 0;
165014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    gp_offset = 0;
166014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    stack_offset = 0;
167014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
168014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
169014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
170014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
171014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass RegisterConfig {
172014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
173014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig(Allocator& p, Allocator& r) : params(p), rets(r) {}
174014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
175014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CallDescriptor* Create(Zone* zone, MachineSignature* msig) {
176014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    rets.Reset();
177014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    params.Reset();
178014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
179014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    LocationSignature::Builder locations(zone, msig->return_count(),
180014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                                         msig->parameter_count());
181014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Add return location(s).
182014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    const int return_count = static_cast<int>(locations.return_count_);
183014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < return_count; i++) {
184014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      locations.AddReturn(rets.Next(msig->GetReturn(i)));
185014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
186014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
187014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Add register and/or stack parameter(s).
188014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    const int parameter_count = static_cast<int>(msig->parameter_count());
189014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < parameter_count; i++) {
190014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      locations.AddParam(params.Next(msig->GetParam(i)));
191014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
192014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
193014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    const RegList kCalleeSaveRegisters = 0;
194014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    const RegList kCalleeSaveFPRegisters = 0;
195014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
196014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType target_type = MachineType::AnyTagged();
197014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    LinkageLocation target_loc = LinkageLocation::ForAnyRegister();
198014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int stack_param_count = params.stack_offset;
199014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return new (zone) CallDescriptor(       // --
200014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CallDescriptor::kCallCodeObject,    // kind
201014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        target_type,                        // target MachineType
202014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        target_loc,                         // target location
203014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        msig,                               // machine_sig
204014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        locations.Build(),                  // location_sig
205014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        stack_param_count,                  // stack_parameter_count
206014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        compiler::Operator::kNoProperties,  // properties
207014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        kCalleeSaveRegisters,               // callee-saved registers
208014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        kCalleeSaveFPRegisters,             // callee-saved fp regs
209014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CallDescriptor::kUseNativeStack,    // flags
210014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        "c-call");
211014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
212014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
213014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch private:
214014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator& params;
215014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator& rets;
216014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
217014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
218014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochconst int kMaxParamCount = 64;
219014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
220014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochMachineType kIntTypes[kMaxParamCount + 1] = {
221014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
222014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
223014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
224014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
225014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
226014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
227014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
228014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
229014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
230014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
231014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
232014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
233014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
234014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
235014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
236014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
237014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
238014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
239014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
240014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
241014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32(), MachineType::Int32(),
242014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType::Int32(), MachineType::Int32()};
243014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
244014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
245014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// For making uniform int32 signatures shorter.
246014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Int32Signature : public MachineSignature {
247014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
248014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  explicit Int32Signature(int param_count)
249014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      : MachineSignature(1, param_count, kIntTypes) {
250014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CHECK(param_count <= kMaxParamCount);
251014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
252014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
253014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
254014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
255014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochHandle<Code> CompileGraph(const char* name, CallDescriptor* desc, Graph* graph,
256014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                          Schedule* schedule = nullptr) {
257014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Isolate* isolate = CcTest::InitIsolateOnce();
258537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch  CompilationInfo info(ArrayVector("testing"), isolate, graph->zone());
259014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> code =
260014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Pipeline::GenerateCodeForTesting(&info, desc, graph, schedule);
261014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CHECK(!code.is_null());
262014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#ifdef ENABLE_DISASSEMBLER
263014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  if (FLAG_print_opt_code) {
264014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    OFStream os(stdout);
265014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    code->Disassemble(name, os);
266014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
267014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#endif
268014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  return code;
269014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
270014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
271014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
272014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochHandle<Code> WrapWithCFunction(Handle<Code> inner, CallDescriptor* desc) {
2731b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(inner->GetIsolate()->allocator());
274014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  MachineSignature* msig =
275014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      const_cast<MachineSignature*>(desc->GetMachineSignature());
276014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int param_count = static_cast<int>(msig->parameter_count());
277014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  GraphAndBuilders caller(&zone);
278014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
279014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    GraphAndBuilders& b = caller;
280014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* start = b.graph()->NewNode(b.common()->Start(param_count + 3));
281014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    b.graph()->SetStart(start);
282014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* target = b.graph()->NewNode(b.common()->HeapConstant(inner));
283014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
284014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Add arguments to the call.
285014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node** args = zone.NewArray<Node*>(param_count + 3);
286014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int index = 0;
287014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    args[index++] = target;
288014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < param_count; i++) {
289014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      args[index] = b.graph()->NewNode(b.common()->Parameter(i), start);
290014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      index++;
291014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
292014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    args[index++] = start;  // effect.
293014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    args[index++] = start;  // control.
294014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
295014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Build the call and return nodes.
296014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* call =
297014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        b.graph()->NewNode(b.common()->Call(desc), param_count + 3, args);
298014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* ret = b.graph()->NewNode(b.common()->Return(), call, call, start);
299014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    b.graph()->SetEnd(ret);
300014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
301014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
302014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CallDescriptor* cdesc = Linkage::GetSimplifiedCDescriptor(&zone, msig);
303014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
304014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  return CompileGraph("wrapper", cdesc, caller.graph());
305014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
306014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
307014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
308014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType>
309014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass ArgsBuffer {
310014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
311014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  static const int kMaxParamCount = 64;
312014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
313014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  explicit ArgsBuffer(int count, int seed = 1) : count_(count), seed_(seed) {
314014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // initialize the buffer with "seed 0"
315014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    seed_ = 0;
316014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Mutate();
317014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    seed_ = seed;
318014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
319014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
320014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  class Sig : public MachineSignature {
321014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch   public:
322014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    explicit Sig(int param_count)
323014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        : MachineSignature(1, param_count, MachTypes()) {
324014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK(param_count <= kMaxParamCount);
325014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
326014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  };
327014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
328014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  static MachineType* MachTypes() {
329014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineType t = MachineTypeForC<CType>();
330014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    static MachineType kTypes[kMaxParamCount + 1] = {
331014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t,
332014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t,
333014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t, t};
334014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return kTypes;
335014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
336014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
337014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* MakeConstant(RawMachineAssembler& raw, int32_t value) {
338014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Int32Constant(value);
339014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
340014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
341014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* MakeConstant(RawMachineAssembler& raw, int64_t value) {
342014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Int64Constant(value);
343014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
344014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
345014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* MakeConstant(RawMachineAssembler& raw, float32 value) {
346014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Float32Constant(value);
347014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
348014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
349014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* MakeConstant(RawMachineAssembler& raw, float64 value) {
350014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Float64Constant(value);
351014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
352014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
353014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* LoadInput(RawMachineAssembler& raw, Node* base, int index) {
354014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* offset = raw.Int32Constant(index * sizeof(CType));
355014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Load(MachineTypeForC<CType>(), base, offset);
356014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
357014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
358014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* StoreOutput(RawMachineAssembler& raw, Node* value) {
359014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* base = raw.PointerConstant(&output);
360014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* offset = raw.Int32Constant(0);
361014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return raw.Store(MachineTypeForC<CType>().representation(), base, offset,
362014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                     value, kNoWriteBarrier);
363014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
364014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
365014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  // Computes the next set of inputs by updating the {input} array.
366014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  void Mutate();
367014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
368014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  void Reset() { memset(input, 0, sizeof(input)); }
369014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
370014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int count_;
371014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int seed_;
372014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CType input[kMaxParamCount];
373014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CType output;
374014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
375014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
376014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
377014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <>
378014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid ArgsBuffer<int32_t>::Mutate() {
379014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  uint32_t base = 1111111111u * seed_;
380014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int j = 0; j < count_ && j < kMaxParamCount; j++) {
381014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    input[j] = static_cast<int32_t>(256 + base + j + seed_ * 13);
382014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
383014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  output = -1;
384014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  seed_++;
385014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
386014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
387014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
388014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <>
389014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid ArgsBuffer<int64_t>::Mutate() {
390014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  uint64_t base = 11111111111111111ull * seed_;
391014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int j = 0; j < count_ && j < kMaxParamCount; j++) {
392014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    input[j] = static_cast<int64_t>(256 + base + j + seed_ * 13);
393014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
394014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  output = -1;
395014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  seed_++;
396014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
397014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
398014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
399014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <>
400014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid ArgsBuffer<float32>::Mutate() {
401014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  float64 base = -33.25 * seed_;
402014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int j = 0; j < count_ && j < kMaxParamCount; j++) {
403014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    input[j] = 256 + base + j + seed_ * 13;
404014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
405014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  output = std::numeric_limits<float32>::quiet_NaN();
406014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  seed_++;
407014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
408014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
409014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
410014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <>
411014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid ArgsBuffer<float64>::Mutate() {
412014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  float64 base = -111.25 * seed_;
413014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int j = 0; j < count_ && j < kMaxParamCount; j++) {
414014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    input[j] = 256 + base + j + seed_ * 13;
415014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
416014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  output = std::numeric_limits<float64>::quiet_NaN();
417014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  seed_++;
418014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
419014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
420014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
421014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochint ParamCount(CallDescriptor* desc) {
422014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  return static_cast<int>(desc->GetMachineSignature()->parameter_count());
423014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
424014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
425014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
426014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType>
427014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Computer {
428014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public:
429014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  static void Run(CallDescriptor* desc,
430014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                  void (*build)(CallDescriptor*, RawMachineAssembler&),
431014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                  CType (*compute)(CallDescriptor*, CType* inputs),
432014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                  int seed = 1) {
433014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int num_params = ParamCount(desc);
434014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CHECK_LE(num_params, kMaxParamCount);
435014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Isolate* isolate = CcTest::InitIsolateOnce();
436014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    HandleScope scope(isolate);
437014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Handle<Code> inner = Handle<Code>::null();
438014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    {
439014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Build the graph for the computation.
4401b268ca467c924004286c97bac133db489cf43d0Ben Murdoch      Zone zone(isolate->allocator());
441014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Graph graph(&zone);
442014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      RawMachineAssembler raw(isolate, &graph, desc);
443014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      build(desc, raw);
444014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      inner = CompileGraph("Compute", desc, &graph, raw.Export());
445014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
446014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
447014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CSignature0<int32_t> csig;
448014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    ArgsBuffer<CType> io(num_params, seed);
449014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
450014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    {
451014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // constant mode.
452014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Handle<Code> wrapper = Handle<Code>::null();
453014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      {
454014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        // Wrap the above code with a callable function that passes constants.
4551b268ca467c924004286c97bac133db489cf43d0Ben Murdoch        Zone zone(isolate->allocator());
456014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Graph graph(&zone);
457014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CallDescriptor* cdesc = Linkage::GetSimplifiedCDescriptor(&zone, &csig);
458014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        RawMachineAssembler raw(isolate, &graph, cdesc);
459014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* target = raw.HeapConstant(inner);
460014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node** args = zone.NewArray<Node*>(num_params);
461014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        for (int i = 0; i < num_params; i++) {
462014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          args[i] = io.MakeConstant(raw, io.input[i]);
463014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        }
464014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
465014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* call = raw.CallN(desc, target, args);
466014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* store = io.StoreOutput(raw, call);
467014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        USE(store);
468014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        raw.Return(raw.Int32Constant(seed));
469014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        wrapper =
470014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            CompileGraph("Compute-wrapper-const", cdesc, &graph, raw.Export());
471014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
472014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
473014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CodeRunner<int32_t> runnable(isolate, wrapper, &csig);
474014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
475014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Run the code, checking it against the reference.
476014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CType expected = compute(desc, io.input);
477014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int32_t check_seed = runnable.Call();
478014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK_EQ(seed, check_seed);
479014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK_EQ(expected, io.output);
480014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
481014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
482014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    {
483014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // buffer mode.
484014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Handle<Code> wrapper = Handle<Code>::null();
485014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      {
486014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        // Wrap the above code with a callable function that loads from {input}.
4871b268ca467c924004286c97bac133db489cf43d0Ben Murdoch        Zone zone(isolate->allocator());
488014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Graph graph(&zone);
489014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CallDescriptor* cdesc = Linkage::GetSimplifiedCDescriptor(&zone, &csig);
490014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        RawMachineAssembler raw(isolate, &graph, cdesc);
491014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* base = raw.PointerConstant(io.input);
492014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* target = raw.HeapConstant(inner);
493014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node** args = zone.NewArray<Node*>(kMaxParamCount);
494014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        for (int i = 0; i < num_params; i++) {
495014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          args[i] = io.LoadInput(raw, base, i);
496014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        }
497014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
498014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* call = raw.CallN(desc, target, args);
499014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* store = io.StoreOutput(raw, call);
500014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        USE(store);
501014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        raw.Return(raw.Int32Constant(seed));
502014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        wrapper = CompileGraph("Compute-wrapper", cdesc, &graph, raw.Export());
503014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
504014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
505014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CodeRunner<int32_t> runnable(isolate, wrapper, &csig);
506014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
507014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // Run the code, checking it against the reference.
508014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      for (int i = 0; i < 5; i++) {
509014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CType expected = compute(desc, io.input);
510014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        int32_t check_seed = runnable.Call();
511014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CHECK_EQ(seed, check_seed);
512014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CHECK_EQ(expected, io.output);
513014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        io.Mutate();
514014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
515014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
516014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
517014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch};
518014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
519014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}  // namespace
520014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
521014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
522014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void TestInt32Sub(CallDescriptor* desc) {
523014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Isolate* isolate = CcTest::InitIsolateOnce();
524014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  HandleScope scope(isolate);
5251b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(isolate->allocator());
526014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  GraphAndBuilders inner(&zone);
527014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
528014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Build the add function.
529014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    GraphAndBuilders& b = inner;
530014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* start = b.graph()->NewNode(b.common()->Start(5));
531014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    b.graph()->SetStart(start);
532014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* p0 = b.graph()->NewNode(b.common()->Parameter(0), start);
533014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* p1 = b.graph()->NewNode(b.common()->Parameter(1), start);
534014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* add = b.graph()->NewNode(b.machine()->Int32Sub(), p0, p1);
535014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* ret = b.graph()->NewNode(b.common()->Return(), add, start, start);
536014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    b.graph()->SetEnd(ret);
537014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
538014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
539014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> inner_code = CompileGraph("Int32Sub", desc, inner.graph());
540014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> wrapper = WrapWithCFunction(inner_code, desc);
541014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  MachineSignature* msig =
542014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      const_cast<MachineSignature*>(desc->GetMachineSignature());
543014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CodeRunner<int32_t> runnable(isolate, wrapper,
544014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                               CSignature::FromMachine(&zone, msig));
545014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
546014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  FOR_INT32_INPUTS(i) {
547014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    FOR_INT32_INPUTS(j) {
548014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int32_t expected = static_cast<int32_t>(static_cast<uint32_t>(*i) -
549014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                                              static_cast<uint32_t>(*j));
550014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int32_t result = runnable.Call(*i, *j);
551014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK_EQ(expected, result);
552014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
553014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
554014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
555014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
556014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
557014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void CopyTwentyInt32(CallDescriptor* desc) {
558014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  const int kNumParams = 20;
559014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int32_t input[kNumParams];
560014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int32_t output[kNumParams];
561014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Isolate* isolate = CcTest::InitIsolateOnce();
562014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  HandleScope scope(isolate);
563014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> inner = Handle<Code>::null();
564014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
565014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Writes all parameters into the output buffer.
5661b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(isolate->allocator());
567014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Graph graph(&zone);
568014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RawMachineAssembler raw(isolate, &graph, desc);
569014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* base = raw.PointerConstant(output);
570014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < kNumParams; i++) {
571014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Node* offset = raw.Int32Constant(i * sizeof(int32_t));
572014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      raw.Store(MachineRepresentation::kWord32, base, offset, raw.Parameter(i),
573014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                kNoWriteBarrier);
574014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
575014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    raw.Return(raw.Int32Constant(42));
576014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    inner = CompileGraph("CopyTwentyInt32", desc, &graph, raw.Export());
577014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
578014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
579014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CSignature0<int32_t> csig;
580014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> wrapper = Handle<Code>::null();
581014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
582014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Loads parameters from the input buffer and calls the above code.
5831b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(isolate->allocator());
584014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Graph graph(&zone);
585014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* cdesc = Linkage::GetSimplifiedCDescriptor(&zone, &csig);
586014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RawMachineAssembler raw(isolate, &graph, cdesc);
587014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* base = raw.PointerConstant(input);
588014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* target = raw.HeapConstant(inner);
589014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node** args = zone.NewArray<Node*>(kNumParams);
590014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < kNumParams; i++) {
591014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Node* offset = raw.Int32Constant(i * sizeof(int32_t));
592014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      args[i] = raw.Load(MachineType::Int32(), base, offset);
593014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
594014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
595014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* call = raw.CallN(desc, target, args);
596014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    raw.Return(call);
597014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    wrapper =
598014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CompileGraph("CopyTwentyInt32-wrapper", cdesc, &graph, raw.Export());
599014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
600014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
601014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CodeRunner<int32_t> runnable(isolate, wrapper, &csig);
602014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
603014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  // Run the code, checking it correctly implements the memcpy.
604014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int i = 0; i < 5; i++) {
605014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    uint32_t base = 1111111111u * i;
606014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int j = 0; j < kNumParams; j++) {
607014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      input[j] = static_cast<int32_t>(base + 13 * j);
608014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
609014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
610014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    memset(output, 0, sizeof(output));
611014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CHECK_EQ(42, runnable.Call());
612014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
613014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int j = 0; j < kNumParams; j++) {
614014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK_EQ(input[j], output[j]);
615014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
616014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
617014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
618014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
619014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
620014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Test_RunInt32SubWithRet(int retreg) {
621014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Int32Signature sig(2);
6221b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
6231b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
624014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterPairs pairs;
625014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
626014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[2];
627014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int rarray[] = {retreg};
628014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&parray[0], &parray[1], false);
629014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(parray, 2, nullptr, 0);
630014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(rarray, 1, nullptr, 0);
631014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
632014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
633014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    TestInt32Sub(desc);
634014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
635014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
636014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
637014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
638014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Separate tests for parallelization.
63921efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch#define TEST_INT32_SUB_WITH_RET(x)                     \
64021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  TEST(Run_Int32Sub_all_allocatable_pairs_##x) {       \
64121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch    if (x < Register::kNumRegisters &&                 \
64221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch        GetRegConfig()->IsAllocatableGeneralCode(x)) { \
64321efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch      Test_RunInt32SubWithRet(x);                      \
64421efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch    }                                                  \
645014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
646014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
647014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(0)
648014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(1)
649014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(2)
650014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(3)
651014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(4)
652014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(5)
653014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(6)
654014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(7)
655014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(8)
656014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(9)
657014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(10)
658014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(11)
659014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(12)
660014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(13)
661014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(14)
662014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(15)
663014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(16)
664014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(17)
665014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(18)
666014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SUB_WITH_RET(19)
667014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
668014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
669014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Run_Int32Sub_all_allocatable_single) {
670014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Int32Signature sig(2);
671014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterPairs pairs;
672014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
6731b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    base::AccountingAllocator allocator;
6741b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(&allocator);
675014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[1];
676014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int rarray[1];
677014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&rarray[0], &parray[0], true);
678014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(parray, 1, nullptr, 0);
679014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(rarray, 1, nullptr, 0);
680014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
681014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
682014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    TestInt32Sub(desc);
683014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
684014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
685014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
686014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
687014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Run_CopyTwentyInt32_all_allocatable_pairs) {
688014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Int32Signature sig(20);
689014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterPairs pairs;
690014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
6911b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    base::AccountingAllocator allocator;
6921b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(&allocator);
693014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[2];
69421efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch    int rarray[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
695014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&parray[0], &parray[1], false);
696014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(parray, 2, nullptr, 0);
697014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(rarray, 1, nullptr, 0);
698014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
699014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
700014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CopyTwentyInt32(desc);
701014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
702014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
703014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
704014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
705014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType>
706014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Run_Computation(
707014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc, void (*build)(CallDescriptor*, RawMachineAssembler&),
708014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CType (*compute)(CallDescriptor*, CType* inputs), int seed = 1) {
709014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Computer<CType>::Run(desc, build, compute, seed);
710014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
711014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
712014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
713014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic uint32_t coeff[] = {1,  2,  3,  5,  7,   11,  13,  17,  19, 23, 29,
714014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                           31, 37, 41, 43, 47,  53,  59,  61,  67, 71, 73,
715014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                           79, 83, 89, 97, 101, 103, 107, 109, 113};
716014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
717014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
718014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Build_Int32_WeightedSum(CallDescriptor* desc,
719014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                                    RawMachineAssembler& raw) {
720014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Node* result = raw.Int32Constant(0);
721014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int i = 0; i < ParamCount(desc); i++) {
722014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* term = raw.Int32Mul(raw.Parameter(i), raw.Int32Constant(coeff[i]));
723014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    result = raw.Int32Add(result, term);
724014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
725014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  raw.Return(result);
726014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
727014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
728014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
729014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic int32_t Compute_Int32_WeightedSum(CallDescriptor* desc, int32_t* input) {
730014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  uint32_t result = 0;
731014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int i = 0; i < ParamCount(desc); i++) {
732014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    result += static_cast<uint32_t>(input[i]) * coeff[i];
733014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
734014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  return static_cast<int32_t>(result);
735014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
736014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
737014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
738014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Test_Int32_WeightedSum_of_size(int count) {
739014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Int32Signature sig(count);
740014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int p0 = 0; p0 < Register::kNumRegisters; p0++) {
74121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch    if (GetRegConfig()->IsAllocatableGeneralCode(p0)) {
7421b268ca467c924004286c97bac133db489cf43d0Ben Murdoch      base::AccountingAllocator allocator;
7431b268ca467c924004286c97bac133db489cf43d0Ben Murdoch      Zone zone(&allocator);
744014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
745014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int parray[] = {p0};
74621efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch      int rarray[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
747014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Allocator params(parray, 1, nullptr, 0);
748014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Allocator rets(rarray, 1, nullptr, 0);
749014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      RegisterConfig config(params, rets);
750014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CallDescriptor* desc = config.Create(&zone, &sig);
751014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Run_Computation<int32_t>(desc, Build_Int32_WeightedSum,
752014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                               Compute_Int32_WeightedSum, 257 + count);
753014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
754014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
755014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
756014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
757014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
758014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Separate tests for parallelization.
759014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#define TEST_INT32_WEIGHTEDSUM(x) \
760014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  TEST(Run_Int32_WeightedSum_##x) { Test_Int32_WeightedSum_of_size(x); }
761014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
762014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
763014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(1)
764014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(2)
765014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(3)
766014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(4)
767014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(5)
768014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(7)
769014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(9)
770014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(11)
771014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(17)
772014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_WEIGHTEDSUM(19)
773014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
774014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
775014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <int which>
776014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Build_Select(CallDescriptor* desc, RawMachineAssembler& raw) {
777014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  raw.Return(raw.Parameter(which));
778014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
779014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
780014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
781014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType, int which>
782014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic CType Compute_Select(CallDescriptor* desc, CType* inputs) {
783014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  return inputs[which];
784014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
785014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
786014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
787014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType, int which>
788014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void RunSelect(CallDescriptor* desc) {
789014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int count = ParamCount(desc);
790014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  if (count <= which) return;
791014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Run_Computation<CType>(desc, Build_Select<which>,
792014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                         Compute_Select<CType, which>,
793014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                         1044 + which + 3 * sizeof(CType));
794014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
795014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
796014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
797014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <int which>
798014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid Test_Int32_Select() {
79921efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int parray[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
80021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
801014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator params(parray, 1, nullptr, 0);
802014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator rets(rarray, 1, nullptr, 0);
803014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig config(params, rets);
804014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
8051b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
8061b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
807014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
808014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int i = which + 1; i <= 64; i++) {
809014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Int32Signature sig(i);
810014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
811014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<int32_t, which>(desc);
812014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
813014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
814014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
815014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
816014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Separate tests for parallelization.
817014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#define TEST_INT32_SELECT(x) \
818014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  TEST(Run_Int32_Select_##x) { Test_Int32_Select<x>(); }
819014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
820014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
821014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(0)
822014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(1)
823014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(2)
824014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(3)
825014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(4)
826014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(5)
827014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(6)
828014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(11)
829014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(15)
830014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(19)
831014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(45)
832014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(62)
833014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST_INT32_SELECT(63)
834014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
835014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
836014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Int64Select_registers) {
83721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_allocatable_general_registers() < 2) return;
838014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  if (kPointerSize < 8) return;  // TODO(titzer): int64 on 32-bit platforms
839014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
84021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
841014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  ArgsBuffer<int64_t>::Sig sig(2);
842014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
843014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterPairs pairs;
8441b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
8451b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
846014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
847014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[2];
848014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&parray[0], &parray[1], false);
849014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(parray, 2, nullptr, 0);
850014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(rarray, 1, nullptr, 0);
851014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
852014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
853014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
854014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<int64_t, 0>(desc);
855014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<int64_t, 1>(desc);
856014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
857014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
858014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
859014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
860014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Float32Select_registers) {
86121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_allocatable_double_registers() < 2) {
862014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    return;
863014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
864014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
86521efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
866014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  ArgsBuffer<float32>::Sig sig(2);
867014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
868014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Float32RegisterPairs pairs;
8691b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
8701b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
871014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
872014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[2];
873014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&parray[0], &parray[1], false);
874014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(nullptr, 0, parray, 2);
875014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(nullptr, 0, rarray, 1);
876014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
877014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
878014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
879014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 0>(desc);
880014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 1>(desc);
881014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
882014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
883014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
884014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
885014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Float64Select_registers) {
88621efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_allocatable_double_registers() < 2) return;
88721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_allocatable_general_registers() < 2) return;
88821efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
889014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  ArgsBuffer<float64>::Sig sig(2);
890014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
891014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Float64RegisterPairs pairs;
8921b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
8931b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
894014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  while (pairs.More()) {
895014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    int parray[2];
896014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    pairs.Next(&parray[0], &parray[1], false);
897014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator params(nullptr, 0, parray, 2);
898014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Allocator rets(nullptr, 0, rarray, 1);
899014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RegisterConfig config(params, rets);
900014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
901014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
902014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 0>(desc);
903014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 1>(desc);
904014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
905014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
906014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
907014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
908014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Float32Select_stack_params_return_reg) {
90921efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
910014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator params(nullptr, 0, nullptr, 0);
911014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator rets(nullptr, 0, rarray, 1);
912014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig config(params, rets);
913014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
9141b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
9151b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
916014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int count = 1; count < 6; count++) {
917014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    ArgsBuffer<float32>::Sig sig(count);
918014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
919014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 0>(desc);
920014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 1>(desc);
921014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 2>(desc);
922014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 3>(desc);
923014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 4>(desc);
924014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float32, 5>(desc);
925014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
926014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
927014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
928014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
929014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Float64Select_stack_params_return_reg) {
93021efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
931014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator params(nullptr, 0, nullptr, 0);
932014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator rets(nullptr, 0, rarray, 1);
933014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig config(params, rets);
934014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
9351b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
9361b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
937014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int count = 1; count < 6; count++) {
938014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    ArgsBuffer<float64>::Sig sig(count);
939014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, &sig);
940014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 0>(desc);
941014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 1>(desc);
942014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 2>(desc);
943014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 3>(desc);
944014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 4>(desc);
945014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RunSelect<float64, 5>(desc);
946014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
947014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
948014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
949014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
950014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochtemplate <typename CType, int which>
951014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochstatic void Build_Select_With_Call(CallDescriptor* desc,
952014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                                   RawMachineAssembler& raw) {
953014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Handle<Code> inner = Handle<Code>::null();
954014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  int num_params = ParamCount(desc);
955014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CHECK_LE(num_params, kMaxParamCount);
956014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
957014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Isolate* isolate = CcTest::InitIsolateOnce();
958014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Build the actual select.
9591b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(isolate->allocator());
960014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Graph graph(&zone);
961014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    RawMachineAssembler raw(isolate, &graph, desc);
962014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    raw.Return(raw.Parameter(which));
963014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    inner = CompileGraph("Select-indirection", desc, &graph, raw.Export());
964014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CHECK(!inner.is_null());
965014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CHECK(inner->IsCode());
966014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
967014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
968014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  {
969014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    // Build a call to the function that does the select.
970014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* target = raw.HeapConstant(inner);
971014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node** args = raw.zone()->NewArray<Node*>(num_params);
972014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int i = 0; i < num_params; i++) {
973014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      args[i] = raw.Parameter(i);
974014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
975014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
976014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Node* call = raw.CallN(desc, target, args);
977014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    raw.Return(call);
978014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
979014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
980014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
981014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
982014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(Float64StackParamsToStackParams) {
98321efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
984014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator params(nullptr, 0, nullptr, 0);
985014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator rets(nullptr, 0, rarray, 1);
986014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
9871b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  base::AccountingAllocator allocator;
9881b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(&allocator);
989014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  ArgsBuffer<float64>::Sig sig(2);
990014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig config(params, rets);
991014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  CallDescriptor* desc = config.Create(&zone, &sig);
992014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
993014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Run_Computation<float64>(desc, Build_Select_With_Call<float64, 0>,
994014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                           Compute_Select<float64, 0>, 1098);
995014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
996014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Run_Computation<float64>(desc, Build_Select_With_Call<float64, 1>,
997014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                           Compute_Select<float64, 1>, 1099);
998014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
999014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1000014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1001014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochvoid MixedParamTest(int start) {
100221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_double_registers() < 2) return;
1003014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1004014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// TODO(titzer): mix in 64-bit types on all platforms when supported.
1005014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#if V8_TARGET_ARCH_32_BIT
1006014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  static MachineType types[] = {
1007014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Int32(),   MachineType::Float32(), MachineType::Float64(),
1008014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Int32(),   MachineType::Float64(), MachineType::Float32(),
1009014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float32(), MachineType::Float64(), MachineType::Int32(),
1010014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float32(), MachineType::Int32(),   MachineType::Float64(),
1011014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float64(), MachineType::Float32(), MachineType::Int32(),
1012014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float64(), MachineType::Int32(),   MachineType::Float32()};
1013014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#else
1014014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  static MachineType types[] = {
1015014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Int32(),   MachineType::Int64(),   MachineType::Float32(),
1016014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float64(), MachineType::Int32(),   MachineType::Float64(),
1017014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float32(), MachineType::Int64(),   MachineType::Int64(),
1018014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float32(), MachineType::Float32(), MachineType::Int32(),
1019014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float64(), MachineType::Float64(), MachineType::Int64(),
1020014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Int32(),   MachineType::Float64(), MachineType::Int32(),
1021014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      MachineType::Float32()};
1022014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#endif
1023014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1024014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Isolate* isolate = CcTest::InitIsolateOnce();
1025014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1026014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  // Build machine signature
1027014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  MachineType* params = &types[start];
1028014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  const int num_params = static_cast<int>(arraysize(types) - start);
1029014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1030014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  // Build call descriptor
103121efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int parray_gp[] = {GetRegConfig()->GetAllocatableGeneralCode(0),
103221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch                     GetRegConfig()->GetAllocatableGeneralCode(1)};
103321efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray_gp[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
103421efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int parray_fp[] = {GetRegConfig()->GetAllocatableDoubleCode(0),
103521efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch                     GetRegConfig()->GetAllocatableDoubleCode(1)};
103621efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray_fp[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
1037014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator palloc(parray_gp, 2, parray_fp, 2);
1038014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  Allocator ralloc(rarray_gp, 1, rarray_fp, 1);
1039014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  RegisterConfig config(palloc, ralloc);
1040014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1041014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  for (int which = 0; which < num_params; which++) {
10421b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    base::AccountingAllocator allocator;
10431b268ca467c924004286c97bac133db489cf43d0Ben Murdoch    Zone zone(&allocator);
1044014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    HandleScope scope(isolate);
1045014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineSignature::Builder builder(&zone, 1, num_params);
1046014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    builder.AddReturn(params[which]);
1047014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    for (int j = 0; j < num_params; j++) builder.AddParam(params[j]);
1048014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    MachineSignature* sig = builder.Build();
1049014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    CallDescriptor* desc = config.Create(&zone, sig);
1050014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1051014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    Handle<Code> select;
1052014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    {
1053014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // build the select.
10541b268ca467c924004286c97bac133db489cf43d0Ben Murdoch      Zone zone(&allocator);
1055014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Graph graph(&zone);
1056014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      RawMachineAssembler raw(isolate, &graph, desc);
1057014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      raw.Return(raw.Parameter(which));
1058014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      select = CompileGraph("Compute", desc, &graph, raw.Export());
1059014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
1060014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1061014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    {
1062014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      // call the select.
1063014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      Handle<Code> wrapper = Handle<Code>::null();
1064014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int32_t expected_ret;
1065014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      char bytes[kDoubleSize];
1066014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      V8_ALIGNED(8) char output[kDoubleSize];
1067014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      int expected_size = 0;
1068014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CSignature0<int32_t> csig;
1069014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      {
1070014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        // Wrap the select code with a callable function that passes constants.
10711b268ca467c924004286c97bac133db489cf43d0Ben Murdoch        Zone zone(&allocator);
1072014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Graph graph(&zone);
1073014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CallDescriptor* cdesc = Linkage::GetSimplifiedCDescriptor(&zone, &csig);
1074014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        RawMachineAssembler raw(isolate, &graph, cdesc);
1075014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* target = raw.HeapConstant(select);
1076014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node** args = zone.NewArray<Node*>(num_params);
1077014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        int64_t constant = 0x0102030405060708;
1078014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        for (int i = 0; i < num_params; i++) {
1079014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          MachineType param_type = sig->GetParam(i);
1080014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          Node* konst = nullptr;
1081014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          if (param_type == MachineType::Int32()) {
1082014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            int32_t value[] = {static_cast<int32_t>(constant)};
1083014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            konst = raw.Int32Constant(value[0]);
1084014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            if (i == which) memcpy(bytes, value, expected_size = 4);
1085014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          }
1086014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          if (param_type == MachineType::Int64()) {
1087014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            int64_t value[] = {static_cast<int64_t>(constant)};
1088014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            konst = raw.Int64Constant(value[0]);
1089014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            if (i == which) memcpy(bytes, value, expected_size = 8);
1090014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          }
1091014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          if (param_type == MachineType::Float32()) {
1092014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            float32 value[] = {static_cast<float32>(constant)};
1093014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            konst = raw.Float32Constant(value[0]);
1094014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            if (i == which) memcpy(bytes, value, expected_size = 4);
1095014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          }
1096014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          if (param_type == MachineType::Float64()) {
1097014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            float64 value[] = {static_cast<float64>(constant)};
1098014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            konst = raw.Float64Constant(value[0]);
1099014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            if (i == which) memcpy(bytes, value, expected_size = 8);
1100014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          }
1101014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          CHECK_NOT_NULL(konst);
1102014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1103014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          args[i] = konst;
1104014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch          constant += 0x1010101010101010;
1105014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        }
1106014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1107014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* call = raw.CallN(desc, target, args);
1108014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        Node* store =
1109014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch            raw.StoreToPointer(output, sig->GetReturn().representation(), call);
1110014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        USE(store);
1111014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        expected_ret = static_cast<int32_t>(constant);
1112014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        raw.Return(raw.Int32Constant(expected_ret));
1113014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        wrapper = CompileGraph("Select-mixed-wrapper-const", cdesc, &graph,
1114014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch                               raw.Export());
1115014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
1116014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1117014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CodeRunner<int32_t> runnable(isolate, wrapper, &csig);
1118014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      CHECK_EQ(expected_ret, runnable.Call());
1119014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      for (int i = 0; i < expected_size; i++) {
1120014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch        CHECK_EQ(static_cast<int>(bytes[i]), static_cast<int>(output[i]));
1121014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch      }
1122014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch    }
1123014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch  }
1124014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}
1125014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1126014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1127014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(MixedParams_0) { MixedParamTest(0); }
1128014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(MixedParams_1) { MixedParamTest(1); }
1129014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(MixedParams_2) { MixedParamTest(2); }
1130014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochTEST(MixedParams_3) { MixedParamTest(3); }
1131014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch
1132342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdochtemplate <typename T>
1133342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdochvoid TestStackSlot(MachineType slot_type, T expected) {
1134342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // Test: Generate with a function f which reserves a stack slot, call an inner
1135342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // function g from f which writes into the stack slot of f.
1136342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
113721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  if (GetRegConfig()->num_allocatable_double_registers() < 2) return;
1138342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1139342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Isolate* isolate = CcTest::InitIsolateOnce();
1140342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1141342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // Lots of code to generate the build descriptor for the inner function.
114221efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int parray_gp[] = {GetRegConfig()->GetAllocatableGeneralCode(0),
114321efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch                     GetRegConfig()->GetAllocatableGeneralCode(1)};
114421efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray_gp[] = {GetRegConfig()->GetAllocatableGeneralCode(0)};
114521efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int parray_fp[] = {GetRegConfig()->GetAllocatableDoubleCode(0),
114621efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch                     GetRegConfig()->GetAllocatableDoubleCode(1)};
114721efce637eb329c94f1323b6a2334a1c977e1a9dBen Murdoch  int rarray_fp[] = {GetRegConfig()->GetAllocatableDoubleCode(0)};
1148342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Allocator palloc(parray_gp, 2, parray_fp, 2);
1149342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Allocator ralloc(rarray_gp, 1, rarray_fp, 1);
1150342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  RegisterConfig config(palloc, ralloc);
1151342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
11521b268ca467c924004286c97bac133db489cf43d0Ben Murdoch  Zone zone(isolate->allocator());
1153342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  HandleScope scope(isolate);
1154342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  MachineSignature::Builder builder(&zone, 1, 12);
1155342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  builder.AddReturn(MachineType::Int32());
1156342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  for (int i = 0; i < 10; i++) {
1157342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch    builder.AddParam(MachineType::Int32());
1158342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  }
1159342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  builder.AddParam(slot_type);
1160342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  builder.AddParam(MachineType::Pointer());
1161342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  MachineSignature* sig = builder.Build();
1162342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  CallDescriptor* desc = config.Create(&zone, sig);
1163342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1164342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // Create inner function g. g has lots of parameters so that they are passed
1165342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // over the stack.
1166342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Handle<Code> inner;
1167342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Graph graph(&zone);
1168342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  RawMachineAssembler g(isolate, &graph, desc);
1169342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1170342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  g.Store(slot_type.representation(), g.Parameter(11), g.Parameter(10),
1171342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch          WriteBarrierKind::kNoWriteBarrier);
1172342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  g.Return(g.Parameter(9));
1173342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  inner = CompileGraph("Compute", desc, &graph, g.Export());
1174342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1175342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  // Create function f with a stack slot which calls the inner function g.
1176342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  BufferedRawMachineAssemblerTester<T> f(slot_type);
1177342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Node* target = f.HeapConstant(inner);
1178342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Node* stack_slot = f.StackSlot(slot_type.representation());
1179342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  Node* args[12];
1180342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  for (int i = 0; i < 10; i++) {
1181342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch    args[i] = f.Int32Constant(i);
1182342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  }
1183342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  args[10] = f.Parameter(0);
1184342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  args[11] = stack_slot;
1185342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1186342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  f.CallN(desc, target, args);
1187342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  f.Return(f.Load(slot_type, stack_slot, f.IntPtrConstant(0)));
1188342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1189342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  CHECK_EQ(expected, f.Call(expected));
1190342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch}
1191342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1192342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen MurdochTEST(RunStackSlotInt32) {
1193342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  int32_t magic = 0x12345678;
1194342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  TestStackSlot(MachineType::Int32(), magic);
1195342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch}
1196342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1197342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch#if !V8_TARGET_ARCH_32_BIT
1198342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen MurdochTEST(RunStackSlotInt64) {
1199342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  int64_t magic = 0x123456789abcdef0;
1200342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  TestStackSlot(MachineType::Int64(), magic);
1201342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch}
1202342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch#endif
1203342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1204342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen MurdochTEST(RunStackSlotFloat32) {
1205342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  float magic = 1234.125f;
1206342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  TestStackSlot(MachineType::Float32(), magic);
1207342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch}
1208342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch
1209342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen MurdochTEST(RunStackSlotFloat64) {
1210342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  double magic = 3456.375;
1211342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch  TestStackSlot(MachineType::Float64(), magic);
1212342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch}
1213014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}  // namespace compiler
1214014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}  // namespace internal
1215014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}  // namespace v8
1216