v8
V8 is Google’s open source high-performance JavaScript and WebAssembly engine, written in C++.
Loading...
Searching...
No Matches
interpreter-intrinsics-generator.cc
Go to the documentation of this file.
1// Copyright 2017 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
6
13
14namespace v8 {
15namespace internal {
16namespace interpreter {
17
19
21 public:
23 : isolate_(assembler->isolate()),
24 zone_(assembler->zone()),
25 assembler_(assembler) {}
28
30 TNode<Uint32T> function_id, TNode<Context> context,
32
33 private:
36 Builtin name, int arg_count);
37 void AbortIfArgCountMismatch(int expected, TNode<Word32T> actual);
38
39#define DECLARE_INTRINSIC_HELPER(name, lower_case, count) \
40 TNode<Object> name(const InterpreterAssembler::RegListNodePair& args, \
41 TNode<Context> context, int arg_count);
43#undef DECLARE_INTRINSIC_HELPER
44
45 Isolate* isolate() { return isolate_; }
46 Zone* zone() { return zone_; }
47 Factory* factory() { return isolate()->factory(); }
48
52};
53
55 InterpreterAssembler* assembler, TNode<Uint32T> function_id,
57 IntrinsicsGenerator generator(assembler);
58 return generator.InvokeIntrinsic(function_id, context, args);
59}
60
61#define __ assembler_->
62
64 TNode<Uint32T> function_id, TNode<Context> context,
68
69#define MAKE_LABEL(name, lower_case, count) \
70 InterpreterAssembler::Label lower_case(assembler_);
72#undef MAKE_LABEL
73
74#define LABEL_POINTER(name, lower_case, count) &lower_case,
76#undef LABEL_POINTER
77
78#define CASE(name, lower_case, count) \
79 static_cast<int32_t>(IntrinsicsHelper::IntrinsicId::k##name),
80 int32_t cases[] = {INTRINSICS_LIST(CASE)};
81#undef CASE
82
83 __ Switch(function_id, &abort, cases, labels, arraysize(cases));
84#define HANDLE_CASE(name, lower_case, expected_arg_count) \
85 __ BIND(&lower_case); \
86 { \
87 if (v8_flags.debug_code && expected_arg_count >= 0) { \
88 AbortIfArgCountMismatch(expected_arg_count, args.reg_count()); \
89 } \
90 TNode<Object> value = name(args, context, expected_arg_count); \
91 if (value) { \
92 result = value; \
93 __ Goto(&end); \
94 } \
95 }
97#undef HANDLE_CASE
98
99 __ BIND(&abort);
100 {
101 __ Abort(AbortReason::kUnexpectedFunctionIDForInvokeIntrinsic);
102 result = __ UndefinedConstant();
103 __ Goto(&end);
104 }
105
106 __ BIND(&end);
107 return result.value();
108}
109
112 Builtin builtin, int arg_count) {
113 switch (arg_count) {
114 case 1:
115 return __ CallBuiltin(builtin, context,
116 __ LoadRegisterFromRegisterList(args, 0));
117 case 2:
118 return __ CallBuiltin(builtin, context,
119 __ LoadRegisterFromRegisterList(args, 0),
120 __ LoadRegisterFromRegisterList(args, 1));
121 case 3:
122 return __ CallBuiltin(builtin, context,
123 __ LoadRegisterFromRegisterList(args, 0),
124 __ LoadRegisterFromRegisterList(args, 1),
125 __ LoadRegisterFromRegisterList(args, 2));
126 default:
127 UNREACHABLE();
128 }
129}
130
131TNode<Object> IntrinsicsGenerator::CopyDataProperties(
133 int arg_count) {
134 return IntrinsicAsBuiltinCall(args, context, Builtin::kCopyDataProperties,
135 arg_count);
136}
137
139IntrinsicsGenerator::CopyDataPropertiesWithExcludedPropertiesOnStack(
140 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
141 int arg_count) {
142 TNode<IntPtrT> offset = __ TimesSystemPointerSize(__ IntPtrConstant(1));
143 auto base = __ Signed(__ IntPtrSub(args.base_reg_location(), offset));
144 TNode<IntPtrT> excluded_property_count = __ IntPtrSub(
145 __ ChangeInt32ToIntPtr(args.reg_count()), __ IntPtrConstant(1));
146 return __ CallBuiltin(
147 Builtin::kCopyDataPropertiesWithExcludedPropertiesOnStack, context,
148 __ LoadRegisterFromRegisterList(args, 0), excluded_property_count, base);
149}
150
151TNode<Object> IntrinsicsGenerator::CreateIterResultObject(
152 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
153 int arg_count) {
154 return IntrinsicAsBuiltinCall(args, context, Builtin::kCreateIterResultObject,
155 arg_count);
156}
157
158TNode<Object> IntrinsicsGenerator::CreateAsyncFromSyncIterator(
159 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
160 int arg_count) {
161 TNode<JSAny> sync_iterator =
162 __ CAST(__ LoadRegisterFromRegisterList(args, 0));
163 return __ CreateAsyncFromSyncIterator(context, sync_iterator);
164}
165
166TNode<Object> IntrinsicsGenerator::CreateJSGeneratorObject(
167 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
168 int arg_count) {
169 return IntrinsicAsBuiltinCall(args, context, Builtin::kCreateGeneratorObject,
170 arg_count);
171}
172
173TNode<Object> IntrinsicsGenerator::GeneratorGetResumeMode(
174 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
175 int arg_count) {
176 TNode<JSGeneratorObject> generator =
177 __ CAST(__ LoadRegisterFromRegisterList(args, 0));
178 const TNode<Object> value =
179 __ LoadObjectField(generator, JSGeneratorObject::kResumeModeOffset);
180
181 return value;
182}
183
184TNode<Object> IntrinsicsGenerator::GeneratorClose(
185 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
186 int arg_count) {
187 TNode<JSGeneratorObject> generator =
188 __ CAST(__ LoadRegisterFromRegisterList(args, 0));
189 __ StoreObjectFieldNoWriteBarrier(
190 generator, JSGeneratorObject::kContinuationOffset,
192 return __ UndefinedConstant();
193}
194
195TNode<Object> IntrinsicsGenerator::GetImportMetaObject(
196 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
197 int arg_count) {
198 return __ GetImportMetaObject(context);
199}
200
201TNode<Object> IntrinsicsGenerator::AsyncFunctionAwait(
202 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
203 int arg_count) {
204 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncFunctionAwait,
205 arg_count);
206}
207
208TNode<Object> IntrinsicsGenerator::AsyncFunctionEnter(
209 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
210 int arg_count) {
211 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncFunctionEnter,
212 arg_count);
213}
214
215TNode<Object> IntrinsicsGenerator::AsyncFunctionReject(
216 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
217 int arg_count) {
218 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncFunctionReject,
219 arg_count);
220}
221
222TNode<Object> IntrinsicsGenerator::AsyncFunctionResolve(
223 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
224 int arg_count) {
225 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncFunctionResolve,
226 arg_count);
227}
228
229TNode<Object> IntrinsicsGenerator::AsyncGeneratorAwait(
230 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
231 int arg_count) {
232 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncGeneratorAwait,
233 arg_count);
234}
235
236TNode<Object> IntrinsicsGenerator::AsyncGeneratorReject(
237 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
238 int arg_count) {
239 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncGeneratorReject,
240 arg_count);
241}
242
243TNode<Object> IntrinsicsGenerator::AsyncGeneratorResolve(
244 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
245 int arg_count) {
246 return IntrinsicAsBuiltinCall(args, context, Builtin::kAsyncGeneratorResolve,
247 arg_count);
248}
249
250TNode<Object> IntrinsicsGenerator::AsyncGeneratorYieldWithAwait(
251 const InterpreterAssembler::RegListNodePair& args, TNode<Context> context,
252 int arg_count) {
254 args, context, Builtin::kAsyncGeneratorYieldWithAwait, arg_count);
255}
256
258 TNode<Word32T> actual) {
260 TNode<BoolT> comparison = __ Word32Equal(actual, __ Int32Constant(expected));
261 __ GotoIf(comparison, &match);
262 __ Abort(AbortReason::kWrongArgumentCountForInvokeIntrinsic);
263 __ Goto(&match);
264 __ BIND(&match);
265}
266
267#undef __
268
270
271} // namespace interpreter
272} // namespace internal
273} // namespace v8
#define HANDLE_CASE(op, opcode, name, result)
#define BIND(label)
v8::internal::Factory * factory()
Definition isolate.h:1527
static const int kGeneratorClosed
TNode< Object > InvokeIntrinsic(TNode< Uint32T > function_id, TNode< Context > context, const InterpreterAssembler::RegListNodePair &args)
IntrinsicsGenerator & operator=(const IntrinsicsGenerator &)=delete
IntrinsicsGenerator(const IntrinsicsGenerator &)=delete
TNode< Object > IntrinsicAsBuiltinCall(const InterpreterAssembler::RegListNodePair &args, TNode< Context > context, Builtin name, int arg_count)
void AbortIfArgCountMismatch(int expected, TNode< Word32T > actual)
#define CAST(x)
int end
base::Vector< const DirectHandle< Object > > args
Definition execution.cc:74
int32_t offset
#define LABEL_POINTER(name, lower_case)
#define MAKE_LABEL(name, lower_case)
#define DECLARE_INTRINSIC_HELPER(name, lower_case, count)
#define INTRINSICS_LIST(V)
ZoneVector< RpoNumber > & result
TNode< Oddball > UndefinedConstant(JSGraph *jsgraph)
TNode< Object > GenerateInvokeIntrinsic(InterpreterAssembler *assembler, TNode< Uint32T > function_id, TNode< Context > context, const InterpreterAssembler::RegListNodePair &args)
return value
Definition map-inl.h:893
#define arraysize(array)
Definition macros.h:67