Line data Source code
1 : // Copyright 2014 the V8 project authors. All rights reserved.
2 : // Use of this source code is governed by a BSD-style license that can be
3 : // found in the LICENSE file.
4 :
5 : #ifndef V8_INTERFACE_DESCRIPTORS_H_
6 : #define V8_INTERFACE_DESCRIPTORS_H_
7 :
8 : #include <memory>
9 :
10 : #include "src/globals.h"
11 : #include "src/isolate.h"
12 : #include "src/machine-type.h"
13 : #include "src/register-arch.h"
14 :
15 : namespace v8 {
16 : namespace internal {
17 :
18 : #define INTERFACE_DESCRIPTOR_LIST(V) \
19 : V(Abort) \
20 : V(Allocate) \
21 : V(AllocateHeapNumber) \
22 : V(ApiCallback) \
23 : V(ApiGetter) \
24 : V(ArgumentsAdaptor) \
25 : V(ArrayConstructor) \
26 : V(ArrayNArgumentsConstructor) \
27 : V(ArrayNoArgumentConstructor) \
28 : V(ArraySingleArgumentConstructor) \
29 : V(AsyncFunctionStackParameter) \
30 : V(BigIntToI64) \
31 : V(I64ToBigInt) \
32 : V(BinaryOp) \
33 : V(CallForwardVarargs) \
34 : V(CallFunctionTemplate) \
35 : V(CallTrampoline) \
36 : V(CallVarargs) \
37 : V(CallWithArrayLike) \
38 : V(CallWithSpread) \
39 : V(CEntry1ArgvOnStack) \
40 : V(CloneObjectWithVector) \
41 : V(Compare) \
42 : V(ConstructForwardVarargs) \
43 : V(ConstructStub) \
44 : V(ConstructVarargs) \
45 : V(ConstructWithArrayLike) \
46 : V(ConstructWithSpread) \
47 : V(ContextOnly) \
48 : V(CppBuiltinAdaptor) \
49 : V(EphemeronKeyBarrier) \
50 : V(FastNewFunctionContext) \
51 : V(FastNewObject) \
52 : V(FrameDropperTrampoline) \
53 : V(GetProperty) \
54 : V(GrowArrayElements) \
55 : V(InterpreterCEntry1) \
56 : V(InterpreterCEntry2) \
57 : V(InterpreterDispatch) \
58 : V(InterpreterPushArgsThenCall) \
59 : V(InterpreterPushArgsThenConstruct) \
60 : V(JSTrampoline) \
61 : V(Load) \
62 : V(LoadGlobal) \
63 : V(LoadGlobalWithVector) \
64 : V(LoadWithVector) \
65 : V(NewArgumentsElements) \
66 : V(NoContext) \
67 : V(RecordWrite) \
68 : V(ResumeGenerator) \
69 : V(RunMicrotasksEntry) \
70 : V(RunMicrotasks) \
71 : V(Store) \
72 : V(StoreGlobal) \
73 : V(StoreGlobalWithVector) \
74 : V(StoreTransition) \
75 : V(StoreWithVector) \
76 : V(StringAt) \
77 : V(StringSubstring) \
78 : V(TypeConversion) \
79 : V(TypeConversionStackParameter) \
80 : V(Typeof) \
81 : V(Void) \
82 : V(WasmAtomicNotify) \
83 : V(WasmI32AtomicWait) \
84 : V(WasmI64AtomicWait) \
85 : V(WasmMemoryGrow) \
86 : V(WasmTableGet) \
87 : V(WasmTableSet) \
88 : V(WasmThrow) \
89 : BUILTIN_LIST_TFS(V)
90 :
91 : class V8_EXPORT_PRIVATE CallInterfaceDescriptorData {
92 : public:
93 : enum Flag {
94 : kNoFlags = 0u,
95 : kNoContext = 1u << 0,
96 :
97 : // This indicates that the code uses a special frame that does not scan the
98 : // stack arguments, e.g. EntryFrame. And this allows the code to use
99 : // untagged stack arguments.
100 : kNoStackScan = 1u << 1,
101 : };
102 : typedef base::Flags<Flag> Flags;
103 :
104 : CallInterfaceDescriptorData() = default;
105 :
106 : // A copy of the passed in registers and param_representations is made
107 : // and owned by the CallInterfaceDescriptorData.
108 :
109 : void InitializePlatformSpecific(int register_parameter_count,
110 : const Register* registers);
111 :
112 : // if machine_types is null, then an array of size
113 : // (return_count + parameter_count) will be created with
114 : // MachineType::AnyTagged() for each member.
115 : //
116 : // if machine_types is not null, then it should be of the size
117 : // (return_count + parameter_count). Those members of the parameter array will
118 : // be initialized from {machine_types}, and the rest initialized to
119 : // MachineType::AnyTagged().
120 : void InitializePlatformIndependent(Flags flags, int return_count,
121 : int parameter_count,
122 : const MachineType* machine_types,
123 : int machine_types_length);
124 :
125 : void Reset();
126 :
127 : bool IsInitialized() const {
128 : return IsInitializedPlatformSpecific() &&
129 : IsInitializedPlatformIndependent();
130 : }
131 :
132 : Flags flags() const { return flags_; }
133 : int return_count() const { return return_count_; }
134 : int param_count() const { return param_count_; }
135 : int register_param_count() const { return register_param_count_; }
136 8349588 : Register register_param(int index) const { return register_params_[index]; }
137 : Register* register_params() const { return register_params_; }
138 : MachineType return_type(int index) const {
139 : DCHECK_LT(index, return_count_);
140 3290644 : return machine_types_[index];
141 : }
142 : MachineType param_type(int index) const {
143 : DCHECK_LT(index, param_count_);
144 7226081 : return machine_types_[return_count_ + index];
145 : }
146 :
147 : void RestrictAllocatableRegisters(const Register* registers, int num) {
148 : DCHECK_EQ(allocatable_registers_, 0);
149 1342176 : for (int i = 0; i < num; ++i) {
150 1220160 : allocatable_registers_ |= registers[i].bit();
151 : }
152 : DCHECK_GT(NumRegs(allocatable_registers_), 0);
153 : }
154 :
155 : RegList allocatable_registers() const { return allocatable_registers_; }
156 :
157 : private:
158 : bool IsInitializedPlatformSpecific() const {
159 : const bool initialized =
160 : (register_param_count_ == 0 && register_params_ == nullptr) ||
161 : (register_param_count_ > 0 && register_params_ != nullptr);
162 : // Platform-specific initialization happens before platform-independent.
163 : return initialized;
164 : }
165 : bool IsInitializedPlatformIndependent() const {
166 : const bool initialized =
167 : return_count_ >= 0 && param_count_ >= 0 && machine_types_ != nullptr;
168 : // Platform-specific initialization happens before platform-independent.
169 : return initialized;
170 : }
171 :
172 : #ifdef DEBUG
173 : bool AllStackParametersAreTagged() const;
174 : #endif // DEBUG
175 :
176 : int register_param_count_ = -1;
177 : int return_count_ = -1;
178 : int param_count_ = -1;
179 : Flags flags_ = kNoFlags;
180 :
181 : // Specifying the set of registers that could be used by the register
182 : // allocator. Currently, it's only used by RecordWrite code stub.
183 : RegList allocatable_registers_ = 0;
184 :
185 : // |registers_params_| defines registers that are used for parameter passing.
186 : // |machine_types_| defines machine types for resulting values and incomping
187 : // parameters.
188 : // Both arrays are allocated dynamically by the InterfaceDescriptor and
189 : // freed on destruction. This is because static arrays cause creation of
190 : // runtime static initializers which we don't want.
191 : Register* register_params_ = nullptr;
192 : MachineType* machine_types_ = nullptr;
193 :
194 : DISALLOW_COPY_AND_ASSIGN(CallInterfaceDescriptorData);
195 : };
196 :
197 : class V8_EXPORT_PRIVATE CallDescriptors : public AllStatic {
198 : public:
199 : enum Key {
200 : #define DEF_ENUM(name, ...) name,
201 : INTERFACE_DESCRIPTOR_LIST(DEF_ENUM)
202 : #undef DEF_ENUM
203 : NUMBER_OF_DESCRIPTORS
204 : };
205 :
206 : static void InitializeOncePerProcess();
207 : static void TearDown();
208 :
209 : static CallInterfaceDescriptorData* call_descriptor_data(
210 : CallDescriptors::Key key) {
211 2651326 : return &call_descriptor_data_[key];
212 : }
213 :
214 : static Key GetKey(const CallInterfaceDescriptorData* data) {
215 3290425 : ptrdiff_t index = data - call_descriptor_data_;
216 : DCHECK_LE(0, index);
217 : DCHECK_LT(index, CallDescriptors::NUMBER_OF_DESCRIPTORS);
218 : return static_cast<CallDescriptors::Key>(index);
219 : }
220 :
221 : private:
222 : static CallInterfaceDescriptorData
223 : call_descriptor_data_[NUMBER_OF_DESCRIPTORS];
224 : };
225 :
226 10571033 : class V8_EXPORT_PRIVATE CallInterfaceDescriptor {
227 : public:
228 : typedef CallInterfaceDescriptorData::Flags Flags;
229 :
230 : CallInterfaceDescriptor() : data_(nullptr) {}
231 25712957 : virtual ~CallInterfaceDescriptor() = default;
232 :
233 : explicit CallInterfaceDescriptor(CallDescriptors::Key key)
234 15341555 : : data_(CallDescriptors::call_descriptor_data(key)) {}
235 :
236 : Flags flags() const { return data()->flags(); }
237 :
238 : bool HasContextParameter() const {
239 : return (flags() & CallInterfaceDescriptorData::kNoContext) == 0;
240 : }
241 :
242 : int GetReturnCount() const { return data()->return_count(); }
243 :
244 : MachineType GetReturnType(int index) const {
245 : DCHECK_LT(index, data()->return_count());
246 : return data()->return_type(index);
247 : }
248 :
249 : int GetParameterCount() const { return data()->param_count(); }
250 :
251 : int GetRegisterParameterCount() const {
252 : return data()->register_param_count();
253 : }
254 :
255 : int GetStackParameterCount() const {
256 2431797 : return data()->param_count() - data()->register_param_count();
257 : }
258 :
259 : Register GetRegisterParameter(int index) const {
260 : return data()->register_param(index);
261 : }
262 :
263 : MachineType GetParameterType(int index) const {
264 : DCHECK_LT(index, data()->param_count());
265 : return data()->param_type(index);
266 : }
267 :
268 : RegList allocatable_registers() const {
269 : return data()->allocatable_registers();
270 : }
271 :
272 : static const Register ContextRegister();
273 :
274 : const char* DebugName() const;
275 :
276 : protected:
277 : const CallInterfaceDescriptorData* data() const { return data_; }
278 :
279 0 : virtual void InitializePlatformSpecific(CallInterfaceDescriptorData* data) {
280 0 : UNREACHABLE();
281 : }
282 :
283 122016 : virtual void InitializePlatformIndependent(
284 : CallInterfaceDescriptorData* data) {
285 : // Default descriptor configuration: one result, all parameters are passed
286 : // in registers and all parameters have MachineType::AnyTagged() type.
287 122016 : data->InitializePlatformIndependent(CallInterfaceDescriptorData::kNoFlags,
288 : 1, data->register_param_count(),
289 122016 : nullptr, 0);
290 122016 : }
291 :
292 : // Initializes |data| using the platform dependent default set of registers.
293 : // It is intended to be used for TurboFan stubs when particular set of
294 : // registers does not matter.
295 : static void DefaultInitializePlatformSpecific(
296 : CallInterfaceDescriptorData* data, int register_parameter_count);
297 :
298 : // Initializes |data| using the platform dependent default set of registers
299 : // for JavaScript-compatible calling convention.
300 : // It is intended to be used for TurboFan stubs being called with JavaScript
301 : // linkage + additional parameters on registers and stack.
302 : static void JSDefaultInitializePlatformSpecific(
303 : CallInterfaceDescriptorData* data, int non_js_register_parameter_count);
304 :
305 : // Checks if float parameters are not assigned invalid registers.
306 : bool CheckFloatingPointParameters(CallInterfaceDescriptorData* data) {
307 : for (int i = 0; i < data->register_param_count(); i++) {
308 : if (IsFloatingPoint(data->param_type(i).representation())) {
309 : if (!IsValidFloatParameterRegister(data->register_param(i))) {
310 : return false;
311 : }
312 : }
313 : }
314 : return true;
315 : }
316 :
317 : bool IsValidFloatParameterRegister(Register reg);
318 :
319 : private:
320 : // {CallDescriptors} is allowed to call the private {Initialize} method.
321 : friend class CallDescriptors;
322 :
323 : const CallInterfaceDescriptorData* data_;
324 :
325 2318304 : void Initialize(CallInterfaceDescriptorData* data) {
326 : // The passed pointer should be a modifiable pointer to our own data.
327 : DCHECK_EQ(data, data_);
328 : DCHECK(!data->IsInitialized());
329 14885952 : InitializePlatformSpecific(data);
330 14885952 : InitializePlatformIndependent(data);
331 : DCHECK(data->IsInitialized());
332 : DCHECK(CheckFloatingPointParameters(data));
333 2318304 : }
334 : };
335 :
336 : #define DECLARE_DESCRIPTOR_WITH_BASE(name, base) \
337 : public: \
338 : explicit name() : base(key()) {} \
339 : static inline CallDescriptors::Key key();
340 :
341 : #if defined(V8_TARGET_ARCH_IA32)
342 : // To support all possible cases, we must limit the number of register args for
343 : // TFS builtins on ia32 to 3. Out of the 6 allocatable registers, esi is taken
344 : // as the context register and ebx is the root register. One register must
345 : // remain available to store the jump/call target. Thus 3 registers remain for
346 : // arguments. The reason this applies to TFS builtins specifically is because
347 : // this becomes relevant for builtins used as targets of Torque function
348 : // pointers (which must have a register available to store the target).
349 : // TODO(jgruber): Ideally we should just decrement kMaxBuiltinRegisterParams but
350 : // that comes with its own set of complications. It's possible, but requires
351 : // refactoring the calling convention of other existing stubs.
352 : constexpr int kMaxBuiltinRegisterParams = 4;
353 : constexpr int kMaxTFSBuiltinRegisterParams = 3;
354 : #else
355 : constexpr int kMaxBuiltinRegisterParams = 5;
356 : constexpr int kMaxTFSBuiltinRegisterParams = kMaxBuiltinRegisterParams;
357 : #endif
358 : STATIC_ASSERT(kMaxTFSBuiltinRegisterParams <= kMaxBuiltinRegisterParams);
359 :
360 : #define DECLARE_DEFAULT_DESCRIPTOR(name, base) \
361 : DECLARE_DESCRIPTOR_WITH_BASE(name, base) \
362 : protected: \
363 : static const int kRegisterParams = \
364 : kParameterCount > kMaxTFSBuiltinRegisterParams \
365 : ? kMaxTFSBuiltinRegisterParams \
366 : : kParameterCount; \
367 : static const int kStackParams = kParameterCount - kRegisterParams; \
368 : void InitializePlatformSpecific(CallInterfaceDescriptorData* data) \
369 : override { \
370 : DefaultInitializePlatformSpecific(data, kRegisterParams); \
371 : } \
372 : void InitializePlatformIndependent(CallInterfaceDescriptorData* data) \
373 : override { \
374 : data->InitializePlatformIndependent(Flags(kDescriptorFlags), kReturnCount, \
375 : kParameterCount, nullptr, 0); \
376 : } \
377 : name(CallDescriptors::Key key) : base(key) {} \
378 : \
379 : public:
380 :
381 : #define DECLARE_JS_COMPATIBLE_DESCRIPTOR(name, base, \
382 : non_js_reg_parameters_count) \
383 : DECLARE_DESCRIPTOR_WITH_BASE(name, base) \
384 : protected: \
385 : void InitializePlatformSpecific(CallInterfaceDescriptorData* data) \
386 : override { \
387 : JSDefaultInitializePlatformSpecific(data, non_js_reg_parameters_count); \
388 : } \
389 : name(CallDescriptors::Key key) : base(key) {} \
390 : \
391 : public:
392 :
393 : #define DEFINE_RESULT_AND_PARAMETERS(return_count, ...) \
394 : static constexpr int kDescriptorFlags = \
395 : CallInterfaceDescriptorData::kNoFlags; \
396 : static constexpr int kReturnCount = return_count; \
397 : enum ParameterIndices { \
398 : __dummy = -1, /* to be able to pass zero arguments */ \
399 : ##__VA_ARGS__, \
400 : \
401 : kParameterCount, \
402 : kContext = kParameterCount /* implicit parameter */ \
403 : };
404 :
405 : #define DEFINE_RESULT_AND_PARAMETERS_NO_CONTEXT(return_count, ...) \
406 : static constexpr int kDescriptorFlags = \
407 : CallInterfaceDescriptorData::kNoContext; \
408 : static constexpr int kReturnCount = return_count; \
409 : enum ParameterIndices { \
410 : __dummy = -1, /* to be able to pass zero arguments */ \
411 : ##__VA_ARGS__, \
412 : \
413 : kParameterCount \
414 : };
415 :
416 : // This is valid only for builtins that use EntryFrame, which does not scan
417 : // stack arguments on GC.
418 : #define DEFINE_PARAMETERS_ENTRY(...) \
419 : static constexpr int kDescriptorFlags = \
420 : CallInterfaceDescriptorData::kNoContext | \
421 : CallInterfaceDescriptorData::kNoStackScan; \
422 : static constexpr int kReturnCount = 1; \
423 : enum ParameterIndices { \
424 : __dummy = -1, /* to be able to pass zero arguments */ \
425 : ##__VA_ARGS__, \
426 : \
427 : kParameterCount \
428 : };
429 :
430 : #define DEFINE_PARAMETERS(...) DEFINE_RESULT_AND_PARAMETERS(1, ##__VA_ARGS__)
431 :
432 : #define DEFINE_PARAMETERS_NO_CONTEXT(...) \
433 : DEFINE_RESULT_AND_PARAMETERS_NO_CONTEXT(1, ##__VA_ARGS__)
434 :
435 : #define DEFINE_RESULT_AND_PARAMETER_TYPES(...) \
436 : void InitializePlatformIndependent(CallInterfaceDescriptorData* data) \
437 : override { \
438 : MachineType machine_types[] = {__VA_ARGS__}; \
439 : static_assert( \
440 : kReturnCount + kParameterCount == arraysize(machine_types), \
441 : "Parameter names definition is not consistent with parameter types"); \
442 : data->InitializePlatformIndependent(Flags(kDescriptorFlags), kReturnCount, \
443 : kParameterCount, machine_types, \
444 : arraysize(machine_types)); \
445 : }
446 :
447 : #define DEFINE_PARAMETER_TYPES(...) \
448 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::AnyTagged() /* result */, \
449 : ##__VA_ARGS__)
450 :
451 : #define DEFINE_JS_PARAMETERS(...) \
452 : static constexpr int kDescriptorFlags = \
453 : CallInterfaceDescriptorData::kNoFlags; \
454 : static constexpr int kReturnCount = 1; \
455 : enum ParameterIndices { \
456 : kTarget, \
457 : kNewTarget, \
458 : kActualArgumentsCount, \
459 : ##__VA_ARGS__, \
460 : \
461 : kParameterCount, \
462 : kContext = kParameterCount /* implicit parameter */ \
463 : };
464 :
465 : #define DEFINE_JS_PARAMETER_TYPES(...) \
466 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), /* kTarget */ \
467 : MachineType::AnyTagged(), /* kNewTarget */ \
468 : MachineType::Int32(), /* kActualArgumentsCount */ \
469 : ##__VA_ARGS__)
470 :
471 : #define DECLARE_DESCRIPTOR(name, base) \
472 : DECLARE_DESCRIPTOR_WITH_BASE(name, base) \
473 : protected: \
474 : void InitializePlatformSpecific(CallInterfaceDescriptorData* data) override; \
475 : name(CallDescriptors::Key key) : base(key) {} \
476 : \
477 : public:
478 :
479 122137 : class V8_EXPORT_PRIVATE VoidDescriptor : public CallInterfaceDescriptor {
480 : public:
481 : DEFINE_PARAMETERS()
482 122016 : DEFINE_PARAMETER_TYPES()
483 61129 : DECLARE_DESCRIPTOR(VoidDescriptor, CallInterfaceDescriptor)
484 : };
485 :
486 : // Dummy descriptor used to mark builtins that don't yet have their proper
487 : // descriptor associated.
488 : typedef VoidDescriptor DummyDescriptor;
489 :
490 : // Dummy descriptor that marks builtins with C calling convention.
491 : typedef VoidDescriptor CCallDescriptor;
492 :
493 350236 : class AllocateDescriptor : public CallInterfaceDescriptor {
494 : public:
495 : DEFINE_PARAMETERS_NO_CONTEXT(kRequestedSize)
496 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::TaggedPointer(), // result 1
497 : MachineType::IntPtr()) // kRequestedSize
498 175118 : DECLARE_DESCRIPTOR(AllocateDescriptor, CallInterfaceDescriptor)
499 : };
500 :
501 : // This descriptor defines the JavaScript calling convention that can be used
502 : // by stubs: target, new.target, argc (not including the receiver) and context
503 : // are passed in registers while receiver and the rest of the JS arguments are
504 : // passed on the stack.
505 122520 : class JSTrampolineDescriptor : public CallInterfaceDescriptor {
506 : public:
507 : DEFINE_JS_PARAMETERS()
508 122016 : DEFINE_JS_PARAMETER_TYPES()
509 :
510 122520 : DECLARE_JS_COMPATIBLE_DESCRIPTOR(JSTrampolineDescriptor,
511 : CallInterfaceDescriptor, 0)
512 : };
513 :
514 122016 : class ContextOnlyDescriptor : public CallInterfaceDescriptor {
515 : public:
516 : DEFINE_PARAMETERS()
517 122016 : DEFINE_PARAMETER_TYPES()
518 61008 : DECLARE_DESCRIPTOR(ContextOnlyDescriptor, CallInterfaceDescriptor)
519 : };
520 :
521 367212 : class NoContextDescriptor : public CallInterfaceDescriptor {
522 : public:
523 : DEFINE_PARAMETERS_NO_CONTEXT()
524 122016 : DEFINE_PARAMETER_TYPES()
525 183631 : DECLARE_DESCRIPTOR(NoContextDescriptor, CallInterfaceDescriptor)
526 : };
527 :
528 : // LoadDescriptor is used by all stubs that implement Load/KeyedLoad ICs.
529 246832 : class LoadDescriptor : public CallInterfaceDescriptor {
530 : public:
531 : DEFINE_PARAMETERS(kReceiver, kName, kSlot)
532 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
533 : MachineType::AnyTagged(), // kName
534 : MachineType::TaggedSigned()) // kSlot
535 123416 : DECLARE_DESCRIPTOR(LoadDescriptor, CallInterfaceDescriptor)
536 :
537 : static const Register ReceiverRegister();
538 : static const Register NameRegister();
539 : static const Register SlotRegister();
540 : };
541 :
542 244032 : class LoadGlobalDescriptor : public CallInterfaceDescriptor {
543 : public:
544 : DEFINE_PARAMETERS(kName, kSlot)
545 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kName
546 : MachineType::TaggedSigned()) // kSlot
547 122016 : DECLARE_DESCRIPTOR(LoadGlobalDescriptor, CallInterfaceDescriptor)
548 :
549 : static const Register NameRegister() {
550 122016 : return LoadDescriptor::NameRegister();
551 : }
552 :
553 : static const Register SlotRegister() {
554 122016 : return LoadDescriptor::SlotRegister();
555 : }
556 : };
557 :
558 366832 : class StoreDescriptor : public CallInterfaceDescriptor {
559 : public:
560 : DEFINE_PARAMETERS(kReceiver, kName, kValue, kSlot)
561 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
562 : MachineType::AnyTagged(), // kName
563 : MachineType::AnyTagged(), // kValue
564 : MachineType::TaggedSigned()) // kSlot
565 183416 : DECLARE_DESCRIPTOR(StoreDescriptor, CallInterfaceDescriptor)
566 :
567 : static const Register ReceiverRegister();
568 : static const Register NameRegister();
569 : static const Register ValueRegister();
570 : static const Register SlotRegister();
571 :
572 : #if V8_TARGET_ARCH_IA32
573 : static const bool kPassLastArgsOnStack = true;
574 : #else
575 : static const bool kPassLastArgsOnStack = false;
576 : #endif
577 :
578 : // Pass value and slot through the stack.
579 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 2 : 0;
580 : };
581 :
582 122240 : class StoreTransitionDescriptor : public StoreDescriptor {
583 : public:
584 : DEFINE_PARAMETERS(kReceiver, kName, kMap, kValue, kSlot, kVector)
585 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
586 : MachineType::AnyTagged(), // kName
587 : MachineType::AnyTagged(), // kMap
588 : MachineType::AnyTagged(), // kValue
589 : MachineType::TaggedSigned(), // kSlot
590 : MachineType::AnyTagged()) // kVector
591 61120 : DECLARE_DESCRIPTOR(StoreTransitionDescriptor, StoreDescriptor)
592 :
593 : static const Register MapRegister();
594 : static const Register SlotRegister();
595 : static const Register VectorRegister();
596 :
597 : // Pass value, slot and vector through the stack.
598 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 3 : 0;
599 : };
600 :
601 122576 : class StoreWithVectorDescriptor : public StoreDescriptor {
602 : public:
603 : DEFINE_PARAMETERS(kReceiver, kName, kValue, kSlot, kVector)
604 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
605 : MachineType::AnyTagged(), // kName
606 : MachineType::AnyTagged(), // kValue
607 : MachineType::TaggedSigned(), // kSlot
608 : MachineType::AnyTagged()) // kVector
609 61288 : DECLARE_DESCRIPTOR(StoreWithVectorDescriptor, StoreDescriptor)
610 :
611 : static const Register VectorRegister();
612 :
613 : // Pass value, slot and vector through the stack.
614 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 3 : 0;
615 : };
616 :
617 244032 : class StoreGlobalDescriptor : public CallInterfaceDescriptor {
618 : public:
619 : DEFINE_PARAMETERS(kName, kValue, kSlot)
620 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kName
621 : MachineType::AnyTagged(), // kValue
622 : MachineType::TaggedSigned()) // kSlot
623 122016 : DECLARE_DESCRIPTOR(StoreGlobalDescriptor, CallInterfaceDescriptor)
624 :
625 : static const bool kPassLastArgsOnStack =
626 : StoreDescriptor::kPassLastArgsOnStack;
627 : // Pass value and slot through the stack.
628 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 2 : 0;
629 :
630 : static const Register NameRegister() {
631 122016 : return StoreDescriptor::NameRegister();
632 : }
633 :
634 : static const Register ValueRegister() {
635 122016 : return StoreDescriptor::ValueRegister();
636 : }
637 :
638 : static const Register SlotRegister() {
639 122016 : return StoreDescriptor::SlotRegister();
640 : }
641 : };
642 :
643 122016 : class StoreGlobalWithVectorDescriptor : public StoreGlobalDescriptor {
644 : public:
645 : DEFINE_PARAMETERS(kName, kValue, kSlot, kVector)
646 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kName
647 : MachineType::AnyTagged(), // kValue
648 : MachineType::TaggedSigned(), // kSlot
649 : MachineType::AnyTagged()) // kVector
650 61008 : DECLARE_DESCRIPTOR(StoreGlobalWithVectorDescriptor, StoreGlobalDescriptor)
651 :
652 : static const Register VectorRegister() {
653 61008 : return StoreWithVectorDescriptor::VectorRegister();
654 : }
655 :
656 : // Pass value, slot and vector through the stack.
657 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 3 : 0;
658 : };
659 :
660 124816 : class LoadWithVectorDescriptor : public LoadDescriptor {
661 : public:
662 : DEFINE_PARAMETERS(kReceiver, kName, kSlot, kVector)
663 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
664 : MachineType::AnyTagged(), // kName
665 : MachineType::TaggedSigned(), // kSlot
666 : MachineType::AnyTagged()) // kVector
667 62408 : DECLARE_DESCRIPTOR(LoadWithVectorDescriptor, LoadDescriptor)
668 :
669 : static const Register VectorRegister();
670 :
671 : #if V8_TARGET_ARCH_IA32
672 : static const bool kPassLastArgsOnStack = true;
673 : #else
674 : static const bool kPassLastArgsOnStack = false;
675 : #endif
676 :
677 : // Pass vector through the stack.
678 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 1 : 0;
679 : };
680 :
681 122016 : class LoadGlobalWithVectorDescriptor : public LoadGlobalDescriptor {
682 : public:
683 : DEFINE_PARAMETERS(kName, kSlot, kVector)
684 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kName
685 : MachineType::TaggedSigned(), // kSlot
686 : MachineType::AnyTagged()) // kVector
687 61008 : DECLARE_DESCRIPTOR(LoadGlobalWithVectorDescriptor, LoadGlobalDescriptor)
688 :
689 : #if V8_TARGET_ARCH_IA32
690 : // On ia32, LoadWithVectorDescriptor passes vector on the stack and thus we
691 : // need to choose a new register here.
692 : static const Register VectorRegister() { return edx; }
693 : #else
694 : static const Register VectorRegister() {
695 61008 : return LoadWithVectorDescriptor::VectorRegister();
696 : }
697 : #endif
698 : };
699 :
700 122016 : class FastNewFunctionContextDescriptor : public CallInterfaceDescriptor {
701 : public:
702 : DEFINE_PARAMETERS(kScopeInfo, kSlots)
703 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kScopeInfo
704 : MachineType::Int32()) // kSlots
705 61008 : DECLARE_DESCRIPTOR(FastNewFunctionContextDescriptor, CallInterfaceDescriptor)
706 :
707 : static const Register ScopeInfoRegister();
708 : static const Register SlotsRegister();
709 : };
710 :
711 122016 : class FastNewObjectDescriptor : public CallInterfaceDescriptor {
712 : public:
713 : DEFINE_PARAMETERS(kTarget, kNewTarget)
714 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
715 : MachineType::AnyTagged()) // kNewTarget
716 61008 : DECLARE_DESCRIPTOR(FastNewObjectDescriptor, CallInterfaceDescriptor)
717 : static const Register TargetRegister();
718 : static const Register NewTargetRegister();
719 : };
720 :
721 122072 : class RecordWriteDescriptor final : public CallInterfaceDescriptor {
722 : public:
723 : DEFINE_PARAMETERS_NO_CONTEXT(kObject, kSlot, kRememberedSet, kFPMode)
724 122016 : DEFINE_PARAMETER_TYPES(MachineType::TaggedPointer(), // kObject
725 : MachineType::Pointer(), // kSlot
726 : MachineType::TaggedSigned(), // kRememberedSet
727 : MachineType::TaggedSigned()) // kFPMode
728 :
729 61064 : DECLARE_DESCRIPTOR(RecordWriteDescriptor, CallInterfaceDescriptor)
730 : };
731 :
732 122016 : class EphemeronKeyBarrierDescriptor final : public CallInterfaceDescriptor {
733 : public:
734 : DEFINE_PARAMETERS_NO_CONTEXT(kObject, kSlotAddress, kFPMode)
735 122016 : DEFINE_PARAMETER_TYPES(MachineType::TaggedPointer(), // kObject
736 : MachineType::Pointer(), // kSlotAddress
737 : MachineType::TaggedSigned()) // kFPMode
738 :
739 61008 : DECLARE_DESCRIPTOR(EphemeronKeyBarrierDescriptor, CallInterfaceDescriptor)
740 : };
741 :
742 287404 : class TypeConversionDescriptor final : public CallInterfaceDescriptor {
743 : public:
744 : DEFINE_PARAMETERS(kArgument)
745 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged())
746 143729 : DECLARE_DESCRIPTOR(TypeConversionDescriptor, CallInterfaceDescriptor)
747 :
748 : static const Register ArgumentRegister();
749 : };
750 :
751 122016 : class TypeConversionStackParameterDescriptor final
752 : : public CallInterfaceDescriptor {
753 : public:
754 : DEFINE_PARAMETERS(kArgument)
755 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged())
756 61008 : DECLARE_DESCRIPTOR(TypeConversionStackParameterDescriptor,
757 : CallInterfaceDescriptor)
758 : };
759 :
760 122016 : class AsyncFunctionStackParameterDescriptor final
761 : : public CallInterfaceDescriptor {
762 : public:
763 : DEFINE_PARAMETERS(kPromise, kResult)
764 122016 : DEFINE_PARAMETER_TYPES(MachineType::TaggedPointer(), MachineType::AnyTagged())
765 61008 : DECLARE_DESCRIPTOR(AsyncFunctionStackParameterDescriptor,
766 : CallInterfaceDescriptor)
767 : };
768 :
769 122016 : class GetPropertyDescriptor final : public CallInterfaceDescriptor {
770 : public:
771 : DEFINE_PARAMETERS(kObject, kKey)
772 244032 : DECLARE_DEFAULT_DESCRIPTOR(GetPropertyDescriptor, CallInterfaceDescriptor)
773 : };
774 :
775 122016 : class TypeofDescriptor : public CallInterfaceDescriptor {
776 : public:
777 : DEFINE_PARAMETERS(kObject)
778 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged())
779 61008 : DECLARE_DESCRIPTOR(TypeofDescriptor, CallInterfaceDescriptor)
780 : };
781 :
782 125488 : class CallTrampolineDescriptor : public CallInterfaceDescriptor {
783 : public:
784 : DEFINE_PARAMETERS(kFunction, kActualArgumentsCount)
785 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kFunction
786 : MachineType::Int32()) // kActualArgumentsCount
787 62772 : DECLARE_DESCRIPTOR(CallTrampolineDescriptor, CallInterfaceDescriptor)
788 : };
789 :
790 122016 : class CallVarargsDescriptor : public CallInterfaceDescriptor {
791 : public:
792 : DEFINE_PARAMETERS(kTarget, kActualArgumentsCount, kArgumentsLength,
793 : kArgumentsList)
794 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
795 : MachineType::Int32(), // kActualArgumentsCount
796 : MachineType::Int32(), // kArgumentsLength
797 : MachineType::AnyTagged()) // kArgumentsList
798 61008 : DECLARE_DESCRIPTOR(CallVarargsDescriptor, CallInterfaceDescriptor)
799 : };
800 :
801 122016 : class CallForwardVarargsDescriptor : public CallInterfaceDescriptor {
802 : public:
803 : DEFINE_PARAMETERS(kTarget, kActualArgumentsCount, kStartIndex)
804 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
805 : MachineType::Int32(), // kActualArgumentsCount
806 : MachineType::Int32()) // kStartIndex
807 61008 : DECLARE_DESCRIPTOR(CallForwardVarargsDescriptor, CallInterfaceDescriptor)
808 : };
809 :
810 122016 : class CallFunctionTemplateDescriptor : public CallInterfaceDescriptor {
811 : public:
812 : DEFINE_PARAMETERS(kFunctionTemplateInfo, kArgumentsCount)
813 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kFunctionTemplateInfo
814 : MachineType::IntPtr()) // kArgumentsCount
815 61008 : DECLARE_DESCRIPTOR(CallFunctionTemplateDescriptor, CallInterfaceDescriptor)
816 : };
817 :
818 122016 : class CallWithSpreadDescriptor : public CallInterfaceDescriptor {
819 : public:
820 : DEFINE_PARAMETERS(kTarget, kArgumentsCount, kSpread)
821 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
822 : MachineType::Int32(), // kArgumentsCount
823 : MachineType::AnyTagged()) // kSpread
824 61008 : DECLARE_DESCRIPTOR(CallWithSpreadDescriptor, CallInterfaceDescriptor)
825 : };
826 :
827 122016 : class CallWithArrayLikeDescriptor : public CallInterfaceDescriptor {
828 : public:
829 : DEFINE_PARAMETERS(kTarget, kArgumentsList)
830 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
831 : MachineType::AnyTagged()) // kArgumentsList
832 61008 : DECLARE_DESCRIPTOR(CallWithArrayLikeDescriptor, CallInterfaceDescriptor)
833 : };
834 :
835 122016 : class ConstructVarargsDescriptor : public CallInterfaceDescriptor {
836 : public:
837 : DEFINE_JS_PARAMETERS(kArgumentsLength, kArgumentsList)
838 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::Int32(), // kArgumentsLength
839 : MachineType::AnyTagged()) // kArgumentsList
840 :
841 61008 : DECLARE_DESCRIPTOR(ConstructVarargsDescriptor, CallInterfaceDescriptor)
842 : };
843 :
844 122016 : class ConstructForwardVarargsDescriptor : public CallInterfaceDescriptor {
845 : public:
846 : DEFINE_JS_PARAMETERS(kStartIndex)
847 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::Int32())
848 61008 : DECLARE_DESCRIPTOR(ConstructForwardVarargsDescriptor, CallInterfaceDescriptor)
849 : };
850 :
851 122016 : class ConstructWithSpreadDescriptor : public CallInterfaceDescriptor {
852 : public:
853 : DEFINE_JS_PARAMETERS(kSpread)
854 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::AnyTagged())
855 61008 : DECLARE_DESCRIPTOR(ConstructWithSpreadDescriptor, CallInterfaceDescriptor)
856 : };
857 :
858 122016 : class ConstructWithArrayLikeDescriptor : public CallInterfaceDescriptor {
859 : public:
860 : DEFINE_PARAMETERS(kTarget, kNewTarget, kArgumentsList)
861 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kTarget
862 : MachineType::AnyTagged(), // kNewTarget
863 : MachineType::AnyTagged()) // kArgumentsList
864 61008 : DECLARE_DESCRIPTOR(ConstructWithArrayLikeDescriptor, CallInterfaceDescriptor)
865 : };
866 :
867 : // TODO(ishell): consider merging this with ArrayConstructorDescriptor
868 125102 : class ConstructStubDescriptor : public CallInterfaceDescriptor {
869 : public:
870 : // TODO(jgruber): Remove the unused allocation site parameter.
871 : DEFINE_JS_PARAMETERS(kAllocationSite)
872 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::AnyTagged())
873 :
874 : // TODO(ishell): Use DECLARE_JS_COMPATIBLE_DESCRIPTOR if registers match
875 64094 : DECLARE_DESCRIPTOR(ConstructStubDescriptor, CallInterfaceDescriptor)
876 : };
877 :
878 122016 : class AbortDescriptor : public CallInterfaceDescriptor {
879 : public:
880 : DEFINE_PARAMETERS_NO_CONTEXT(kMessageOrMessageId)
881 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged())
882 61008 : DECLARE_DESCRIPTOR(AbortDescriptor, CallInterfaceDescriptor)
883 : };
884 :
885 145170 : class AllocateHeapNumberDescriptor : public CallInterfaceDescriptor {
886 : public:
887 : DEFINE_PARAMETERS_NO_CONTEXT()
888 122016 : DEFINE_PARAMETER_TYPES()
889 72613 : DECLARE_DESCRIPTOR(AllocateHeapNumberDescriptor, CallInterfaceDescriptor)
890 : };
891 :
892 122350 : class ArrayConstructorDescriptor : public CallInterfaceDescriptor {
893 : public:
894 : DEFINE_JS_PARAMETERS(kAllocationSite)
895 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::AnyTagged())
896 :
897 122183 : DECLARE_JS_COMPATIBLE_DESCRIPTOR(ArrayConstructorDescriptor,
898 : CallInterfaceDescriptor, 1)
899 : };
900 :
901 366832 : class ArrayNArgumentsConstructorDescriptor : public CallInterfaceDescriptor {
902 : public:
903 : // This descriptor declares only register arguments while respective number
904 : // of JS arguments stay on the expression stack.
905 : // The ArrayNArgumentsConstructor builtin does not access stack arguments
906 : // directly it just forwards them to the runtime function.
907 : DEFINE_PARAMETERS(kFunction, kAllocationSite, kActualArgumentsCount)
908 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kFunction,
909 : MachineType::AnyTagged(), // kAllocationSite
910 : MachineType::Int32()) // kActualArgumentsCount
911 183808 : DECLARE_DESCRIPTOR(ArrayNArgumentsConstructorDescriptor,
912 : CallInterfaceDescriptor)
913 : };
914 :
915 122016 : class ArrayNoArgumentConstructorDescriptor
916 : : public ArrayNArgumentsConstructorDescriptor {
917 : public:
918 : // This descriptor declares same register arguments as the parent
919 : // ArrayNArgumentsConstructorDescriptor and it declares indices for
920 : // JS arguments passed on the expression stack.
921 : DEFINE_PARAMETERS(kFunction, kAllocationSite, kActualArgumentsCount,
922 : kFunctionParameter)
923 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kFunction
924 : MachineType::AnyTagged(), // kAllocationSite
925 : MachineType::Int32(), // kActualArgumentsCount
926 : MachineType::AnyTagged()) // kFunctionParameter
927 61008 : DECLARE_DESCRIPTOR(ArrayNoArgumentConstructorDescriptor,
928 : ArrayNArgumentsConstructorDescriptor)
929 : };
930 :
931 122016 : class ArraySingleArgumentConstructorDescriptor
932 : : public ArrayNArgumentsConstructorDescriptor {
933 : public:
934 : // This descriptor declares same register arguments as the parent
935 : // ArrayNArgumentsConstructorDescriptor and it declares indices for
936 : // JS arguments passed on the expression stack.
937 : DEFINE_PARAMETERS(kFunction, kAllocationSite, kActualArgumentsCount,
938 : kFunctionParameter, kArraySizeSmiParameter)
939 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kFunction
940 : MachineType::AnyTagged(), // kAllocationSite
941 : MachineType::Int32(), // kActualArgumentsCount
942 : MachineType::AnyTagged(), // kFunctionParameter
943 : MachineType::AnyTagged()) // kArraySizeSmiParameter
944 61008 : DECLARE_DESCRIPTOR(ArraySingleArgumentConstructorDescriptor,
945 : ArrayNArgumentsConstructorDescriptor)
946 : };
947 :
948 122016 : class CompareDescriptor : public CallInterfaceDescriptor {
949 : public:
950 : DEFINE_PARAMETERS(kLeft, kRight)
951 61008 : DECLARE_DESCRIPTOR(CompareDescriptor, CallInterfaceDescriptor)
952 : };
953 :
954 :
955 122016 : class BinaryOpDescriptor : public CallInterfaceDescriptor {
956 : public:
957 : DEFINE_PARAMETERS(kLeft, kRight)
958 61008 : DECLARE_DESCRIPTOR(BinaryOpDescriptor, CallInterfaceDescriptor)
959 : };
960 :
961 : // This desciptor is shared among String.p.charAt/charCodeAt/codePointAt
962 : // as they all have the same interface.
963 122016 : class StringAtDescriptor final : public CallInterfaceDescriptor {
964 : public:
965 : DEFINE_PARAMETERS(kReceiver, kPosition)
966 : // TODO(turbofan): Return untagged value here.
967 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::TaggedSigned(), // result 1
968 : MachineType::AnyTagged(), // kReceiver
969 : MachineType::IntPtr()) // kPosition
970 61008 : DECLARE_DESCRIPTOR(StringAtDescriptor, CallInterfaceDescriptor)
971 : };
972 :
973 122016 : class StringSubstringDescriptor final : public CallInterfaceDescriptor {
974 : public:
975 : DEFINE_PARAMETERS(kString, kFrom, kTo)
976 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kString
977 : MachineType::IntPtr(), // kFrom
978 : MachineType::IntPtr()) // kTo
979 :
980 : // TODO(turbofan): Allow builtins to return untagged values.
981 61008 : DECLARE_DESCRIPTOR(StringSubstringDescriptor, CallInterfaceDescriptor)
982 : };
983 :
984 123612 : class ArgumentsAdaptorDescriptor : public CallInterfaceDescriptor {
985 : public:
986 : DEFINE_JS_PARAMETERS(kExpectedArgumentsCount)
987 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::Int32())
988 61806 : DECLARE_DESCRIPTOR(ArgumentsAdaptorDescriptor, CallInterfaceDescriptor)
989 : };
990 :
991 122016 : class CppBuiltinAdaptorDescriptor : public CallInterfaceDescriptor {
992 : public:
993 : DEFINE_JS_PARAMETERS(kCFunction)
994 122016 : DEFINE_JS_PARAMETER_TYPES(MachineType::Pointer())
995 122016 : DECLARE_JS_COMPATIBLE_DESCRIPTOR(CppBuiltinAdaptorDescriptor,
996 : CallInterfaceDescriptor, 1)
997 : };
998 :
999 122128 : class CEntry1ArgvOnStackDescriptor : public CallInterfaceDescriptor {
1000 : public:
1001 : DEFINE_PARAMETERS(kArity, // register argument
1002 : kCFunction, // register argument
1003 : kPadding, // stack argument 1 (just padding)
1004 : kArgcSmi, // stack argument 2
1005 : kTargetCopy, // stack argument 3
1006 : kNewTargetCopy) // stack argument 4
1007 122016 : DEFINE_PARAMETER_TYPES(MachineType::Int32(), // kArity
1008 : MachineType::Pointer(), // kCFunction
1009 : MachineType::AnyTagged(), // kPadding
1010 : MachineType::AnyTagged(), // kArgcSmi
1011 : MachineType::AnyTagged(), // kTargetCopy
1012 : MachineType::AnyTagged()) // kNewTargetCopy
1013 61120 : DECLARE_DESCRIPTOR(CEntry1ArgvOnStackDescriptor, CallInterfaceDescriptor)
1014 : };
1015 :
1016 122016 : class ApiCallbackDescriptor : public CallInterfaceDescriptor {
1017 : public:
1018 : DEFINE_PARAMETERS(kApiFunctionAddress, kActualArgumentsCount, kCallData,
1019 : kHolder)
1020 : // receiver is implicit stack argument 1
1021 : // argv are implicit stack arguments [2, 2 + kArgc[
1022 122016 : DEFINE_PARAMETER_TYPES(MachineType::Pointer(), // kApiFunctionAddress
1023 : MachineType::IntPtr(), // kActualArgumentsCount
1024 : MachineType::AnyTagged(), // kCallData
1025 : MachineType::AnyTagged()) // kHolder
1026 61008 : DECLARE_DESCRIPTOR(ApiCallbackDescriptor, CallInterfaceDescriptor)
1027 : };
1028 :
1029 122016 : class ApiGetterDescriptor : public CallInterfaceDescriptor {
1030 : public:
1031 : DEFINE_PARAMETERS(kReceiver, kHolder, kCallback)
1032 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kReceiver
1033 : MachineType::AnyTagged(), // kHolder
1034 : MachineType::AnyTagged()) // kCallback
1035 61008 : DECLARE_DESCRIPTOR(ApiGetterDescriptor, CallInterfaceDescriptor)
1036 :
1037 : static const Register ReceiverRegister();
1038 : static const Register HolderRegister();
1039 : static const Register CallbackRegister();
1040 : };
1041 :
1042 : // TODO(turbofan): We should probably rename this to GrowFastElementsDescriptor.
1043 122016 : class GrowArrayElementsDescriptor : public CallInterfaceDescriptor {
1044 : public:
1045 : DEFINE_PARAMETERS(kObject, kKey)
1046 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kObject
1047 : MachineType::AnyTagged()) // kKey
1048 61008 : DECLARE_DESCRIPTOR(GrowArrayElementsDescriptor, CallInterfaceDescriptor)
1049 :
1050 : static const Register ObjectRegister();
1051 : static const Register KeyRegister();
1052 : };
1053 :
1054 122016 : class NewArgumentsElementsDescriptor final : public CallInterfaceDescriptor {
1055 : public:
1056 : DEFINE_PARAMETERS(kFrame, kLength, kMappedCount)
1057 122016 : DEFINE_PARAMETER_TYPES(MachineType::Pointer(), // kFrame
1058 : MachineType::TaggedSigned(), // kLength
1059 : MachineType::TaggedSigned()) // kMappedCount
1060 61008 : DECLARE_DESCRIPTOR(NewArgumentsElementsDescriptor, CallInterfaceDescriptor)
1061 : };
1062 :
1063 220230 : class V8_EXPORT_PRIVATE InterpreterDispatchDescriptor
1064 : : public CallInterfaceDescriptor {
1065 : public:
1066 : DEFINE_PARAMETERS(kAccumulator, kBytecodeOffset, kBytecodeArray,
1067 : kDispatchTable)
1068 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kAccumulator
1069 : MachineType::IntPtr(), // kBytecodeOffset
1070 : MachineType::AnyTagged(), // kBytecodeArray
1071 : MachineType::IntPtr()) // kDispatchTable
1072 132678 : DECLARE_DESCRIPTOR(InterpreterDispatchDescriptor, CallInterfaceDescriptor)
1073 : };
1074 :
1075 122016 : class InterpreterPushArgsThenCallDescriptor : public CallInterfaceDescriptor {
1076 : public:
1077 : DEFINE_PARAMETERS(kNumberOfArguments, kFirstArgument, kFunction)
1078 122016 : DEFINE_PARAMETER_TYPES(MachineType::Int32(), // kNumberOfArguments
1079 : MachineType::Pointer(), // kFirstArgument
1080 : MachineType::AnyTagged()) // kFunction
1081 61008 : DECLARE_DESCRIPTOR(InterpreterPushArgsThenCallDescriptor,
1082 : CallInterfaceDescriptor)
1083 : };
1084 :
1085 122016 : class InterpreterPushArgsThenConstructDescriptor
1086 : : public CallInterfaceDescriptor {
1087 : public:
1088 : DEFINE_PARAMETERS(kNumberOfArguments, kFirstArgument, kConstructor,
1089 : kNewTarget, kFeedbackElement)
1090 122016 : DEFINE_PARAMETER_TYPES(MachineType::Int32(), // kNumberOfArguments
1091 : MachineType::Pointer(), // kFirstArgument
1092 : MachineType::AnyTagged(), // kConstructor
1093 : MachineType::AnyTagged(), // kNewTarget
1094 : MachineType::AnyTagged()) // kFeedbackElement
1095 61008 : DECLARE_DESCRIPTOR(InterpreterPushArgsThenConstructDescriptor,
1096 : CallInterfaceDescriptor)
1097 :
1098 : #if V8_TARGET_ARCH_IA32
1099 : static const bool kPassLastArgsOnStack = true;
1100 : #else
1101 : static const bool kPassLastArgsOnStack = false;
1102 : #endif
1103 :
1104 : // Pass constructor, new target and feedback element through the stack.
1105 : static const int kStackArgumentsCount = kPassLastArgsOnStack ? 3 : 0;
1106 : };
1107 :
1108 122016 : class InterpreterCEntry1Descriptor : public CallInterfaceDescriptor {
1109 : public:
1110 : DEFINE_RESULT_AND_PARAMETERS(1, kNumberOfArguments, kFirstArgument,
1111 : kFunctionEntry)
1112 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::AnyTagged(), // result 1
1113 : MachineType::Int32(), // kNumberOfArguments
1114 : MachineType::Pointer(), // kFirstArgument
1115 : MachineType::Pointer()) // kFunctionEntry
1116 61008 : DECLARE_DESCRIPTOR(InterpreterCEntry1Descriptor, CallInterfaceDescriptor)
1117 : };
1118 :
1119 122016 : class InterpreterCEntry2Descriptor : public CallInterfaceDescriptor {
1120 : public:
1121 : DEFINE_RESULT_AND_PARAMETERS(2, kNumberOfArguments, kFirstArgument,
1122 : kFunctionEntry)
1123 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::AnyTagged(), // result 1
1124 : MachineType::AnyTagged(), // result 2
1125 : MachineType::Int32(), // kNumberOfArguments
1126 : MachineType::Pointer(), // kFirstArgument
1127 : MachineType::Pointer()) // kFunctionEntry
1128 61008 : DECLARE_DESCRIPTOR(InterpreterCEntry2Descriptor, CallInterfaceDescriptor)
1129 : };
1130 :
1131 122016 : class ResumeGeneratorDescriptor final : public CallInterfaceDescriptor {
1132 : public:
1133 : DEFINE_PARAMETERS(kValue, kGenerator)
1134 122016 : DEFINE_PARAMETER_TYPES(MachineType::AnyTagged(), // kValue
1135 : MachineType::AnyTagged()) // kGenerator
1136 61008 : DECLARE_DESCRIPTOR(ResumeGeneratorDescriptor, CallInterfaceDescriptor)
1137 : };
1138 :
1139 122016 : class FrameDropperTrampolineDescriptor final : public CallInterfaceDescriptor {
1140 : public:
1141 : DEFINE_PARAMETERS(kRestartFp)
1142 122016 : DEFINE_PARAMETER_TYPES(MachineType::Pointer())
1143 61008 : DECLARE_DESCRIPTOR(FrameDropperTrampolineDescriptor, CallInterfaceDescriptor)
1144 : };
1145 :
1146 122016 : class RunMicrotasksEntryDescriptor final : public CallInterfaceDescriptor {
1147 : public:
1148 : DEFINE_PARAMETERS_ENTRY(kRootRegisterValue, kMicrotaskQueue)
1149 122016 : DEFINE_PARAMETER_TYPES(MachineType::Pointer(), // kRootRegisterValue
1150 : MachineType::Pointer()) // kMicrotaskQueue
1151 61008 : DECLARE_DESCRIPTOR(RunMicrotasksEntryDescriptor, CallInterfaceDescriptor)
1152 : };
1153 :
1154 122016 : class RunMicrotasksDescriptor final : public CallInterfaceDescriptor {
1155 : public:
1156 : DEFINE_PARAMETERS(kMicrotaskQueue)
1157 122016 : DEFINE_PARAMETER_TYPES(MachineType::Pointer())
1158 61008 : DECLARE_DESCRIPTOR(RunMicrotasksDescriptor, CallInterfaceDescriptor)
1159 :
1160 : static Register MicrotaskQueueRegister();
1161 : };
1162 :
1163 123321 : class WasmMemoryGrowDescriptor final : public CallInterfaceDescriptor {
1164 : public:
1165 : DEFINE_PARAMETERS_NO_CONTEXT(kNumPages)
1166 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::Int32(), // result 1
1167 : MachineType::Int32()) // kNumPages
1168 62314 : DECLARE_DESCRIPTOR(WasmMemoryGrowDescriptor, CallInterfaceDescriptor)
1169 : };
1170 :
1171 122060 : class WasmTableGetDescriptor final : public CallInterfaceDescriptor {
1172 : public:
1173 : DEFINE_PARAMETERS_NO_CONTEXT(kTableIndex, kEntryIndex)
1174 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::AnyTagged(), // result 1
1175 : MachineType::TaggedSigned(), // kTableIndex
1176 : MachineType::Int32()) // kEntryIndex
1177 61052 : DECLARE_DESCRIPTOR(WasmTableGetDescriptor, CallInterfaceDescriptor)
1178 : };
1179 :
1180 122038 : class WasmTableSetDescriptor final : public CallInterfaceDescriptor {
1181 : public:
1182 : DEFINE_PARAMETERS_NO_CONTEXT(kTableIndex, kEntryIndex, kValue)
1183 122016 : DEFINE_PARAMETER_TYPES(MachineType::TaggedSigned(), // kTableIndex
1184 : MachineType::Int32(), // kEntryIndex
1185 : MachineType::AnyTagged()) // kValue
1186 61030 : DECLARE_DESCRIPTOR(WasmTableSetDescriptor, CallInterfaceDescriptor)
1187 : };
1188 :
1189 122974 : class WasmThrowDescriptor final : public CallInterfaceDescriptor {
1190 : public:
1191 : DEFINE_PARAMETERS_NO_CONTEXT(kException)
1192 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::AnyTagged(), // result 1
1193 : MachineType::AnyTagged()) // kException
1194 61966 : DECLARE_DESCRIPTOR(WasmThrowDescriptor, CallInterfaceDescriptor)
1195 : };
1196 :
1197 122104 : class I64ToBigIntDescriptor final : public CallInterfaceDescriptor {
1198 : public:
1199 : DEFINE_PARAMETERS_NO_CONTEXT(kArgument)
1200 122016 : DEFINE_PARAMETER_TYPES(MachineType::Int64()) // kArgument
1201 61096 : DECLARE_DESCRIPTOR(I64ToBigIntDescriptor, CallInterfaceDescriptor)
1202 : };
1203 :
1204 122088 : class BigIntToI64Descriptor final : public CallInterfaceDescriptor {
1205 : public:
1206 : DEFINE_PARAMETERS(kArgument)
1207 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::Int64(), // result 1
1208 : MachineType::AnyTagged()) // kArgument
1209 61080 : DECLARE_DESCRIPTOR(BigIntToI64Descriptor, CallInterfaceDescriptor)
1210 : };
1211 :
1212 122586 : class WasmAtomicNotifyDescriptor final : public CallInterfaceDescriptor {
1213 : public:
1214 : DEFINE_PARAMETERS_NO_CONTEXT(kAddress, kCount)
1215 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::Uint32(), // result 1
1216 : MachineType::Uint32(), // kAddress
1217 : MachineType::Uint32()) // kCount
1218 61294 : DECLARE_DESCRIPTOR(WasmAtomicNotifyDescriptor, CallInterfaceDescriptor)
1219 : };
1220 :
1221 122856 : class WasmI32AtomicWaitDescriptor final : public CallInterfaceDescriptor {
1222 : public:
1223 : DEFINE_PARAMETERS_NO_CONTEXT(kAddress, kExpectedValue, kTimeout)
1224 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::Uint32(), // result 1
1225 : MachineType::Uint32(), // kAddress
1226 : MachineType::Int32(), // kExpectedValue
1227 : MachineType::Float64()) // kTimeout
1228 61428 : DECLARE_DESCRIPTOR(WasmI32AtomicWaitDescriptor, CallInterfaceDescriptor)
1229 : };
1230 :
1231 123034 : class WasmI64AtomicWaitDescriptor final : public CallInterfaceDescriptor {
1232 : public:
1233 : DEFINE_PARAMETERS_NO_CONTEXT(kAddress, kExpectedValueHigh, kExpectedValueLow,
1234 : kTimeout)
1235 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(
1236 : MachineType::Uint32(), // result 1
1237 : MachineType::Uint32(), // kAddress
1238 : MachineType::Uint32(), // kExpectedValueHigh
1239 : MachineType::Uint32(), // kExpectedValueLow
1240 : MachineType::Float64()) // kTimeout
1241 61518 : DECLARE_DESCRIPTOR(WasmI64AtomicWaitDescriptor, CallInterfaceDescriptor)
1242 : };
1243 :
1244 122016 : class CloneObjectWithVectorDescriptor final : public CallInterfaceDescriptor {
1245 : public:
1246 : DEFINE_PARAMETERS(kSource, kFlags, kSlot, kVector)
1247 122016 : DEFINE_RESULT_AND_PARAMETER_TYPES(MachineType::TaggedPointer(), // result 1
1248 : MachineType::AnyTagged(), // kSource
1249 : MachineType::TaggedSigned(), // kFlags
1250 : MachineType::TaggedSigned(), // kSlot
1251 : MachineType::AnyTagged()) // kVector
1252 61008 : DECLARE_DESCRIPTOR(CloneObjectWithVectorDescriptor, CallInterfaceDescriptor)
1253 : };
1254 :
1255 : #define DEFINE_TFS_BUILTIN_DESCRIPTOR(Name, ...) \
1256 : class Name##Descriptor : public CallInterfaceDescriptor { \
1257 : public: \
1258 : DEFINE_PARAMETERS(__VA_ARGS__) \
1259 : DECLARE_DEFAULT_DESCRIPTOR(Name##Descriptor, CallInterfaceDescriptor) \
1260 : };
1261 63631344 : BUILTIN_LIST_TFS(DEFINE_TFS_BUILTIN_DESCRIPTOR)
1262 : #undef DEFINE_TFS_BUILTIN_DESCRIPTOR
1263 :
1264 : #undef DECLARE_DEFAULT_DESCRIPTOR
1265 : #undef DECLARE_DESCRIPTOR_WITH_BASE
1266 : #undef DECLARE_DESCRIPTOR
1267 : #undef DECLARE_JS_COMPATIBLE_DESCRIPTOR
1268 : #undef DEFINE_RESULT_AND_PARAMETERS
1269 : #undef DEFINE_RESULT_AND_PARAMETERS_NO_CONTEXT
1270 : #undef DEFINE_PARAMETERS
1271 : #undef DEFINE_PARAMETERS_NO_CONTEXT
1272 : #undef DEFINE_RESULT_AND_PARAMETER_TYPES
1273 : #undef DEFINE_PARAMETER_TYPES
1274 : #undef DEFINE_JS_PARAMETERS
1275 : #undef DEFINE_JS_PARAMETER_TYPES
1276 :
1277 : // We define the association between CallDescriptors::Key and the specialized
1278 : // descriptor here to reduce boilerplate and mistakes.
1279 : #define DEF_KEY(name, ...) \
1280 : CallDescriptors::Key name##Descriptor::key() { return CallDescriptors::name; }
1281 : INTERFACE_DESCRIPTOR_LIST(DEF_KEY)
1282 : #undef DEF_KEY
1283 : } // namespace internal
1284 : } // namespace v8
1285 :
1286 : #endif // V8_INTERFACE_DESCRIPTORS_H_
|