1 /**
2 * Copyright (c) 2025 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <cstddef>
17 #include <iostream>
18 #include <limits>
19 #include <ostream>
20 #include <optional>
21 #include <string_view>
22 #include "ani.h"
23 #include "macros.h"
24 #include "libpandabase/utils/logger.h"
25 #include "runtime/coroutines/coroutine_scopes.h"
26 #include "plugins/ets/runtime/ani/ani_checkers.h"
27 #include "plugins/ets/runtime/ani/ani_interaction_api.h"
28 #include "plugins/ets/runtime/ani/ani_mangle.h"
29 #include "plugins/ets/runtime/ani/ani_type_info.h"
30 #include "plugins/ets/runtime/ani/scoped_objects_fix.h"
31 #include "plugins/ets/runtime/types/ets_module.h"
32 #include "plugins/ets/runtime/types/ets_namespace.h"
33 #include "plugins/ets/runtime/types/ets_box_primitive-inl.h"
34 #include "plugins/ets/runtime/ets_class_linker_extension.h"
35 #include "plugins/ets/runtime/ets_napi_env.h"
36 #include "plugins/ets/runtime/ets_stubs-inl.h"
37 #include "plugins/ets/runtime/types/ets_object.h"
38 #include "plugins/ets/runtime/types/ets_array.h"
39 #include "plugins/ets/runtime/types/ets_escompat_array.h"
40 #include "plugins/ets/runtime/ets_handle_scope.h"
41
42 // NOLINTBEGIN(cppcoreguidelines-macro-usage)
43
44 // CC-OFFNXT(G.PRE.02) should be with define
45 #define CHECK_PTR_ARG(arg) ANI_CHECK_RETURN_IF_EQ(arg, nullptr, ANI_INVALID_ARGS)
46
47 // CC-OFFNXT(G.PRE.02) should be with define
48 #define CHECK_ENV(env) \
49 do { \
50 ANI_CHECK_RETURN_IF_EQ(env, nullptr, ANI_INVALID_ARGS); \
51 bool hasPendingException = ::ark::ets::PandaEnv::FromAniEnv(env)->HasPendingException(); \
52 ANI_CHECK_RETURN_IF_EQ(hasPendingException, true, ANI_PENDING_ERROR); \
53 } while (false)
54
55 // NOLINTEND(cppcoreguidelines-macro-usage)
56
57 namespace ark::ets::ani {
58
59 template <typename T>
60 using ArgVector = PandaSmallVector<T>;
61
62 using TypeId = panda_file::Type::TypeId;
63
IsUndefined(ani_ref ref)64 static inline bool IsUndefined(ani_ref ref)
65 {
66 return ManagedCodeAccessor::IsUndefined(ref);
67 }
68
ToAniField(EtsField * field)69 static inline ani_field ToAniField(EtsField *field)
70 {
71 ASSERT(field != nullptr);
72 ASSERT(!field->IsStatic());
73 return reinterpret_cast<ani_field>(field);
74 }
75
ToInternalField(ani_field field)76 static inline EtsField *ToInternalField(ani_field field)
77 {
78 auto *f = reinterpret_cast<EtsField *>(field);
79 ASSERT(f != nullptr);
80 ASSERT(!f->IsStatic());
81 return f;
82 }
83
ToAniStaticField(EtsField * field)84 static inline ani_static_field ToAniStaticField(EtsField *field)
85 {
86 ASSERT(field != nullptr);
87 ASSERT(field->IsStatic());
88 return reinterpret_cast<ani_static_field>(field);
89 }
90
ToInternalField(ani_static_field field)91 [[maybe_unused]] static inline EtsField *ToInternalField(ani_static_field field)
92 {
93 auto *f = reinterpret_cast<EtsField *>(field);
94 ASSERT(f->IsStatic());
95 return f;
96 }
97
ToAniVariable(EtsVariable * variable)98 static inline ani_variable ToAniVariable(EtsVariable *variable)
99 {
100 return reinterpret_cast<ani_variable>(variable);
101 }
102
ToInternalVariable(ani_variable variable)103 static inline EtsVariable *ToInternalVariable(ani_variable variable)
104 {
105 return reinterpret_cast<EtsVariable *>(variable);
106 }
107
ToInternalMethod(ani_method method)108 static inline EtsMethod *ToInternalMethod(ani_method method)
109 {
110 auto *m = reinterpret_cast<EtsMethod *>(method);
111 ASSERT(m != nullptr);
112 ASSERT(!m->IsStatic());
113 ASSERT(!m->IsFunction());
114 return m;
115 }
116
ToAniMethod(EtsMethod * method)117 static inline ani_method ToAniMethod(EtsMethod *method)
118 {
119 ASSERT(method != nullptr);
120 ASSERT(!method->IsStatic());
121 ASSERT(!method->IsFunction());
122 return reinterpret_cast<ani_method>(method);
123 }
124
ToInternalMethod(ani_static_method method)125 static inline EtsMethod *ToInternalMethod(ani_static_method method)
126 {
127 auto *m = reinterpret_cast<EtsMethod *>(method);
128 ASSERT(m != nullptr);
129 ASSERT(m->IsStatic());
130 ASSERT(!m->IsFunction());
131 return m;
132 }
133
ToAniStaticMethod(EtsMethod * method)134 static inline ani_static_method ToAniStaticMethod(EtsMethod *method)
135 {
136 ASSERT(method != nullptr);
137 ASSERT(method->IsStatic());
138 ASSERT(!method->IsFunction());
139 return reinterpret_cast<ani_static_method>(method);
140 }
141
ToInternalFunction(ani_function fn)142 static inline EtsMethod *ToInternalFunction(ani_function fn)
143 {
144 auto *m = reinterpret_cast<EtsMethod *>(fn);
145 ASSERT(m != nullptr);
146 ASSERT(m->IsStatic());
147 ASSERT(m->IsFunction());
148 return m;
149 }
150
ToAniFunction(EtsMethod * method)151 static inline ani_function ToAniFunction(EtsMethod *method)
152 {
153 ASSERT(method != nullptr);
154 ASSERT(method->IsStatic());
155 ASSERT(method->IsFunction());
156 return reinterpret_cast<ani_function>(method);
157 }
158
CheckStaticMethodReturnType(ani_static_method method,EtsType type)159 static void CheckStaticMethodReturnType(ani_static_method method, EtsType type)
160 {
161 EtsMethod *m = ToInternalMethod(method);
162 if (UNLIKELY(m->GetReturnValueType() != type)) {
163 LOG(FATAL, ANI) << "Return type mismatch";
164 }
165 }
166
CheckMethodReturnType(ani_method method,EtsType type)167 static void CheckMethodReturnType(ani_method method, EtsType type)
168 {
169 EtsMethod *m = ToInternalMethod(method);
170 if (UNLIKELY(m->GetReturnValueType() != type)) {
171 LOG(FATAL, ANI) << "Return type mismatch";
172 }
173 }
174
CheckFunctionReturnType(ani_function fn,EtsType type)175 static void CheckFunctionReturnType(ani_function fn, EtsType type)
176 {
177 EtsMethod *m = ToInternalFunction(fn);
178 if (UNLIKELY(m->GetReturnValueType() != type)) {
179 LOG(FATAL, ANI) << "Return type mismatch";
180 }
181 }
182
GetClassLinkerContext(EtsCoroutine * coroutine)183 static ClassLinkerContext *GetClassLinkerContext(EtsCoroutine *coroutine)
184 {
185 auto stack = StackWalker::Create(coroutine);
186 if (!stack.HasFrame()) {
187 return nullptr;
188 }
189
190 auto *method = EtsMethod::FromRuntimeMethod(stack.GetMethod());
191 if (method != nullptr) {
192 return method->GetClass()->GetLoadContext();
193 }
194 return nullptr;
195 }
196
InitializeClass(ScopedManagedCodeFix & s,EtsClass * klass)197 static ani_status InitializeClass(ScopedManagedCodeFix &s, EtsClass *klass)
198 {
199 ASSERT(klass != nullptr);
200 if (klass->IsInitialized()) {
201 return ANI_OK;
202 }
203
204 // Initialize class
205 EtsCoroutine *corutine = s.GetCoroutine();
206 EtsClassLinker *classLinker = corutine->GetPandaVM()->GetClassLinker();
207 bool isInitialized = classLinker->InitializeClass(corutine, klass);
208 if (!isInitialized) {
209 LOG(ERROR, ANI) << "Cannot initialize class: " << klass->GetDescriptor();
210 if (corutine->HasPendingException()) {
211 return ANI_PENDING_ERROR;
212 }
213 return ANI_ERROR;
214 }
215 return ANI_OK;
216 }
217
ConstructValueFromFloatingPoint(float val)218 static Value ConstructValueFromFloatingPoint(float val)
219 {
220 return Value(bit_cast<int32_t>(val));
221 }
222
ConstructValueFromFloatingPoint(double val)223 static Value ConstructValueFromFloatingPoint(double val)
224 {
225 return Value(bit_cast<int64_t>(val));
226 }
227
GetArgValues(ScopedManagedCodeFix & s,EtsMethod * method,va_list args,ani_object object)228 static ArgVector<Value> GetArgValues(ScopedManagedCodeFix &s, EtsMethod *method, va_list args, ani_object object)
229 {
230 ASSERT(method != nullptr);
231 ArgVector<Value> parsedArgs;
232 parsedArgs.reserve(method->GetNumArgs());
233 if (object != nullptr) {
234 parsedArgs.emplace_back(s.ToInternalType(object)->GetCoreType());
235 }
236
237 panda_file::ShortyIterator it(method->GetPandaMethod()->GetShorty());
238 panda_file::ShortyIterator end;
239 ++it; // skip the return value
240 for (; it != end; ++it) {
241 panda_file::Type type = *it;
242 // NOLINTBEGIN(cppcoreguidelines-pro-type-vararg)
243 switch (type.GetId()) {
244 case TypeId::U1:
245 case TypeId::U16:
246 parsedArgs.emplace_back(va_arg(args, uint32_t));
247 break;
248 case TypeId::I8:
249 case TypeId::I16:
250 case TypeId::I32:
251 parsedArgs.emplace_back(va_arg(args, int32_t));
252 break;
253 case TypeId::I64:
254 parsedArgs.emplace_back(va_arg(args, int64_t));
255 break;
256 case TypeId::F32:
257 parsedArgs.push_back(ConstructValueFromFloatingPoint(static_cast<float>(va_arg(args, double))));
258 break;
259 case TypeId::F64:
260 parsedArgs.push_back(ConstructValueFromFloatingPoint(va_arg(args, double)));
261 break;
262 case TypeId::REFERENCE: {
263 auto *param = s.ToInternalType(va_arg(args, ani_ref));
264 parsedArgs.emplace_back(param != nullptr ? param->GetCoreType() : nullptr);
265 break;
266 }
267 default:
268 LOG(FATAL, ANI) << "Unexpected argument type";
269 break;
270 }
271 // NOLINTEND(cppcoreguidelines-pro-type-vararg)
272 }
273 return parsedArgs;
274 }
275
276 // CC-OFFNXT(huge_method[C++], G.FUN.01-CPP) solid logic
GetArgValues(ScopedManagedCodeFix & s,EtsMethod * method,const ani_value * args,ani_object object)277 static ArgVector<Value> GetArgValues(ScopedManagedCodeFix &s, EtsMethod *method, const ani_value *args,
278 ani_object object)
279 {
280 ASSERT(method != nullptr);
281 ASSERT(args != nullptr);
282 ArgVector<Value> parsedArgs;
283 parsedArgs.reserve(method->GetNumArgs());
284 if (object != nullptr) {
285 parsedArgs.emplace_back(s.ToInternalType(object)->GetCoreType());
286 }
287
288 panda_file::ShortyIterator it(method->GetPandaMethod()->GetShorty());
289 panda_file::ShortyIterator end;
290 ++it; // skip the return value
291 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
292 for (const auto *arg = args; it != end; ++arg, ++it) {
293 panda_file::Type type = *it;
294 switch (type.GetId()) {
295 case TypeId::U1:
296 parsedArgs.emplace_back(arg->z);
297 break;
298 case TypeId::U16:
299 parsedArgs.emplace_back(arg->c);
300 break;
301 case TypeId::I8:
302 parsedArgs.emplace_back(arg->b);
303 break;
304 case TypeId::I16:
305 parsedArgs.emplace_back(arg->s);
306 break;
307 case TypeId::I32:
308 parsedArgs.emplace_back(arg->i);
309 break;
310 case TypeId::I64:
311 parsedArgs.emplace_back(arg->l);
312 break;
313 case TypeId::F32:
314 parsedArgs.push_back(ConstructValueFromFloatingPoint(arg->f));
315 break;
316 case TypeId::F64:
317 parsedArgs.push_back(ConstructValueFromFloatingPoint(arg->d));
318 break;
319 case TypeId::REFERENCE: {
320 auto *param = s.ToInternalType(arg->r);
321 parsedArgs.emplace_back(param != nullptr ? param->GetCoreType() : nullptr);
322 break;
323 }
324 default:
325 LOG(FATAL, ANI) << "Unexpected argument type";
326 break;
327 }
328 }
329 return parsedArgs;
330 }
331
ResolveVirtualMethod(ScopedManagedCodeFix & s,ani_object object,ani_method method)332 static inline EtsMethod *ResolveVirtualMethod(ScopedManagedCodeFix &s, ani_object object, ani_method method)
333 {
334 EtsMethod *m = ToInternalMethod(method);
335 if (UNLIKELY(m->IsStatic())) {
336 LOG(FATAL, ANI) << "Called ResolveVirtualMethod of static method, invalid ANI usage";
337 return m;
338 }
339 EtsObject *obj = s.ToInternalType(object);
340 return obj->GetClass()->ResolveVirtualMethod(m);
341 }
342
343 template <typename EtsValueType, typename AniType, typename MethodType, typename Args>
DoGeneralMethodCall(ScopedManagedCodeFix & s,ani_object obj,MethodType method,AniType * result,Args args)344 static ani_status DoGeneralMethodCall(ScopedManagedCodeFix &s, ani_object obj, MethodType method, AniType *result,
345 Args args)
346 {
347 ASSERT(result != nullptr);
348 // Trigger coroutine manager native call events
349 ScopedCoroutineNativeCall c(s.GetCoroutine());
350
351 EtsMethod *m = nullptr;
352 if constexpr (std::is_same_v<MethodType, ani_method>) {
353 m = ResolveVirtualMethod(s, obj, method);
354 } else if constexpr (std::is_same_v<MethodType, ani_static_method>) {
355 m = ToInternalMethod(method);
356
357 ani_status status = InitializeClass(s, m->GetClass());
358 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
359 } else if constexpr (std::is_same_v<MethodType, ani_function>) {
360 m = ToInternalFunction(method);
361
362 ani_status status = InitializeClass(s, m->GetClass());
363 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
364 } else {
365 static_assert(!(std::is_same_v<MethodType, ani_method> || std::is_same_v<MethodType, ani_static_method> ||
366 std::is_same_v<MethodType, ani_function>),
367 "Unreachable type");
368 }
369 ASSERT(m != nullptr);
370
371 EtsValue res {};
372 ArgVector<Value> values = GetArgValues(s, m, args, obj);
373 ani_status status = m->Invoke(s, values.data(), &res);
374 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
375 // Now AniType and EtsValueType are the same, but later it could be changed
376 static_assert(std::is_same_v<AniType, EtsValueType>);
377 *result = res.GetAs<EtsValueType>();
378 return ANI_OK;
379 }
380
381 template <typename EtsValueType, typename AniType, typename MethodType, typename Args>
GeneralMethodCall(ani_env * env,ani_object obj,MethodType method,AniType * result,Args args)382 static ani_status GeneralMethodCall(ani_env *env, ani_object obj, MethodType method, AniType *result, Args args)
383 {
384 ScopedManagedCodeFix s(env);
385 return DoGeneralMethodCall<EtsValueType, AniType, MethodType, Args>(s, obj, method, result, args);
386 }
387
388 template <typename EtsValueType, typename AniType, typename Args>
GeneralFunctionCall(ani_env * env,ani_function fn,AniType * result,Args args)389 static ani_status GeneralFunctionCall(ani_env *env, ani_function fn, AniType *result, Args args)
390 {
391 auto method = reinterpret_cast<ani_function>(fn);
392 ScopedManagedCodeFix s(env);
393 return DoGeneralMethodCall<EtsValueType, AniType, ani_function, Args>(s, nullptr, method, result, args);
394 }
395
396 template <typename T>
GetPrimitiveTypeField(ani_env * env,ani_object object,ani_field field,T * result)397 static inline ani_status GetPrimitiveTypeField(ani_env *env, ani_object object, ani_field field, T *result)
398 {
399 CHECK_ENV(env);
400 CHECK_PTR_ARG(object);
401 CHECK_PTR_ARG(field);
402 CHECK_PTR_ARG(result);
403
404 EtsField *etsField = ToInternalField(field);
405 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
406
407 ScopedManagedCodeFix s(env);
408 EtsObject *etsObject = s.ToInternalType(object);
409 *result = etsObject->GetFieldPrimitive<T>(etsField);
410 return ANI_OK;
411 }
412
413 template <typename T>
SetPrimitiveTypeField(ani_env * env,ani_object object,ani_field field,T value)414 static inline ani_status SetPrimitiveTypeField(ani_env *env, ani_object object, ani_field field, T value)
415 {
416 CHECK_ENV(env);
417 CHECK_PTR_ARG(object);
418 CHECK_PTR_ARG(field);
419
420 EtsField *etsField = ToInternalField(field);
421 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
422
423 ScopedManagedCodeFix s(env);
424 EtsObject *etsObject = s.ToInternalType(object);
425 etsObject->SetFieldPrimitive(etsField, value);
426 return ANI_OK;
427 }
428
429 template <typename T>
ClassGetStaticField(ani_env * env,ani_class cls,ani_static_field field,T * result)430 static ani_status ClassGetStaticField(ani_env *env, ani_class cls, ani_static_field field, T *result)
431 {
432 CHECK_ENV(env);
433 CHECK_PTR_ARG(cls);
434 CHECK_PTR_ARG(field);
435 CHECK_PTR_ARG(result);
436
437 EtsField *etsField = ToInternalField(field);
438 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
439
440 ScopedManagedCodeFix s(env);
441 EtsClass *etsClass = s.ToInternalType(cls);
442 ani_status status = InitializeClass(s, etsClass);
443 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
444
445 *result = etsClass->GetStaticFieldPrimitive<T>(etsField);
446 return ANI_OK;
447 }
448
449 template <typename T>
ClassSetStaticField(ani_env * env,ani_class cls,ani_static_field field,T value)450 static ani_status ClassSetStaticField(ani_env *env, ani_class cls, ani_static_field field, T value)
451 {
452 CHECK_ENV(env);
453 CHECK_PTR_ARG(cls);
454 CHECK_PTR_ARG(field);
455
456 EtsField *etsField = ToInternalField(field);
457 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
458
459 ScopedManagedCodeFix s(env);
460 EtsClass *etsClass = s.ToInternalType(cls);
461 ani_status status = InitializeClass(s, etsClass);
462 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
463
464 etsClass->SetStaticFieldPrimitive(etsField, value);
465 return ANI_OK;
466 }
467
468 template <typename T>
ClassGetStaticFieldByName(ani_env * env,ani_class cls,const char * name,T * result)469 static ani_status ClassGetStaticFieldByName(ani_env *env, ani_class cls, const char *name, T *result)
470 {
471 CHECK_ENV(env);
472 CHECK_PTR_ARG(cls);
473 CHECK_PTR_ARG(name);
474 CHECK_PTR_ARG(result);
475
476 ScopedManagedCodeFix s(env);
477 EtsClass *etsClass = s.ToInternalType(cls);
478
479 EtsField *etsField = etsClass->GetStaticFieldIDByName(name, nullptr);
480 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
481 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
482
483 ani_status status = InitializeClass(s, etsClass);
484 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
485
486 *result = etsClass->GetStaticFieldPrimitive<T>(etsField);
487 return ANI_OK;
488 }
489
490 template <typename T>
ClassSetStaticFieldByName(ani_env * env,ani_class cls,const char * name,T value)491 static ani_status ClassSetStaticFieldByName(ani_env *env, ani_class cls, const char *name, T value)
492 {
493 CHECK_ENV(env);
494 CHECK_PTR_ARG(cls);
495 CHECK_PTR_ARG(name);
496
497 ScopedManagedCodeFix s(env);
498 EtsClass *etsClass = s.ToInternalType(cls);
499
500 EtsField *etsField = etsClass->GetStaticFieldIDByName(name, nullptr);
501 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
502 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
503
504 ani_status status = InitializeClass(s, etsClass);
505 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
506
507 etsClass->SetStaticFieldPrimitive(etsField, value);
508 return ANI_OK;
509 }
510
511 // Descriptor should conform to rules of runtime internal descriptors
512 template <bool IS_MODULE, typename T>
DoFind(PandaEnv * pandaEnv,const char * descriptor,ScopedManagedCodeFix & s,T * result)513 static ani_status DoFind(PandaEnv *pandaEnv, const char *descriptor, ScopedManagedCodeFix &s, T *result)
514 {
515 ASSERT(pandaEnv != nullptr);
516 ASSERT(descriptor != nullptr);
517 ASSERT(result != nullptr);
518 EtsClassLinker *classLinker = pandaEnv->GetEtsVM()->GetClassLinker();
519 EtsClass *klass = classLinker->GetClass(descriptor, true, GetClassLinkerContext(s.GetCoroutine()));
520 if (UNLIKELY(pandaEnv->HasPendingException())) {
521 EtsThrowable *currentException = pandaEnv->GetThrowable();
522 std::string_view exceptionString = currentException->GetClass()->GetDescriptor();
523 if (exceptionString == panda_file_items::class_descriptors::LINKER_CLASS_NOT_FOUND_ERROR) {
524 pandaEnv->ClearException();
525 return ANI_NOT_FOUND;
526 }
527
528 // NOTE: Handle exception
529 return ANI_PENDING_ERROR;
530 }
531 ANI_CHECK_RETURN_IF_EQ(klass, nullptr, ANI_NOT_FOUND);
532 ANI_CHECK_RETURN_IF_NE(klass->IsModule(), IS_MODULE, ANI_NOT_FOUND);
533
534 ASSERT_MANAGED_CODE();
535 return s.AddLocalRef(reinterpret_cast<EtsObject *>(klass), reinterpret_cast<ani_ref *>(result));
536 }
537
538 template <bool IS_MODULE, typename T>
DoFind(ani_env * env,const char * descriptor,T * result)539 static ani_status DoFind(ani_env *env, const char *descriptor, T *result)
540 {
541 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
542 ScopedManagedCodeFix s(pandaEnv);
543 return DoFind<IS_MODULE>(pandaEnv, descriptor, s, result);
544 }
545
546 template <bool IS_STATIC>
CheckUniqueMethod(EtsClass * klass,const char * name)547 static bool CheckUniqueMethod(EtsClass *klass, const char *name)
548 {
549 ASSERT(klass != nullptr);
550 ASSERT(name != nullptr);
551 size_t nameCounter = 0;
552 for (auto &method : klass->GetMethods()) {
553 if (method->IsStatic() == IS_STATIC && ::strcmp(method->GetName(), name) == 0) {
554 if (++nameCounter == 2U) {
555 return false;
556 }
557 }
558 }
559 return true;
560 }
561
CheckPrimitiveEncoding(char primitiveEncoding)562 static bool CheckPrimitiveEncoding(char primitiveEncoding)
563 {
564 // Switch-case is more optimal when compiled for arm
565 switch (primitiveEncoding) {
566 case 'Z':
567 [[fallthrough]];
568 case 'B':
569 [[fallthrough]];
570 case 'S':
571 [[fallthrough]];
572 case 'C':
573 [[fallthrough]];
574 case 'I':
575 [[fallthrough]];
576 case 'J':
577 [[fallthrough]];
578 case 'F':
579 [[fallthrough]];
580 case 'D':
581 return true;
582 default:
583 return false;
584 }
585 UNREACHABLE();
586 }
587
ReplaceArrayInSignature(const char * signature)588 static std::optional<std::string> ReplaceArrayInSignature(const char *signature)
589 {
590 static constexpr std::string_view ESCOMPAT_ARRAY = "Lescompat/Array;";
591
592 ASSERT(signature != nullptr);
593 std::string_view signatureView(signature);
594 auto pos = signatureView.find('[');
595 if (pos == std::string_view::npos) {
596 // Arrays are not used in signature
597 return std::string(signature);
598 }
599
600 std::stringstream ss;
601 std::string_view::size_type prevPos = 0;
602 for (; pos != std::string_view::npos; pos = signatureView.find('[', prevPos)) {
603 ss << signatureView.substr(prevPos, pos - prevPos);
604
605 prevPos = signatureView.find_first_not_of('[', pos);
606 if (UNLIKELY(prevPos == std::string_view::npos)) {
607 // Invalid signature, incorrect array encoding (trailing '[')
608 return std::nullopt;
609 }
610
611 auto elementTypeEncoding = signatureView[prevPos];
612 if (elementTypeEncoding == 'L') {
613 auto tmpPrevPos = signatureView.find(';', prevPos);
614 if (UNLIKELY(tmpPrevPos == std::string_view::npos || (tmpPrevPos - prevPos) == 1)) {
615 // Invalid signature, incorrectly encoded reference type
616 return std::nullopt;
617 }
618 prevPos = tmpPrevPos + 1;
619 } else {
620 // Primitive array, check its encoding
621 if (UNLIKELY(!CheckPrimitiveEncoding(elementTypeEncoding))) {
622 return std::nullopt;
623 }
624 ++prevPos;
625 }
626 // Add escompat.Array as replacement. This is required to support compatibility with existing user code.
627 // In order to use signatures with FixedArray, use new mangling rules, which are supported as part of #IBZ7ML
628 ss << ESCOMPAT_ARRAY;
629 }
630 // Append final part of signature
631 if (prevPos < signatureView.size()) {
632 ss << signatureView.substr(prevPos);
633 }
634
635 return ss.str();
636 }
637
638 template <bool IS_STATIC_METHOD>
DoGetClassMethod(EtsClass * klass,const char * name,const char * signature,EtsMethod ** result)639 static ani_status DoGetClassMethod(EtsClass *klass, const char *name, const char *signature, EtsMethod **result)
640 {
641 ASSERT_MANAGED_CODE();
642 ASSERT(klass != nullptr);
643 ASSERT(result != nullptr);
644 if (signature == nullptr && !CheckUniqueMethod<IS_STATIC_METHOD>(klass, name)) {
645 return ANI_AMBIGUOUS;
646 }
647
648 // CC-OFFNXT(G.FMT.14-CPP) project code style
649 auto *method = [klass, name, signature]() -> EtsMethod * {
650 if (signature == nullptr) {
651 if constexpr (IS_STATIC_METHOD) {
652 return klass->GetStaticMethod(name, signature, true);
653 } else {
654 return klass->GetInstanceMethod(name, signature, true);
655 }
656 }
657 auto optSignature = ReplaceArrayInSignature(signature);
658 if (optSignature) {
659 if constexpr (IS_STATIC_METHOD) {
660 return klass->GetStaticMethod(name, optSignature.value().c_str(), true);
661 } else {
662 return klass->GetInstanceMethod(name, optSignature.value().c_str(), true);
663 }
664 }
665 return nullptr;
666 }();
667 if (method == nullptr || method->IsStatic() != IS_STATIC_METHOD) {
668 return ANI_NOT_FOUND;
669 }
670 *result = method;
671 return ANI_OK;
672 }
673
674 template <bool IS_STATIC_METHOD>
GetClassMethod(ani_env * env,ani_class cls,const char * name,const char * signature,EtsMethod ** result)675 static ani_status GetClassMethod(ani_env *env, ani_class cls, const char *name, const char *signature,
676 EtsMethod **result)
677 {
678 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
679 EtsClass *klass = s.ToInternalType(cls);
680 return DoGetClassMethod<IS_STATIC_METHOD>(klass, name, signature, result);
681 }
682
683 template <typename ReturnType, EtsType EXPECT_TYPE, typename Args>
684 // CC-OFFNXT(G.FUN.01-CPP) solid logic
ObjectCallMethodByName(ani_env * env,ani_object object,const char * name,const char * signature,ReturnType * result,Args args)685 static ani_status ObjectCallMethodByName(ani_env *env, ani_object object, const char *name, const char *signature,
686 ReturnType *result, Args args)
687 {
688 CHECK_ENV(env);
689 CHECK_PTR_ARG(object);
690 CHECK_PTR_ARG(result);
691 CHECK_PTR_ARG(name);
692
693 ScopedManagedCodeFix s(env);
694 EtsObject *etsObject = s.ToInternalType(object);
695 ASSERT(etsObject != nullptr);
696 EtsClass *cls = etsObject->GetClass();
697 EtsMethod *method = nullptr;
698 ani_status status = DoGetClassMethod<false>(cls, name, signature, &method);
699 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
700 ASSERT(method != nullptr);
701 ani_method aniMethod = ToAniMethod(method);
702 CheckMethodReturnType(aniMethod, EXPECT_TYPE);
703 return DoGeneralMethodCall<ReturnType>(s, object, aniMethod, result, args);
704 }
705
GetNamespaceFunction(ani_env * env,ani_namespace ns,const char * name,const char * signature,EtsMethod ** result)706 static ani_status GetNamespaceFunction(ani_env *env, ani_namespace ns, const char *name, const char *signature,
707 EtsMethod **result)
708 {
709 ScopedManagedCodeFix s(env);
710 EtsNamespace *etsNs = EtsNamespace::FromClass(s.ToInternalType(ns)->AsClass());
711 return DoGetClassMethod<true>(etsNs->AsClass(), name, signature, result);
712 }
713
GetModuleFunction(ani_env * env,ani_module ns,const char * name,const char * signature,EtsMethod ** result)714 static ani_status GetModuleFunction(ani_env *env, ani_module ns, const char *name, const char *signature,
715 EtsMethod **result)
716 {
717 ScopedManagedCodeFix s(env);
718 EtsModule *etsModule = EtsModule::FromClass(s.ToInternalType(ns)->AsClass());
719 return DoGetClassMethod<true>(etsModule->AsClass(), name, signature, result);
720 }
721
722 template <typename ReturnType, EtsType EXPECT_TYPE, typename Args>
723 // CC-OFFNXT(G.FUN.01-CPP) solid logic
ClassCallMethodByName(ani_env * env,ani_class cls,const char * name,const char * signature,ReturnType * result,Args args)724 static ani_status ClassCallMethodByName(ani_env *env, ani_class cls, const char *name, const char *signature,
725 ReturnType *result, Args args)
726 {
727 CHECK_ENV(env);
728 CHECK_PTR_ARG(cls);
729 CHECK_PTR_ARG(name);
730 CHECK_PTR_ARG(result);
731
732 EtsMethod *method = nullptr;
733 ani_status status = GetClassMethod<true>(env, cls, name, signature, &method);
734 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
735 ASSERT(method != nullptr);
736 ani_static_method staticMethod = ToAniStaticMethod(method);
737 CheckStaticMethodReturnType(staticMethod, EXPECT_TYPE);
738 return GeneralMethodCall<ReturnType>(env, nullptr, staticMethod, result, args);
739 }
740
741 template <bool IS_MODULE, typename T>
FindInModule(ani_env * env,ani_module module,const char * targetDescriptor,T * result)742 static ani_status FindInModule(ani_env *env, ani_module module, const char *targetDescriptor, T *result)
743 {
744 CHECK_ENV(env);
745 CHECK_PTR_ARG(module);
746 CHECK_PTR_ARG(targetDescriptor);
747 CHECK_PTR_ARG(result);
748
749 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
750 ScopedManagedCodeFix s(pandaEnv);
751 EtsModule *etsModule = EtsModule::FromClass(s.ToInternalType(module)->AsClass());
752
753 PandaString descriptor;
754 ANI_CHECK_RETURN_IF_NE(etsModule->GetModulePrefix(descriptor), ANI_OK, ANI_INVALID_DESCRIPTOR);
755 PandaString className = Mangle::ConvertDescriptor(targetDescriptor);
756 ANI_CHECK_RETURN_IF_LE(className.length(), 2U, ANI_INVALID_ARGS);
757 ANI_CHECK_RETURN_IF_NE(className[0], 'L', ANI_INVALID_ARGS);
758
759 className[0] = '/';
760 descriptor += className;
761
762 return DoFind<IS_MODULE>(pandaEnv, descriptor.c_str(), s, result);
763 }
764
GetVersion(ani_env * env,uint32_t * result)765 NO_UB_SANITIZE static ani_status GetVersion(ani_env *env, uint32_t *result)
766 {
767 ANI_DEBUG_TRACE(env);
768 CHECK_ENV(env);
769 CHECK_PTR_ARG(result);
770
771 *result = ANI_VERSION_1;
772 return ANI_OK;
773 }
774
GetVM(ani_env * env,ani_vm ** result)775 ani_status GetVM(ani_env *env, ani_vm **result)
776 {
777 ANI_DEBUG_TRACE(env);
778 CHECK_ENV(env);
779 CHECK_PTR_ARG(result);
780
781 *result = PandaEnv::FromAniEnv(env)->GetEtsVM();
782 return ANI_OK;
783 }
784
AllocObject(ScopedManagedCodeFix & s,ani_class cls,ani_object * result)785 static ani_status AllocObject(ScopedManagedCodeFix &s, ani_class cls, ani_object *result)
786 {
787 EtsClass *klass = s.ToInternalType(cls);
788 ANI_CHECK_RETURN_IF_EQ(klass->IsAbstract(), true, ANI_INVALID_TYPE);
789 ANI_CHECK_RETURN_IF_EQ(klass->IsInterface(), true, ANI_INVALID_TYPE);
790
791 // NODE: Check than we have the ability to create String/FiexedArray in this API, #22280
792 ANI_CHECK_RETURN_IF_EQ(klass->IsStringClass(), true, ANI_INVALID_TYPE);
793 ANI_CHECK_RETURN_IF_EQ(klass->IsArrayClass(), true, ANI_INVALID_TYPE);
794
795 EtsObject *obj = EtsObject::Create(klass);
796 ANI_CHECK_RETURN_IF_EQ(obj, nullptr, ANI_OUT_OF_MEMORY);
797 return s.AddLocalRef(obj, reinterpret_cast<ani_ref *>(result));
798 }
799
800 template <typename Args>
DoNewObject(ani_env * env,ani_class cls,ani_method method,ani_object * result,Args args)801 static ani_status DoNewObject(ani_env *env, ani_class cls, ani_method method, ani_object *result, Args args)
802 {
803 ani_object object;
804 ScopedManagedCodeFix s(env);
805 ani_status status = AllocObject(s, cls, &object);
806 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
807
808 EtsClass *klass = s.ToInternalType(cls);
809 status = InitializeClass(s, klass);
810 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
811
812 // Use any primitive type as template parameter and just ignore the result
813 ani_int tmp;
814 status = DoGeneralMethodCall<EtsInt>(s, object, method, &tmp, args);
815 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
816 *result = object;
817 return ANI_OK;
818 }
819
820 // NOLINTNEXTLINE(readability-identifier-naming)
Object_New_A(ani_env * env,ani_class cls,ani_method method,ani_object * result,const ani_value * args)821 NO_UB_SANITIZE static ani_status Object_New_A(ani_env *env, ani_class cls, ani_method method, ani_object *result,
822 const ani_value *args)
823 {
824 ANI_DEBUG_TRACE(env);
825 CHECK_ENV(env);
826 CHECK_PTR_ARG(cls);
827 CHECK_PTR_ARG(method);
828 CHECK_PTR_ARG(result);
829 CHECK_PTR_ARG(args);
830
831 return DoNewObject(env, cls, method, result, args);
832 }
833
834 // NOLINTNEXTLINE(readability-identifier-naming)
Object_New_V(ani_env * env,ani_class cls,ani_method method,ani_object * result,va_list args)835 NO_UB_SANITIZE static ani_status Object_New_V(ani_env *env, ani_class cls, ani_method method, ani_object *result,
836 va_list args)
837 {
838 ANI_DEBUG_TRACE(env);
839 CHECK_ENV(env);
840 CHECK_PTR_ARG(cls);
841 CHECK_PTR_ARG(method);
842 CHECK_PTR_ARG(result);
843
844 return DoNewObject(env, cls, method, result, args);
845 }
846
847 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetType(ani_env * env,ani_object object,ani_type * result)848 NO_UB_SANITIZE static ani_status Object_GetType(ani_env *env, ani_object object, ani_type *result)
849 {
850 ANI_DEBUG_TRACE(env);
851 CHECK_ENV(env);
852 CHECK_PTR_ARG(object);
853 CHECK_PTR_ARG(result);
854
855 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
856 EtsObject *etsObject = s.ToInternalType(object);
857 ASSERT(etsObject != nullptr);
858 EtsClass *etsClass = etsObject->GetClass();
859 ASSERT(etsClass != nullptr);
860
861 s.AddLocalRef(etsClass->AsObject(), reinterpret_cast<ani_ref *>(result));
862 return ANI_OK;
863 }
864
865 // NOLINTNEXTLINE(readability-identifier-naming)
Object_New(ani_env * env,ani_class cls,ani_method method,ani_object * result,...)866 NO_UB_SANITIZE static ani_status Object_New(ani_env *env, ani_class cls, ani_method method, ani_object *result, ...)
867 {
868 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
869 va_start(args, result);
870 ani_status status = Object_New_V(env, cls, method, result, args);
871 va_end(args);
872 return status;
873 }
874
875 // NOLINTNEXTLINE(readability-identifier-naming)
Type_GetSuperClass(ani_env * env,ani_type type,ani_class * result)876 ani_status Type_GetSuperClass(ani_env *env, ani_type type, ani_class *result)
877 {
878 ANI_DEBUG_TRACE(env);
879 CHECK_ENV(env);
880 CHECK_PTR_ARG(type);
881 CHECK_PTR_ARG(result);
882
883 ScopedManagedCodeFix s(env);
884 EtsClass *cls = s.ToInternalType(type);
885
886 EtsClass *superCls = cls->GetSuperClass();
887 if (superCls != nullptr) {
888 ASSERT(superCls->IsClass());
889 return s.AddLocalRef(superCls->AsObject(), reinterpret_cast<ani_ref *>(result));
890 }
891 *result = nullptr;
892 return ANI_OK;
893 }
894
895 // NOLINTNEXTLINE(readability-identifier-naming)
Type_IsAssignableFrom(ani_env * env,ani_type fromType,ani_type toType,ani_boolean * result)896 ani_status Type_IsAssignableFrom(ani_env *env, ani_type fromType, ani_type toType, ani_boolean *result)
897 {
898 ANI_DEBUG_TRACE(env);
899 CHECK_ENV(env);
900 CHECK_PTR_ARG(fromType);
901 CHECK_PTR_ARG(toType);
902 CHECK_PTR_ARG(result);
903
904 ScopedManagedCodeFix s(env);
905 EtsClass *toClass = s.ToInternalType(toType);
906 EtsClass *fromClass = s.ToInternalType(fromType);
907
908 *result = toClass->IsAssignableFrom(fromClass) ? ANI_TRUE : ANI_FALSE;
909 return ANI_OK;
910 }
911
FindModule(ani_env * env,const char * moduleDescriptor,ani_module * result)912 NO_UB_SANITIZE static ani_status FindModule(ani_env *env, const char *moduleDescriptor, ani_module *result)
913 {
914 ANI_DEBUG_TRACE(env);
915 CHECK_ENV(env);
916 CHECK_PTR_ARG(moduleDescriptor);
917 CHECK_PTR_ARG(result);
918
919 PandaString desc = Mangle::ConvertDescriptor(moduleDescriptor);
920 ANI_CHECK_RETURN_IF_LE(desc.size(), 2U, ANI_INVALID_DESCRIPTOR);
921 ANI_CHECK_RETURN_IF_NE(desc.back(), ';', ANI_INVALID_DESCRIPTOR);
922 PandaString descriptor(desc.data(), desc.size() - 1);
923 descriptor += "/ETSGLOBAL;";
924
925 // NOTE: Check that results is namespace, #22400
926 return DoFind<true>(env, descriptor.c_str(), result);
927 }
928
FindNamespace(ani_env * env,const char * namespaceDescriptor,ani_namespace * result)929 NO_UB_SANITIZE static ani_status FindNamespace(ani_env *env, const char *namespaceDescriptor, ani_namespace *result)
930 {
931 ANI_DEBUG_TRACE(env);
932 CHECK_ENV(env);
933 CHECK_PTR_ARG(namespaceDescriptor);
934 CHECK_PTR_ARG(result);
935
936 PandaString desc = Mangle::ConvertDescriptor(namespaceDescriptor);
937 // NOTE: Check that results is namespace, #22400
938 return DoFind<true>(env, desc.c_str(), result);
939 }
940
FindClass(ani_env * env,const char * classDescriptor,ani_class * result)941 NO_UB_SANITIZE static ani_status FindClass(ani_env *env, const char *classDescriptor, ani_class *result)
942 {
943 ANI_DEBUG_TRACE(env);
944 CHECK_ENV(env);
945 CHECK_PTR_ARG(classDescriptor);
946 CHECK_PTR_ARG(result);
947 PandaString desc = Mangle::ConvertDescriptor(classDescriptor, true);
948
949 // NOTE: Check that results is class, #22400
950 return DoFind<false>(env, desc.c_str(), result);
951 }
952
953 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_FindFunction(ani_env * env,ani_namespace ns,const char * name,const char * signature,ani_function * result)954 NO_UB_SANITIZE static ani_status Namespace_FindFunction(ani_env *env, ani_namespace ns, const char *name,
955 const char *signature, ani_function *result)
956 {
957 ANI_DEBUG_TRACE(env);
958 CHECK_ENV(env);
959 CHECK_PTR_ARG(ns);
960 CHECK_PTR_ARG(name);
961 CHECK_PTR_ARG(result);
962
963 EtsMethod *method = nullptr;
964 ani_status status = GetNamespaceFunction(env, ns, name, signature, &method);
965 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
966 *result = ToAniFunction(method);
967 return ANI_OK;
968 }
969
970 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_FindNamespace(ani_env * env,ani_namespace ns,const char * namespaceDescriptor,ani_namespace * result)971 NO_UB_SANITIZE static ani_status Namespace_FindNamespace(ani_env *env, ani_namespace ns,
972 const char *namespaceDescriptor, ani_namespace *result)
973 {
974 ANI_DEBUG_TRACE(env);
975 CHECK_ENV(env);
976 CHECK_PTR_ARG(ns);
977 CHECK_PTR_ARG(namespaceDescriptor);
978 CHECK_PTR_ARG(result);
979
980 auto pandaEnv = PandaEtsNapiEnv::FromAniEnv(env);
981 ScopedManagedCodeFix s(pandaEnv);
982 EtsNamespace *etsNs = EtsNamespace::FromClass(s.ToInternalType(ns)->AsClass());
983 std::string_view nsDescriptor = etsNs->AsClass()->GetDescriptor();
984 ASSERT(nsDescriptor.size() > 2U);
985
986 PandaString nameDescriptor = Mangle::ConvertDescriptor(namespaceDescriptor);
987 if (nameDescriptor[0] == 'L') {
988 nameDescriptor[0] = '/';
989 } else {
990 return ANI_NOT_FOUND;
991 }
992
993 PandaString descriptor(nsDescriptor.data(), nsDescriptor.size() - 1);
994 descriptor += nameDescriptor;
995
996 // NOTE: Check that results is namespace, #22400
997 return DoFind<true>(pandaEnv, descriptor.c_str(), s, result);
998 }
999
1000 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_FindClass(ani_env * env,ani_namespace ns,const char * classDescriptor,ani_class * result)1001 NO_UB_SANITIZE static ani_status Namespace_FindClass(ani_env *env, ani_namespace ns, const char *classDescriptor,
1002 ani_class *result)
1003 {
1004 ANI_DEBUG_TRACE(env);
1005 CHECK_ENV(env);
1006 CHECK_PTR_ARG(ns);
1007 CHECK_PTR_ARG(classDescriptor);
1008 CHECK_PTR_ARG(result);
1009
1010 auto pandaEnv = PandaEtsNapiEnv::FromAniEnv(env);
1011 ScopedManagedCodeFix s(pandaEnv);
1012 EtsNamespace *etsNs = EtsNamespace::FromClass(s.ToInternalType(ns)->AsClass());
1013 std::string_view nsDescriptor = etsNs->AsClass()->GetDescriptor();
1014 ASSERT(nsDescriptor.size() > 2U);
1015
1016 PandaString clDescriptor = Mangle::ConvertDescriptor(classDescriptor);
1017 if (clDescriptor[0] == 'L') {
1018 clDescriptor[0] = '/';
1019 } else {
1020 return ANI_NOT_FOUND;
1021 }
1022
1023 PandaString descriptor(nsDescriptor.data(), nsDescriptor.size() - 1);
1024 descriptor += clDescriptor;
1025
1026 // NOTE: Check that results is class, #22400
1027 return DoFind<false>(pandaEnv, descriptor.c_str(), s, result);
1028 }
1029
1030 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_FindVariable(ani_env * env,ani_namespace ns,const char * variableDescriptor,ani_variable * result)1031 NO_UB_SANITIZE static ani_status Namespace_FindVariable(ani_env *env, ani_namespace ns, const char *variableDescriptor,
1032 ani_variable *result)
1033 {
1034 ANI_DEBUG_TRACE(env);
1035 CHECK_ENV(env);
1036 CHECK_PTR_ARG(ns);
1037 CHECK_PTR_ARG(variableDescriptor);
1038 CHECK_PTR_ARG(result);
1039
1040 ScopedManagedCodeFix s(env);
1041 EtsNamespace *etsNs = EtsNamespace::FromClass(s.ToInternalType(ns)->AsClass());
1042 EtsVariable *variable = etsNs->GetVariabe(variableDescriptor);
1043 ANI_CHECK_RETURN_IF_EQ(variable, nullptr, ANI_NOT_FOUND);
1044
1045 *result = ToAniVariable(variable);
1046 return ANI_OK;
1047 }
1048
1049 // NOLINTNEXTLINE(readability-identifier-naming)
Module_FindFunction(ani_env * env,ani_module module,const char * name,const char * signature,ani_function * result)1050 NO_UB_SANITIZE static ani_status Module_FindFunction(ani_env *env, ani_module module, const char *name,
1051 const char *signature, ani_function *result)
1052 {
1053 ANI_DEBUG_TRACE(env);
1054 CHECK_ENV(env);
1055 CHECK_PTR_ARG(module);
1056 CHECK_PTR_ARG(name);
1057 CHECK_PTR_ARG(result);
1058
1059 EtsMethod *method = nullptr;
1060 ani_status status = GetModuleFunction(env, module, name, signature, &method);
1061 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1062 *result = ToAniFunction(method);
1063 return ANI_OK;
1064 }
1065
1066 // NOLINTNEXTLINE(readability-identifier-naming)
Module_FindVariable(ani_env * env,ani_module module,const char * variableDescriptor,ani_variable * result)1067 NO_UB_SANITIZE static ani_status Module_FindVariable(ani_env *env, ani_module module, const char *variableDescriptor,
1068 ani_variable *result)
1069 {
1070 ANI_DEBUG_TRACE(env);
1071 CHECK_ENV(env);
1072 CHECK_PTR_ARG(module);
1073 CHECK_PTR_ARG(variableDescriptor);
1074 CHECK_PTR_ARG(result);
1075
1076 ScopedManagedCodeFix s(env);
1077 EtsModule *etsModule = EtsModule::FromClass(s.ToInternalType(module)->AsClass());
1078 EtsVariable *variable = etsModule->GetVariabe(variableDescriptor);
1079 ANI_CHECK_RETURN_IF_EQ(variable, nullptr, ANI_NOT_FOUND);
1080
1081 *result = ToAniVariable(variable);
1082 return ANI_OK;
1083 }
1084
1085 // NOLINTNEXTLINE(readability-identifier-naming)
Module_FindClass(ani_env * env,ani_module module,const char * classDescriptor,ani_class * result)1086 NO_UB_SANITIZE static ani_status Module_FindClass(ani_env *env, ani_module module, const char *classDescriptor,
1087 ani_class *result)
1088 {
1089 ANI_DEBUG_TRACE(env);
1090 return FindInModule<false>(env, module, classDescriptor, result);
1091 }
1092
1093 // NOLINTNEXTLINE(readability-identifier-naming)
Module_FindNamespace(ani_env * env,ani_module module,const char * namespaceDescriptor,ani_namespace * result)1094 NO_UB_SANITIZE static ani_status Module_FindNamespace(ani_env *env, ani_module module, const char *namespaceDescriptor,
1095 ani_namespace *result)
1096 {
1097 ANI_DEBUG_TRACE(env);
1098 return FindInModule<true>(env, module, namespaceDescriptor, result);
1099 }
1100
1101 template <typename InternalType, typename AniFixedArrayType>
NewPrimitiveTypeArray(ani_env * env,ani_size length,AniFixedArrayType * result)1102 static ani_status NewPrimitiveTypeArray(ani_env *env, ani_size length, AniFixedArrayType *result)
1103 {
1104 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
1105 auto *array = InternalType::Create(length);
1106 ANI_CHECK_RETURN_IF_EQ(array, nullptr, ANI_OUT_OF_MEMORY);
1107 return s.AddLocalRef(reinterpret_cast<EtsObject *>(array), reinterpret_cast<ani_ref *>(result));
1108 }
1109
1110 template <typename T>
GetArrayRegion(EtsArrayObject<EtsBoxPrimitive<T>> * objectArray,size_t start,size_t offset,T * buff)1111 static ani_status GetArrayRegion(EtsArrayObject<EtsBoxPrimitive<T>> *objectArray, size_t start, size_t offset, T *buff)
1112 {
1113 ASSERT(buff != nullptr);
1114 ANI_CHECK_RETURN_IF_GT(offset, std::numeric_limits<size_t>::max() - start, ANI_OUT_OF_RANGE);
1115 size_t end = start + offset;
1116 ANI_CHECK_RETURN_IF_GT(end, objectArray->GetActualLength(), ANI_OUT_OF_RANGE);
1117
1118 Class *boxPrimitiveClass = EtsBoxPrimitive<T>::GetBoxClass(EtsCoroutine::GetCurrent());
1119 for (size_t posArr = start, posBuff = 0; posArr < end; ++posArr, ++posBuff) {
1120 EtsBoxPrimitive<T> *boxedVal = nullptr;
1121 [[maybe_unused]] auto getRes = objectArray->GetRef(posArr, &boxedVal);
1122 ASSERT(getRes);
1123 ANI_CHECK_RETURN_IF_EQ(boxedVal, nullptr, ANI_ERROR);
1124 if (boxPrimitiveClass != boxedVal->GetClass()->GetRuntimeClass()) {
1125 return ANI_INVALID_TYPE;
1126 }
1127
1128 auto primitiveValue = boxedVal->GetValue();
1129 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1130 buff[posBuff] = primitiveValue;
1131 }
1132 return ANI_OK;
1133 }
1134
1135 template <typename T>
SetArrayRegion(ScopedManagedCodeFix & s,EtsArrayObject<EtsBoxPrimitive<std::remove_const_t<T>>> * objectArray,size_t start,size_t offset,T * buff)1136 static ani_status SetArrayRegion(ScopedManagedCodeFix &s,
1137 EtsArrayObject<EtsBoxPrimitive<std::remove_const_t<T>>> *objectArray, size_t start,
1138 size_t offset, T *buff)
1139 {
1140 ASSERT(buff != nullptr);
1141 auto *coro = EtsCoroutine::GetCurrent();
1142
1143 ANI_CHECK_RETURN_IF_GT(offset, std::numeric_limits<size_t>::max() - start, ANI_OUT_OF_RANGE);
1144 size_t end = start + offset;
1145 ANI_CHECK_RETURN_IF_GT(end, objectArray->GetActualLength(), ANI_OUT_OF_RANGE);
1146
1147 EtsCoroutine *coroutine = s.GetCoroutine();
1148 EtsHandleScope scope(coroutine);
1149 EtsHandle objectArrayHandle(coroutine, objectArray);
1150 ASSERT(objectArrayHandle.GetPtr() != nullptr);
1151 for (size_t posArr = start, posBuff = 0; posArr < end; ++posArr, ++posBuff) {
1152 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1153 T value = buff[posBuff];
1154 auto boxedValue = EtsBoxPrimitive<std::remove_const_t<T>>::Create(coro, value);
1155 ANI_CHECK_RETURN_IF_EQ(boxedValue, nullptr, ANI_OUT_OF_MEMORY);
1156 [[maybe_unused]] auto setRes = objectArrayHandle->SetRef(posArr, boxedValue);
1157 ASSERT(setRes);
1158 }
1159 return ANI_OK;
1160 }
1161
1162 template <typename T, typename ArrayType>
GetPrimitiveTypeArrayRegion(ani_env * env,ArrayType array,ani_size start,ani_size len,T * buf)1163 static ani_status GetPrimitiveTypeArrayRegion(ani_env *env, ArrayType array, ani_size start, ani_size len, T *buf)
1164 {
1165 ASSERT(array != nullptr);
1166 ANI_CHECK_RETURN_IF_EQ(len != 0 && buf == nullptr, true, ANI_INVALID_ARGS);
1167
1168 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
1169 EtsObject *objArray = s.ToInternalType(static_cast<ani_object>(array));
1170 if (!objArray->IsArrayClass()) {
1171 EtsArrayObject<EtsBoxPrimitive<T>> *escompatArray = EtsArrayObject<EtsBoxPrimitive<T>>::FromEtsObject(objArray);
1172 auto length = escompatArray->GetActualLength();
1173 if (UNLIKELY(start > length || len > (length - start))) {
1174 return ANI_OUT_OF_RANGE;
1175 }
1176 return GetArrayRegion(escompatArray, start, len, buf);
1177 }
1178
1179 EtsArray *internalArray = EtsArray::FromEtsObject(objArray);
1180 auto length = internalArray->GetLength();
1181 if (UNLIKELY(start > length || len > (length - start))) {
1182 return ANI_OUT_OF_RANGE;
1183 }
1184 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1185 auto res = memcpy_s(buf, len * sizeof(T), internalArray->GetData<T>() + start, len * sizeof(T));
1186 if (res != 0) {
1187 UNREACHABLE();
1188 }
1189 return ANI_OK;
1190 }
1191
1192 template <typename T, typename ArrayType>
SetPrimitiveTypeArrayRegion(ani_env * env,ArrayType array,ani_size start,ani_size len,T * buf)1193 static ani_status SetPrimitiveTypeArrayRegion(ani_env *env, ArrayType array, ani_size start, ani_size len, T *buf)
1194 {
1195 ASSERT(array != nullptr);
1196 ANI_CHECK_RETURN_IF_EQ(len != 0 && buf == nullptr, true, ANI_INVALID_ARGS);
1197 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
1198 EtsObject *objArray = s.ToInternalType(static_cast<ani_object>(array));
1199 if (!objArray->IsArrayClass()) {
1200 EtsArrayObject<EtsBoxPrimitive<std::remove_const_t<T>>> *escompatArray =
1201 EtsArrayObject<EtsBoxPrimitive<std::remove_const_t<T>>>::FromEtsObject(objArray);
1202 auto length = escompatArray->GetActualLength();
1203 if (UNLIKELY(start > length || len > (length - start))) {
1204 return ANI_OUT_OF_RANGE;
1205 }
1206 return SetArrayRegion(s, escompatArray, start, len, buf);
1207 }
1208
1209 EtsArray *internalArray = EtsArray::FromEtsObject(objArray);
1210 auto length = internalArray->GetLength();
1211 if (UNLIKELY(start > length || len > (length - start))) {
1212 return ANI_OUT_OF_RANGE;
1213 }
1214 auto data = internalArray->GetData<std::remove_const_t<T>>();
1215 auto dataLen = len * sizeof(T);
1216 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1217 auto res = memcpy_s(data + start, dataLen, buf, dataLen);
1218 if (res != 0) {
1219 UNREACHABLE();
1220 }
1221 return ANI_OK;
1222 }
1223
1224 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetLength(ani_env * env,ani_array array,ani_size * result)1225 NO_UB_SANITIZE static ani_status Array_GetLength(ani_env *env, ani_array array, ani_size *result)
1226 {
1227 ANI_DEBUG_TRACE(env);
1228 CHECK_ENV(env);
1229 CHECK_PTR_ARG(array);
1230 CHECK_PTR_ARG(result);
1231
1232 ScopedManagedCodeFix s(env);
1233 EtsObject *objArray = s.ToInternalType(static_cast<ani_object>(array));
1234 if (!objArray->IsArrayClass()) {
1235 auto escompatArray = EtsArrayObject<EtsObject>::FromEtsObject(objArray);
1236 *result = escompatArray->GetActualLength();
1237 } else {
1238 auto etsArray = reinterpret_cast<EtsArray *>(objArray);
1239 *result = etsArray->GetLength();
1240 }
1241
1242 return ANI_OK;
1243 }
1244
1245 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Boolean(ani_env * env,ani_size length,ani_array_boolean * result)1246 NO_UB_SANITIZE static ani_status Array_New_Boolean(ani_env *env, ani_size length, ani_array_boolean *result)
1247 {
1248 ANI_DEBUG_TRACE(env);
1249 CHECK_ENV(env);
1250 CHECK_PTR_ARG(result);
1251 return NewPrimitiveTypeArray<EtsBoxedBooleanArray>(env, length, result);
1252 }
1253
1254 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Char(ani_env * env,ani_size length,ani_array_char * result)1255 NO_UB_SANITIZE static ani_status Array_New_Char(ani_env *env, ani_size length, ani_array_char *result)
1256 {
1257 ANI_DEBUG_TRACE(env);
1258 CHECK_ENV(env);
1259 CHECK_PTR_ARG(result);
1260 return NewPrimitiveTypeArray<EtsBoxedCharArray>(env, length, result);
1261 }
1262
1263 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Byte(ani_env * env,ani_size length,ani_array_byte * result)1264 NO_UB_SANITIZE static ani_status Array_New_Byte(ani_env *env, ani_size length, ani_array_byte *result)
1265 {
1266 ANI_DEBUG_TRACE(env);
1267 CHECK_ENV(env);
1268 CHECK_PTR_ARG(result);
1269 return NewPrimitiveTypeArray<EtsBoxedByteArray>(env, length, result);
1270 }
1271
1272 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Short(ani_env * env,ani_size length,ani_array_short * result)1273 NO_UB_SANITIZE static ani_status Array_New_Short(ani_env *env, ani_size length, ani_array_short *result)
1274 {
1275 ANI_DEBUG_TRACE(env);
1276 CHECK_ENV(env);
1277 CHECK_PTR_ARG(result);
1278 return NewPrimitiveTypeArray<EtsBoxedShortArray>(env, length, result);
1279 }
1280
1281 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Int(ani_env * env,ani_size length,ani_array_int * result)1282 NO_UB_SANITIZE static ani_status Array_New_Int(ani_env *env, ani_size length, ani_array_int *result)
1283 {
1284 ANI_DEBUG_TRACE(env);
1285 CHECK_ENV(env);
1286 CHECK_PTR_ARG(result);
1287 return NewPrimitiveTypeArray<EtsBoxedIntArray>(env, length, result);
1288 }
1289
1290 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Long(ani_env * env,ani_size length,ani_array_long * result)1291 NO_UB_SANITIZE static ani_status Array_New_Long(ani_env *env, ani_size length, ani_array_long *result)
1292 {
1293 ANI_DEBUG_TRACE(env);
1294 CHECK_ENV(env);
1295 CHECK_PTR_ARG(result);
1296 return NewPrimitiveTypeArray<EtsBoxedLongArray>(env, length, result);
1297 }
1298
1299 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Float(ani_env * env,ani_size length,ani_array_float * result)1300 NO_UB_SANITIZE static ani_status Array_New_Float(ani_env *env, ani_size length, ani_array_float *result)
1301 {
1302 ANI_DEBUG_TRACE(env);
1303 CHECK_ENV(env);
1304 CHECK_PTR_ARG(result);
1305 return NewPrimitiveTypeArray<EtsBoxedFloatArray>(env, length, result);
1306 }
1307
1308 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Double(ani_env * env,ani_size length,ani_array_double * result)1309 NO_UB_SANITIZE static ani_status Array_New_Double(ani_env *env, ani_size length, ani_array_double *result)
1310 {
1311 ANI_DEBUG_TRACE(env);
1312 CHECK_ENV(env);
1313 CHECK_PTR_ARG(result);
1314 return NewPrimitiveTypeArray<EtsBoxedDoubleArray>(env, length, result);
1315 }
1316
1317 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Boolean(ani_env * env,ani_array_boolean array,ani_size offset,ani_size length,ani_boolean * nativeBuffer)1318 NO_UB_SANITIZE static ani_status Array_GetRegion_Boolean(ani_env *env, ani_array_boolean array, ani_size offset,
1319 ani_size length, ani_boolean *nativeBuffer)
1320 {
1321 ANI_DEBUG_TRACE(env);
1322 CHECK_ENV(env);
1323 CHECK_PTR_ARG(array);
1324 CHECK_PTR_ARG(nativeBuffer);
1325 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1326 }
1327
1328 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Char(ani_env * env,ani_array_char array,ani_size offset,ani_size length,ani_char * nativeBuffer)1329 NO_UB_SANITIZE static ani_status Array_GetRegion_Char(ani_env *env, ani_array_char array, ani_size offset,
1330 ani_size length, ani_char *nativeBuffer)
1331 {
1332 ANI_DEBUG_TRACE(env);
1333 CHECK_ENV(env);
1334 CHECK_PTR_ARG(array);
1335 CHECK_PTR_ARG(nativeBuffer);
1336 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1337 }
1338
1339 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Byte(ani_env * env,ani_array_byte array,ani_size offset,ani_size length,ani_byte * nativeBuffer)1340 NO_UB_SANITIZE static ani_status Array_GetRegion_Byte(ani_env *env, ani_array_byte array, ani_size offset,
1341 ani_size length, ani_byte *nativeBuffer)
1342 {
1343 ANI_DEBUG_TRACE(env);
1344 CHECK_ENV(env);
1345 CHECK_PTR_ARG(array);
1346 CHECK_PTR_ARG(nativeBuffer);
1347 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1348 }
1349
1350 // NOLINTNEXTLINE(readability-identifier-naming)
Array_New_Ref(ani_env * env,ani_type type,ani_size length,ani_ref initialElement,ani_array_ref * result)1351 NO_UB_SANITIZE static ani_status Array_New_Ref(ani_env *env, ani_type type, ani_size length, ani_ref initialElement,
1352 ani_array_ref *result)
1353 {
1354 ANI_DEBUG_TRACE(env);
1355 CHECK_ENV(env);
1356 ANI_CHECK_RETURN_IF_GT(length, std::numeric_limits<uint32_t>::max(), ANI_INVALID_ARGS);
1357 CHECK_PTR_ARG(type);
1358 CHECK_PTR_ARG(result);
1359
1360 ScopedManagedCodeFix s(env);
1361 auto *internalArray = EtsArrayObject<EtsObject>::Create(length);
1362 ANI_CHECK_RETURN_IF_EQ(internalArray, nullptr, ANI_OUT_OF_MEMORY);
1363 if (initialElement != nullptr) {
1364 EtsObject *obj = s.ToInternalType(initialElement);
1365 for (ani_size i = 0; i < length; i++) {
1366 internalArray->SetRef(i, obj);
1367 }
1368 }
1369 return s.AddLocalRef(reinterpret_cast<EtsObject *>(internalArray), reinterpret_cast<ani_ref *>(result));
1370 }
1371
1372 // NOLINTNEXTLINE(readability-identifier-naming)
Array_Set_Ref(ani_env * env,ani_array_ref array,ani_size index,ani_ref ref)1373 NO_UB_SANITIZE static ani_status Array_Set_Ref(ani_env *env, ani_array_ref array, ani_size index, ani_ref ref)
1374 {
1375 ANI_DEBUG_TRACE(env);
1376 CHECK_ENV(env);
1377 CHECK_PTR_ARG(array);
1378
1379 ScopedManagedCodeFix s(env);
1380 EtsObject *objArray = s.ToInternalType(reinterpret_cast<ani_object>(array));
1381 EtsObject *obj = s.ToInternalType(ref);
1382 if (!objArray->IsArrayClass()) {
1383 EtsArrayObject<EtsObject> *escompatArray = EtsArrayObject<EtsObject>::FromEtsObject(objArray);
1384 const auto length = escompatArray->GetActualLength();
1385 ANI_CHECK_RETURN_IF_GE(index, length, ANI_OUT_OF_RANGE);
1386 if (!escompatArray->SetRef(index, obj)) {
1387 return ANI_ERROR;
1388 }
1389 } else {
1390 EtsObjectArray *internalArray = EtsObjectArray::FromEtsObject(objArray);
1391 const auto length = internalArray->GetLength();
1392 ANI_CHECK_RETURN_IF_GE(index, length, ANI_OUT_OF_RANGE);
1393
1394 if (obj != nullptr) {
1395 auto componentClass = internalArray->GetClass()->GetComponentType();
1396 if (!obj->IsInstanceOf(componentClass)) {
1397 return ANI_INVALID_TYPE;
1398 }
1399 }
1400 internalArray->Set(static_cast<uint32_t>(index), obj);
1401 }
1402 return ANI_OK;
1403 }
1404
1405 // NOLINTNEXTLINE(readability-identifier-naming)
Array_Get_Ref(ani_env * env,ani_array_ref array,ani_size index,ani_ref * result)1406 NO_UB_SANITIZE static ani_status Array_Get_Ref(ani_env *env, ani_array_ref array, ani_size index, ani_ref *result)
1407 {
1408 ANI_DEBUG_TRACE(env);
1409 CHECK_ENV(env);
1410 CHECK_PTR_ARG(array);
1411 CHECK_PTR_ARG(result);
1412
1413 ScopedManagedCodeFix s(env);
1414 EtsObject *objArray = s.ToInternalType(reinterpret_cast<ani_object>(array));
1415 EtsObject *obj = nullptr;
1416 if (!objArray->IsArrayClass()) {
1417 EtsArrayObject<EtsObject> *escompatArray = EtsArrayObject<EtsObject>::FromEtsObject(objArray);
1418 const auto length = escompatArray->GetActualLength();
1419 ANI_CHECK_RETURN_IF_GE(index, length, ANI_OUT_OF_RANGE);
1420 if (!escompatArray->GetRef(index, &obj)) {
1421 return ANI_ERROR;
1422 }
1423 } else {
1424 EtsObjectArray *internalArray = EtsObjectArray::FromEtsObject(objArray);
1425 const auto length = internalArray->GetLength();
1426 ANI_CHECK_RETURN_IF_GE(index, length, ANI_OUT_OF_RANGE);
1427
1428 obj = internalArray->Get(static_cast<uint32_t>(index));
1429 }
1430 return s.AddLocalRef(obj, result);
1431 }
1432
DoBindNative(ScopedManagedCodeFix & s,const PandaVector<EtsMethod * > & etsMethods,const ani_native_function * functions,ani_size nrFunctions)1433 static ani_status DoBindNative(ScopedManagedCodeFix &s, const PandaVector<EtsMethod *> &etsMethods,
1434 const ani_native_function *functions, ani_size nrFunctions)
1435 {
1436 ASSERT(etsMethods.size() == nrFunctions);
1437
1438 // Get global mutex to guarantee that checked native methods don't changed in other thread.
1439 os::memory::LockHolder lock(s.GetPandaEnv()->GetEtsVM()->GetAniBindMutex());
1440
1441 // Check native methods
1442 for (EtsMethod *method : etsMethods) {
1443 ANI_CHECK_RETURN_IF_EQ(method, nullptr, ANI_NOT_FOUND);
1444
1445 if (!method->IsNative()) {
1446 LOG(ERROR, ANI) << "Registered function isn't native";
1447 return ANI_NOT_FOUND;
1448 }
1449 if (method->IsIntrinsic()) {
1450 LOG(ERROR, ANI) << "Register native method to intrinsic is not supported";
1451 return ANI_ALREADY_BINDED;
1452 }
1453 if (method->IsBoundNativeFunction()) {
1454 return ANI_ALREADY_BINDED;
1455 }
1456 }
1457
1458 // Bind native methods
1459 for (ani_size i = 0; i < nrFunctions; ++i) {
1460 EtsMethod *method = etsMethods[i]; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1461 const void *ptr = functions[i].pointer; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1462 method->RegisterNative(ptr);
1463 }
1464 return ANI_OK;
1465 }
1466
DoBindNativeFunctions(ani_env * env,ani_namespace ns,const ani_native_function * functions,ani_size nrFunctions)1467 static ani_status DoBindNativeFunctions(ani_env *env, ani_namespace ns, const ani_native_function *functions,
1468 ani_size nrFunctions)
1469 {
1470 ANI_CHECK_RETURN_IF_EQ(nrFunctions, 0, ANI_OK);
1471 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
1472 EtsNamespace *etsNs = s.ToInternalType(ns);
1473 PandaVector<EtsMethod *> etsMethods;
1474 etsMethods.reserve(nrFunctions);
1475 for (ani_size i = 0; i < nrFunctions; ++i) {
1476 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1477 if (functions[i].signature == nullptr) {
1478 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1479 etsMethods.push_back(etsNs->GetFunction(functions[i].name, functions[i].signature));
1480 continue;
1481 }
1482 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1483 auto optSignature = ReplaceArrayInSignature(functions[i].signature);
1484 if (!optSignature) {
1485 return ANI_INVALID_ARGS;
1486 }
1487 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1488 etsMethods.push_back(etsNs->GetFunction(functions[i].name, optSignature.value().c_str()));
1489 }
1490 return DoBindNative(s, etsMethods, functions, nrFunctions);
1491 }
1492
1493 // NOLINTNEXTLINE(readability-identifier-naming)
Module_BindNativeFunctions(ani_env * env,ani_module module,const ani_native_function * functions,ani_size nrFunctions)1494 NO_UB_SANITIZE static ani_status Module_BindNativeFunctions(ani_env *env, ani_module module,
1495 const ani_native_function *functions, ani_size nrFunctions)
1496 {
1497 ANI_DEBUG_TRACE(env);
1498 CHECK_ENV(env);
1499 CHECK_PTR_ARG(module);
1500 CHECK_PTR_ARG(functions);
1501
1502 return DoBindNativeFunctions(env, reinterpret_cast<ani_namespace>(module), functions, nrFunctions);
1503 }
1504
1505 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_BindNativeFunctions(ani_env * env,ani_namespace ns,const ani_native_function * functions,ani_size nrFunctions)1506 NO_UB_SANITIZE static ani_status Namespace_BindNativeFunctions(ani_env *env, ani_namespace ns,
1507 const ani_native_function *functions,
1508 ani_size nrFunctions)
1509 {
1510 ANI_DEBUG_TRACE(env);
1511 CHECK_ENV(env);
1512 CHECK_PTR_ARG(ns);
1513 CHECK_PTR_ARG(functions);
1514
1515 return DoBindNativeFunctions(env, ns, functions, nrFunctions);
1516 }
1517
1518 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Short(ani_env * env,ani_array_short array,ani_size offset,ani_size length,ani_short * nativeBuffer)1519 NO_UB_SANITIZE static ani_status Array_GetRegion_Short(ani_env *env, ani_array_short array, ani_size offset,
1520 ani_size length, ani_short *nativeBuffer)
1521 {
1522 ANI_DEBUG_TRACE(env);
1523 CHECK_ENV(env);
1524 CHECK_PTR_ARG(array);
1525 CHECK_PTR_ARG(nativeBuffer);
1526 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1527 }
1528
1529 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Int(ani_env * env,ani_array_int array,ani_size offset,ani_size length,ani_int * nativeBuffer)1530 NO_UB_SANITIZE static ani_status Array_GetRegion_Int(ani_env *env, ani_array_int array, ani_size offset,
1531 ani_size length, ani_int *nativeBuffer)
1532 {
1533 ANI_DEBUG_TRACE(env);
1534 CHECK_ENV(env);
1535 CHECK_PTR_ARG(array);
1536 CHECK_PTR_ARG(nativeBuffer);
1537 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1538 }
1539
1540 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Long(ani_env * env,ani_array_long array,ani_size offset,ani_size length,ani_long * nativeBuffer)1541 NO_UB_SANITIZE static ani_status Array_GetRegion_Long(ani_env *env, ani_array_long array, ani_size offset,
1542 ani_size length, ani_long *nativeBuffer)
1543 {
1544 ANI_DEBUG_TRACE(env);
1545 CHECK_ENV(env);
1546 CHECK_PTR_ARG(array);
1547 CHECK_PTR_ARG(nativeBuffer);
1548 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1549 }
1550
1551 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Float(ani_env * env,ani_array_float array,ani_size offset,ani_size length,ani_float * nativeBuffer)1552 NO_UB_SANITIZE static ani_status Array_GetRegion_Float(ani_env *env, ani_array_float array, ani_size offset,
1553 ani_size length, ani_float *nativeBuffer)
1554 {
1555 ANI_DEBUG_TRACE(env);
1556 CHECK_ENV(env);
1557 CHECK_PTR_ARG(array);
1558 CHECK_PTR_ARG(nativeBuffer);
1559 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1560 }
1561
1562 // NOLINTNEXTLINE(readability-identifier-naming)
Array_GetRegion_Double(ani_env * env,ani_array_double array,ani_size offset,ani_size length,ani_double * nativeBuffer)1563 NO_UB_SANITIZE static ani_status Array_GetRegion_Double(ani_env *env, ani_array_double array, ani_size offset,
1564 ani_size length, ani_double *nativeBuffer)
1565 {
1566 ANI_DEBUG_TRACE(env);
1567 CHECK_ENV(env);
1568 CHECK_PTR_ARG(array);
1569 CHECK_PTR_ARG(nativeBuffer);
1570 return GetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1571 }
1572
1573 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Char(ani_env * env,ani_array_char array,ani_size offset,ani_size length,const ani_char * nativeBuffer)1574 NO_UB_SANITIZE static ani_status Array_SetRegion_Char(ani_env *env, ani_array_char array, ani_size offset,
1575 ani_size length, const ani_char *nativeBuffer)
1576 {
1577 ANI_DEBUG_TRACE(env);
1578 CHECK_ENV(env);
1579 CHECK_PTR_ARG(array);
1580 CHECK_PTR_ARG(nativeBuffer);
1581 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1582 }
1583
1584 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Boolean(ani_env * env,ani_array_boolean array,ani_size offset,ani_size length,const ani_boolean * nativeBuffer)1585 NO_UB_SANITIZE static ani_status Array_SetRegion_Boolean(ani_env *env, ani_array_boolean array, ani_size offset,
1586 ani_size length, const ani_boolean *nativeBuffer)
1587 {
1588 ANI_DEBUG_TRACE(env);
1589 CHECK_ENV(env);
1590 CHECK_PTR_ARG(array);
1591 CHECK_PTR_ARG(nativeBuffer);
1592 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1593 }
1594
1595 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Short(ani_env * env,ani_array_short array,ani_size offset,ani_size length,const ani_short * nativeBuffer)1596 NO_UB_SANITIZE static ani_status Array_SetRegion_Short(ani_env *env, ani_array_short array, ani_size offset,
1597 ani_size length, const ani_short *nativeBuffer)
1598 {
1599 ANI_DEBUG_TRACE(env);
1600 CHECK_ENV(env);
1601 CHECK_PTR_ARG(array);
1602 CHECK_PTR_ARG(nativeBuffer);
1603 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1604 }
1605
1606 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Int(ani_env * env,ani_array_int array,ani_size offset,ani_size length,const ani_int * nativeBuffer)1607 NO_UB_SANITIZE static ani_status Array_SetRegion_Int(ani_env *env, ani_array_int array, ani_size offset,
1608 ani_size length, const ani_int *nativeBuffer)
1609 {
1610 ANI_DEBUG_TRACE(env);
1611 CHECK_ENV(env);
1612 CHECK_PTR_ARG(array);
1613 CHECK_PTR_ARG(nativeBuffer);
1614 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1615 }
1616
1617 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Long(ani_env * env,ani_array_long array,ani_size offset,ani_size length,const ani_long * nativeBuffer)1618 NO_UB_SANITIZE static ani_status Array_SetRegion_Long(ani_env *env, ani_array_long array, ani_size offset,
1619 ani_size length, const ani_long *nativeBuffer)
1620 {
1621 ANI_DEBUG_TRACE(env);
1622 CHECK_ENV(env);
1623 CHECK_PTR_ARG(array);
1624 CHECK_PTR_ARG(nativeBuffer);
1625 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1626 }
1627
1628 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Float(ani_env * env,ani_array_float array,ani_size offset,ani_size length,const ani_float * nativeBuffer)1629 NO_UB_SANITIZE static ani_status Array_SetRegion_Float(ani_env *env, ani_array_float array, ani_size offset,
1630 ani_size length, const ani_float *nativeBuffer)
1631 {
1632 ANI_DEBUG_TRACE(env);
1633 CHECK_ENV(env);
1634 CHECK_PTR_ARG(array);
1635 CHECK_PTR_ARG(nativeBuffer);
1636 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1637 }
1638
1639 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Double(ani_env * env,ani_array_double array,ani_size offset,ani_size length,const ani_double * nativeBuffer)1640 NO_UB_SANITIZE static ani_status Array_SetRegion_Double(ani_env *env, ani_array_double array, ani_size offset,
1641 ani_size length, const ani_double *nativeBuffer)
1642 {
1643 ANI_DEBUG_TRACE(env);
1644 CHECK_ENV(env);
1645 CHECK_PTR_ARG(array);
1646 CHECK_PTR_ARG(nativeBuffer);
1647 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1648 }
1649
1650 // NOLINTNEXTLINE(readability-identifier-naming)
Array_SetRegion_Byte(ani_env * env,ani_array_byte array,ani_size offset,ani_size length,const ani_byte * nativeBuffer)1651 NO_UB_SANITIZE static ani_status Array_SetRegion_Byte(ani_env *env, ani_array_byte array, ani_size offset,
1652 ani_size length, const ani_byte *nativeBuffer)
1653 {
1654 ANI_DEBUG_TRACE(env);
1655 CHECK_ENV(env);
1656 CHECK_PTR_ARG(array);
1657 CHECK_PTR_ARG(nativeBuffer);
1658 return SetPrimitiveTypeArrayRegion(env, array, offset, length, nativeBuffer);
1659 }
1660
1661 // NOLINTNEXTLINE(readability-identifier-naming)
Class_BindNativeMethods(ani_env * env,ani_class cls,const ani_native_function * methods,ani_size nrMethods)1662 NO_UB_SANITIZE static ani_status Class_BindNativeMethods(ani_env *env, ani_class cls,
1663 const ani_native_function *methods, ani_size nrMethods)
1664 {
1665 ANI_DEBUG_TRACE(env);
1666 CHECK_ENV(env);
1667 CHECK_PTR_ARG(cls);
1668 CHECK_PTR_ARG(methods);
1669
1670 ANI_CHECK_RETURN_IF_EQ(nrMethods, 0, ANI_OK);
1671 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
1672 EtsClass *klass = s.ToInternalType(cls);
1673
1674 PandaVector<EtsMethod *> etsMethods;
1675 etsMethods.reserve(nrMethods);
1676 for (ani_size i = 0; i < nrMethods; ++i) {
1677 ani_native_function m = methods[i]; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1678 const char *signature = m.signature;
1679
1680 // CC-OFFNXT(G.FMT.14-CPP) project code style
1681 auto *method = [klass, name = m.name, signature]() -> EtsMethod * {
1682 if (signature == nullptr) {
1683 return klass->GetDirectMethod(name);
1684 }
1685 auto optSignature = ReplaceArrayInSignature(signature);
1686 if (optSignature) {
1687 return klass->GetDirectMethod(name, optSignature.value().c_str());
1688 }
1689 return nullptr;
1690 }();
1691 etsMethods.push_back(method);
1692 }
1693 return DoBindNative(s, etsMethods, methods, nrMethods);
1694 }
1695
1696 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_Delete(ani_env * env,ani_ref ref)1697 NO_UB_SANITIZE static ani_status Reference_Delete(ani_env *env, ani_ref ref)
1698 {
1699 ANI_DEBUG_TRACE(env);
1700 CHECK_ENV(env);
1701
1702 ScopedManagedCodeFix s(env);
1703 return s.DelLocalRef(ref);
1704 }
1705
1706 template <typename T>
SetVariableValue(ani_env * env,ani_variable variable,T value)1707 static ani_status SetVariableValue(ani_env *env, ani_variable variable, T value)
1708 {
1709 CHECK_ENV(env);
1710 CHECK_PTR_ARG(variable);
1711
1712 ScopedManagedCodeFix s(env);
1713 EtsVariable *etsVariable = ToInternalVariable(variable);
1714 EtsField *etsField = etsVariable->AsField();
1715 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
1716
1717 EtsClass *cls = etsField->GetDeclaringClass();
1718 ani_status status = InitializeClass(s, cls);
1719 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1720
1721 static constexpr auto IS_REF = std::is_same_v<T, ani_ref>;
1722 if constexpr (IS_REF) {
1723 EtsObject *object = s.ToInternalType(value);
1724 cls->SetStaticFieldObject(etsField, object);
1725 } else {
1726 cls->SetStaticFieldPrimitive<T>(etsField, value);
1727 }
1728 return ANI_OK;
1729 }
1730
1731 // NOLINTNEXTLINE(readability-identifier-naming)
FunctionalObject_Call(ani_env * env,ani_fn_object fn,ani_size argc,ani_ref * argv,ani_ref * result)1732 NO_UB_SANITIZE static ani_status FunctionalObject_Call(ani_env *env, ani_fn_object fn, ani_size argc, ani_ref *argv,
1733 ani_ref *result)
1734 {
1735 ANI_DEBUG_TRACE(env);
1736 CHECK_ENV(env);
1737 CHECK_PTR_ARG(fn);
1738 if (argc != 0) {
1739 CHECK_PTR_ARG(argv);
1740 }
1741 CHECK_PTR_ARG(result);
1742
1743 ANI_CHECK_RETURN_IF_GT(argc, STD_CORE_FUNCTION_MAX_ARITY, ANI_INVALID_ARGS);
1744
1745 ani_status status = ANI_OK;
1746 ScopedManagedCodeFix s(env);
1747 EtsObject *etsFn = s.ToInternalType(fn);
1748 EtsClass *etsCls = etsFn->GetClass();
1749
1750 ANI_CHECK_RETURN_IF_EQ(etsCls->IsFunction(), false, ANI_INVALID_TYPE);
1751
1752 EtsMethod *method = nullptr;
1753 PandaStringStream methodName;
1754 methodName << STD_CORE_FUNCTION_INVOKE_PREFIX << argc;
1755 status = DoGetClassMethod<false>(etsCls, methodName.str().c_str(), nullptr, &method);
1756 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1757
1758 ArgVector<Value> args = {};
1759 args.reserve(argc + 1);
1760 args.emplace_back(s.ToInternalType(fn)->GetCoreType());
1761 for (ani_size i = 0; i < argc; ++i) {
1762 // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-pointer-arithmetic)
1763 auto *internalType = s.ToInternalType(argv[i]);
1764 args.emplace_back(internalType != nullptr ? internalType->GetCoreType() : nullptr);
1765 }
1766
1767 EtsValue res {};
1768 status = method->Invoke(s, args.data(), &res);
1769 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1770
1771 *result = res.GetAs<ani_ref>();
1772 return status;
1773 }
1774
1775 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Boolean(ani_env * env,ani_variable variable,ani_boolean value)1776 NO_UB_SANITIZE static ani_status Variable_SetValue_Boolean(ani_env *env, ani_variable variable, ani_boolean value)
1777 {
1778 ANI_DEBUG_TRACE(env);
1779 return SetVariableValue<ani_boolean>(env, variable, value);
1780 }
1781
1782 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Char(ani_env * env,ani_variable variable,ani_char value)1783 NO_UB_SANITIZE static ani_status Variable_SetValue_Char(ani_env *env, ani_variable variable, ani_char value)
1784 {
1785 ANI_DEBUG_TRACE(env);
1786 return SetVariableValue<ani_char>(env, variable, value);
1787 }
1788
1789 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Byte(ani_env * env,ani_variable variable,ani_byte value)1790 NO_UB_SANITIZE static ani_status Variable_SetValue_Byte(ani_env *env, ani_variable variable, ani_byte value)
1791 {
1792 ANI_DEBUG_TRACE(env);
1793 return SetVariableValue<ani_byte>(env, variable, value);
1794 }
1795
1796 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Short(ani_env * env,ani_variable variable,ani_short value)1797 NO_UB_SANITIZE static ani_status Variable_SetValue_Short(ani_env *env, ani_variable variable, ani_short value)
1798 {
1799 ANI_DEBUG_TRACE(env);
1800 return SetVariableValue<EtsShort>(env, variable, value);
1801 }
1802
1803 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Int(ani_env * env,ani_variable variable,ani_int value)1804 NO_UB_SANITIZE static ani_status Variable_SetValue_Int(ani_env *env, ani_variable variable, ani_int value)
1805 {
1806 ANI_DEBUG_TRACE(env);
1807 return SetVariableValue<EtsInt>(env, variable, value);
1808 }
1809
1810 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Long(ani_env * env,ani_variable variable,ani_long value)1811 NO_UB_SANITIZE static ani_status Variable_SetValue_Long(ani_env *env, ani_variable variable, ani_long value)
1812 {
1813 ANI_DEBUG_TRACE(env);
1814 return SetVariableValue<EtsLong>(env, variable, value);
1815 }
1816
1817 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Float(ani_env * env,ani_variable variable,ani_float value)1818 NO_UB_SANITIZE static ani_status Variable_SetValue_Float(ani_env *env, ani_variable variable, ani_float value)
1819 {
1820 ANI_DEBUG_TRACE(env);
1821 return SetVariableValue<EtsFloat>(env, variable, value);
1822 }
1823
1824 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Double(ani_env * env,ani_variable variable,ani_double value)1825 NO_UB_SANITIZE static ani_status Variable_SetValue_Double(ani_env *env, ani_variable variable, ani_double value)
1826 {
1827 ANI_DEBUG_TRACE(env);
1828 return SetVariableValue<ani_double>(env, variable, value);
1829 }
1830
1831 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_SetValue_Ref(ani_env * env,ani_variable variable,ani_ref value)1832 NO_UB_SANITIZE static ani_status Variable_SetValue_Ref(ani_env *env, ani_variable variable, ani_ref value)
1833 {
1834 ANI_DEBUG_TRACE(env);
1835 CHECK_PTR_ARG(value);
1836 return SetVariableValue<ani_ref>(env, variable, value);
1837 }
1838
1839 template <bool IS_STATIC_FIELD>
DoGetField(ScopedManagedCodeFix & s,ani_class cls,const char * name,EtsField ** result)1840 static ani_status DoGetField(ScopedManagedCodeFix &s, ani_class cls, const char *name, EtsField **result)
1841 {
1842 EtsClass *klass = s.ToInternalType(cls);
1843
1844 EtsField *field = [&]() {
1845 if constexpr (IS_STATIC_FIELD) {
1846 return klass->GetStaticFieldIDByName(name, nullptr);
1847 } else {
1848 EtsField *foundField = klass->GetFieldIDByName(name, nullptr);
1849 if (UNLIKELY(foundField == nullptr)) {
1850 // NOTE: Need to look for class property implemented from interface
1851 auto interfaceFieldName = PandaString("<property>") + name;
1852 foundField = klass->GetFieldIDByName(interfaceFieldName.c_str(), nullptr);
1853 }
1854 return foundField;
1855 }
1856 }();
1857 ANI_CHECK_RETURN_IF_EQ(field, nullptr, ANI_NOT_FOUND);
1858
1859 *result = field;
1860 return ANI_OK;
1861 }
1862
1863 template <bool IS_STATIC_FIELD>
DoGetField(ani_env * env,ani_class cls,const char * name,EtsField ** result)1864 static ani_status DoGetField(ani_env *env, ani_class cls, const char *name, EtsField **result)
1865 {
1866 ScopedManagedCodeFix s(env);
1867 return DoGetField<IS_STATIC_FIELD>(s, cls, name, result);
1868 }
1869
1870 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindField(ani_env * env,ani_class cls,const char * name,ani_field * result)1871 NO_UB_SANITIZE static ani_status Class_FindField(ani_env *env, ani_class cls, const char *name, ani_field *result)
1872 {
1873 ANI_DEBUG_TRACE(env);
1874 CHECK_ENV(env);
1875 CHECK_PTR_ARG(cls);
1876 CHECK_PTR_ARG(name);
1877 CHECK_PTR_ARG(result);
1878
1879 EtsField *field = nullptr;
1880 ani_status status = DoGetField<false>(env, cls, name, &field);
1881 if (UNLIKELY(status != ANI_OK)) {
1882 return status;
1883 }
1884 *result = ToAniField(field);
1885 return ANI_OK;
1886 }
1887
1888 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindStaticField(ani_env * env,ani_class cls,const char * name,ani_static_field * result)1889 NO_UB_SANITIZE static ani_status Class_FindStaticField(ani_env *env, ani_class cls, const char *name,
1890 ani_static_field *result)
1891 {
1892 ANI_DEBUG_TRACE(env);
1893 CHECK_ENV(env);
1894 CHECK_PTR_ARG(cls);
1895 CHECK_PTR_ARG(name);
1896 CHECK_PTR_ARG(result);
1897
1898 EtsField *field = nullptr;
1899 ani_status status = DoGetField<true>(env, cls, name, &field);
1900 if (UNLIKELY(status != ANI_OK)) {
1901 return status;
1902 }
1903 *result = ToAniStaticField(field);
1904 return ANI_OK;
1905 }
1906
1907 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindMethod(ani_env * env,ani_class cls,const char * name,const char * signature,ani_method * result)1908 NO_UB_SANITIZE static ani_status Class_FindMethod(ani_env *env, ani_class cls, const char *name, const char *signature,
1909 ani_method *result)
1910 {
1911 ANI_DEBUG_TRACE(env);
1912 CHECK_ENV(env);
1913 CHECK_PTR_ARG(cls);
1914 CHECK_PTR_ARG(name);
1915 CHECK_PTR_ARG(result);
1916
1917 EtsMethod *method = nullptr;
1918 ani_status status = GetClassMethod<false>(env, cls, name, signature, &method);
1919 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1920 *result = ToAniMethod(method);
1921 return ANI_OK;
1922 }
1923
1924 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindStaticMethod(ani_env * env,ani_class cls,const char * name,const char * signature,ani_static_method * result)1925 NO_UB_SANITIZE static ani_status Class_FindStaticMethod(ani_env *env, ani_class cls, const char *name,
1926 const char *signature, ani_static_method *result)
1927 {
1928 ANI_DEBUG_TRACE(env);
1929 CHECK_ENV(env);
1930 CHECK_PTR_ARG(cls);
1931 CHECK_PTR_ARG(name);
1932 CHECK_PTR_ARG(result);
1933
1934 EtsMethod *method = nullptr;
1935 ani_status status = GetClassMethod<true>(env, cls, name, signature, &method);
1936 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1937 *result = ToAniStaticMethod(method);
1938 return ANI_OK;
1939 }
1940
1941 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindIterator(ani_env * env,ani_class cls,ani_method * result)1942 NO_UB_SANITIZE static ani_status Class_FindIterator(ani_env *env, ani_class cls, ani_method *result)
1943 {
1944 ANI_DEBUG_TRACE(env);
1945 CHECK_ENV(env);
1946 CHECK_PTR_ARG(cls);
1947 CHECK_PTR_ARG(result);
1948
1949 EtsMethod *method = nullptr;
1950 ani_status status = GetClassMethod<false>(env, cls, "$_iterator", nullptr, &method);
1951 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
1952 *result = ToAniMethod(method);
1953 return ANI_OK;
1954 }
1955
1956 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Boolean(ani_env * env,ani_class cls,ani_static_field field,ani_boolean * result)1957 NO_UB_SANITIZE static ani_status Class_GetStaticField_Boolean(ani_env *env, ani_class cls, ani_static_field field,
1958 ani_boolean *result)
1959 {
1960 ANI_DEBUG_TRACE(env);
1961
1962 return ClassGetStaticField<ani_boolean>(env, cls, field, result);
1963 }
1964
1965 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Char(ani_env * env,ani_class cls,ani_static_field field,ani_char * result)1966 NO_UB_SANITIZE static ani_status Class_GetStaticField_Char(ani_env *env, ani_class cls, ani_static_field field,
1967 ani_char *result)
1968 {
1969 ANI_DEBUG_TRACE(env);
1970
1971 return ClassGetStaticField<ani_char>(env, cls, field, result);
1972 }
1973
1974 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Byte(ani_env * env,ani_class cls,ani_static_field field,ani_byte * result)1975 NO_UB_SANITIZE static ani_status Class_GetStaticField_Byte(ani_env *env, ani_class cls, ani_static_field field,
1976 ani_byte *result)
1977 {
1978 ANI_DEBUG_TRACE(env);
1979
1980 return ClassGetStaticField<ani_byte>(env, cls, field, result);
1981 }
1982
1983 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Short(ani_env * env,ani_class cls,ani_static_field field,ani_short * result)1984 NO_UB_SANITIZE static ani_status Class_GetStaticField_Short(ani_env *env, ani_class cls, ani_static_field field,
1985 ani_short *result)
1986 {
1987 ANI_DEBUG_TRACE(env);
1988
1989 return ClassGetStaticField<ani_short>(env, cls, field, result);
1990 }
1991
1992 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Int(ani_env * env,ani_class cls,ani_static_field field,ani_int * result)1993 NO_UB_SANITIZE static ani_status Class_GetStaticField_Int(ani_env *env, ani_class cls, ani_static_field field,
1994 ani_int *result)
1995 {
1996 ANI_DEBUG_TRACE(env);
1997
1998 return ClassGetStaticField<ani_int>(env, cls, field, result);
1999 }
2000
2001 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Long(ani_env * env,ani_class cls,ani_static_field field,ani_long * result)2002 NO_UB_SANITIZE static ani_status Class_GetStaticField_Long(ani_env *env, ani_class cls, ani_static_field field,
2003 ani_long *result)
2004 {
2005 ANI_DEBUG_TRACE(env);
2006
2007 return ClassGetStaticField<ani_long>(env, cls, field, result);
2008 }
2009
2010 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Float(ani_env * env,ani_class cls,ani_static_field field,ani_float * result)2011 NO_UB_SANITIZE static ani_status Class_GetStaticField_Float(ani_env *env, ani_class cls, ani_static_field field,
2012 ani_float *result)
2013 {
2014 ANI_DEBUG_TRACE(env);
2015
2016 return ClassGetStaticField<ani_float>(env, cls, field, result);
2017 }
2018
2019 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Double(ani_env * env,ani_class cls,ani_static_field field,ani_double * result)2020 NO_UB_SANITIZE static ani_status Class_GetStaticField_Double(ani_env *env, ani_class cls, ani_static_field field,
2021 ani_double *result)
2022 {
2023 ANI_DEBUG_TRACE(env);
2024
2025 return ClassGetStaticField<ani_double>(env, cls, field, result);
2026 }
2027
2028 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticField_Ref(ani_env * env,ani_class cls,ani_static_field field,ani_ref * result)2029 NO_UB_SANITIZE static ani_status Class_GetStaticField_Ref(ani_env *env, ani_class cls, ani_static_field field,
2030 ani_ref *result)
2031 {
2032 ANI_DEBUG_TRACE(env);
2033 CHECK_ENV(env);
2034 CHECK_PTR_ARG(cls);
2035 CHECK_PTR_ARG(field);
2036 CHECK_PTR_ARG(result);
2037
2038 EtsField *etsField = ToInternalField(field);
2039 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2040
2041 ScopedManagedCodeFix s(env);
2042 EtsClass *etsClass = s.ToInternalType(cls);
2043 ani_status status = InitializeClass(s, etsClass);
2044 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
2045
2046 auto *etsRes = etsClass->GetStaticFieldObject(etsField);
2047 return s.AddLocalRef(etsRes, result);
2048 }
2049
2050 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Boolean(ani_env * env,ani_class cls,ani_static_field field,ani_boolean value)2051 NO_UB_SANITIZE static ani_status Class_SetStaticField_Boolean(ani_env *env, ani_class cls, ani_static_field field,
2052 ani_boolean value)
2053 {
2054 ANI_DEBUG_TRACE(env);
2055
2056 return ClassSetStaticField(env, cls, field, value);
2057 }
2058
2059 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Char(ani_env * env,ani_class cls,ani_static_field field,ani_char value)2060 NO_UB_SANITIZE static ani_status Class_SetStaticField_Char(ani_env *env, ani_class cls, ani_static_field field,
2061 ani_char value)
2062 {
2063 ANI_DEBUG_TRACE(env);
2064
2065 return ClassSetStaticField(env, cls, field, value);
2066 }
2067
2068 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Byte(ani_env * env,ani_class cls,ani_static_field field,ani_byte value)2069 NO_UB_SANITIZE static ani_status Class_SetStaticField_Byte(ani_env *env, ani_class cls, ani_static_field field,
2070 ani_byte value)
2071 {
2072 ANI_DEBUG_TRACE(env);
2073
2074 return ClassSetStaticField(env, cls, field, value);
2075 }
2076
2077 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Short(ani_env * env,ani_class cls,ani_static_field field,ani_short value)2078 NO_UB_SANITIZE static ani_status Class_SetStaticField_Short(ani_env *env, ani_class cls, ani_static_field field,
2079 ani_short value)
2080 {
2081 ANI_DEBUG_TRACE(env);
2082
2083 return ClassSetStaticField(env, cls, field, value);
2084 }
2085
2086 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Int(ani_env * env,ani_class cls,ani_static_field field,ani_int value)2087 NO_UB_SANITIZE static ani_status Class_SetStaticField_Int(ani_env *env, ani_class cls, ani_static_field field,
2088 ani_int value)
2089 {
2090 ANI_DEBUG_TRACE(env);
2091
2092 return ClassSetStaticField(env, cls, field, value);
2093 }
2094
2095 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Long(ani_env * env,ani_class cls,ani_static_field field,ani_long value)2096 NO_UB_SANITIZE static ani_status Class_SetStaticField_Long(ani_env *env, ani_class cls, ani_static_field field,
2097 ani_long value)
2098 {
2099 ANI_DEBUG_TRACE(env);
2100
2101 return ClassSetStaticField(env, cls, field, value);
2102 }
2103
2104 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Float(ani_env * env,ani_class cls,ani_static_field field,ani_float value)2105 NO_UB_SANITIZE static ani_status Class_SetStaticField_Float(ani_env *env, ani_class cls, ani_static_field field,
2106 ani_float value)
2107 {
2108 ANI_DEBUG_TRACE(env);
2109
2110 return ClassSetStaticField(env, cls, field, value);
2111 }
2112
2113 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Double(ani_env * env,ani_class cls,ani_static_field field,ani_double value)2114 NO_UB_SANITIZE static ani_status Class_SetStaticField_Double(ani_env *env, ani_class cls, ani_static_field field,
2115 ani_double value)
2116 {
2117 ANI_DEBUG_TRACE(env);
2118
2119 return ClassSetStaticField(env, cls, field, value);
2120 }
2121
2122 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticField_Ref(ani_env * env,ani_class cls,ani_static_field field,ani_ref value)2123 NO_UB_SANITIZE static ani_status Class_SetStaticField_Ref(ani_env *env, ani_class cls, ani_static_field field,
2124 ani_ref value)
2125 {
2126 ANI_DEBUG_TRACE(env);
2127 CHECK_ENV(env);
2128 CHECK_PTR_ARG(cls);
2129 CHECK_PTR_ARG(field);
2130 CHECK_PTR_ARG(value);
2131
2132 EtsField *etsField = ToInternalField(field);
2133 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2134
2135 ScopedManagedCodeFix s(env);
2136 EtsClass *etsClass = s.ToInternalType(cls);
2137 ani_status status = InitializeClass(s, etsClass);
2138 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
2139
2140 EtsObject *etsValue = s.ToInternalType(value);
2141 etsClass->SetStaticFieldObject(etsField, etsValue);
2142 return ANI_OK;
2143 }
2144
2145 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Boolean(ani_env * env,ani_class cls,const char * name,ani_boolean * result)2146 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Boolean(ani_env *env, ani_class cls, const char *name,
2147 ani_boolean *result)
2148 {
2149 ANI_DEBUG_TRACE(env);
2150
2151 return ClassGetStaticFieldByName(env, cls, name, result);
2152 }
2153
2154 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Char(ani_env * env,ani_class cls,const char * name,ani_char * result)2155 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Char(ani_env *env, ani_class cls, const char *name,
2156 ani_char *result)
2157 {
2158 ANI_DEBUG_TRACE(env);
2159
2160 return ClassGetStaticFieldByName(env, cls, name, result);
2161 }
2162
2163 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Byte(ani_env * env,ani_class cls,const char * name,ani_byte * result)2164 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Byte(ani_env *env, ani_class cls, const char *name,
2165 ani_byte *result)
2166 {
2167 ANI_DEBUG_TRACE(env);
2168
2169 return ClassGetStaticFieldByName(env, cls, name, result);
2170 }
2171
2172 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Short(ani_env * env,ani_class cls,const char * name,ani_short * result)2173 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Short(ani_env *env, ani_class cls, const char *name,
2174 ani_short *result)
2175 {
2176 ANI_DEBUG_TRACE(env);
2177
2178 return ClassGetStaticFieldByName(env, cls, name, result);
2179 }
2180
2181 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Int(ani_env * env,ani_class cls,const char * name,ani_int * result)2182 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Int(ani_env *env, ani_class cls, const char *name,
2183 ani_int *result)
2184 {
2185 ANI_DEBUG_TRACE(env);
2186
2187 return ClassGetStaticFieldByName(env, cls, name, result);
2188 }
2189
2190 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Long(ani_env * env,ani_class cls,const char * name,ani_long * result)2191 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Long(ani_env *env, ani_class cls, const char *name,
2192 ani_long *result)
2193 {
2194 ANI_DEBUG_TRACE(env);
2195
2196 return ClassGetStaticFieldByName(env, cls, name, result);
2197 }
2198
2199 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Float(ani_env * env,ani_class cls,const char * name,ani_float * result)2200 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Float(ani_env *env, ani_class cls, const char *name,
2201 ani_float *result)
2202 {
2203 ANI_DEBUG_TRACE(env);
2204
2205 return ClassGetStaticFieldByName(env, cls, name, result);
2206 }
2207
2208 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Double(ani_env * env,ani_class cls,const char * name,ani_double * result)2209 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Double(ani_env *env, ani_class cls, const char *name,
2210 ani_double *result)
2211 {
2212 ANI_DEBUG_TRACE(env);
2213
2214 return ClassGetStaticFieldByName(env, cls, name, result);
2215 }
2216
2217 // NOLINTNEXTLINE(readability-identifier-naming)
Class_GetStaticFieldByName_Ref(ani_env * env,ani_class cls,const char * name,ani_ref * result)2218 NO_UB_SANITIZE static ani_status Class_GetStaticFieldByName_Ref(ani_env *env, ani_class cls, const char *name,
2219 ani_ref *result)
2220 {
2221 ANI_DEBUG_TRACE(env);
2222 CHECK_ENV(env);
2223 CHECK_PTR_ARG(cls);
2224 CHECK_PTR_ARG(name);
2225 CHECK_PTR_ARG(result);
2226
2227 ScopedManagedCodeFix s(env);
2228 EtsClass *klass = s.ToInternalType(cls);
2229
2230 EtsField *etsField = klass->GetStaticFieldIDByName(name, nullptr);
2231 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
2232 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2233
2234 ani_status status = InitializeClass(s, klass);
2235 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
2236
2237 EtsObject *etsRes = klass->GetStaticFieldObject(etsField);
2238 return s.AddLocalRef(etsRes, result);
2239 }
2240
2241 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Boolean(ani_env * env,ani_class cls,const char * name,ani_boolean value)2242 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Boolean(ani_env *env, ani_class cls, const char *name,
2243 ani_boolean value)
2244 {
2245 ANI_DEBUG_TRACE(env);
2246
2247 return ClassSetStaticFieldByName(env, cls, name, value);
2248 }
2249
2250 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Char(ani_env * env,ani_class cls,const char * name,ani_char value)2251 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Char(ani_env *env, ani_class cls, const char *name,
2252 ani_char value)
2253 {
2254 ANI_DEBUG_TRACE(env);
2255
2256 return ClassSetStaticFieldByName(env, cls, name, value);
2257 }
2258
2259 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Byte(ani_env * env,ani_class cls,const char * name,ani_byte value)2260 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Byte(ani_env *env, ani_class cls, const char *name,
2261 ani_byte value)
2262 {
2263 ANI_DEBUG_TRACE(env);
2264
2265 return ClassSetStaticFieldByName(env, cls, name, value);
2266 }
2267
2268 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Short(ani_env * env,ani_class cls,const char * name,ani_short value)2269 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Short(ani_env *env, ani_class cls, const char *name,
2270 ani_short value)
2271 {
2272 ANI_DEBUG_TRACE(env);
2273
2274 return ClassSetStaticFieldByName(env, cls, name, value);
2275 }
2276
2277 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Int(ani_env * env,ani_class cls,const char * name,ani_int value)2278 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Int(ani_env *env, ani_class cls, const char *name,
2279 ani_int value)
2280 {
2281 ANI_DEBUG_TRACE(env);
2282
2283 return ClassSetStaticFieldByName(env, cls, name, value);
2284 }
2285
2286 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Long(ani_env * env,ani_class cls,const char * name,ani_long value)2287 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Long(ani_env *env, ani_class cls, const char *name,
2288 ani_long value)
2289 {
2290 ANI_DEBUG_TRACE(env);
2291
2292 return ClassSetStaticFieldByName(env, cls, name, value);
2293 }
2294 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Float(ani_env * env,ani_class cls,const char * name,ani_float value)2295 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Float(ani_env *env, ani_class cls, const char *name,
2296 ani_float value)
2297 {
2298 ANI_DEBUG_TRACE(env);
2299
2300 return ClassSetStaticFieldByName(env, cls, name, value);
2301 }
2302
2303 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Double(ani_env * env,ani_class cls,const char * name,ani_double value)2304 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Double(ani_env *env, ani_class cls, const char *name,
2305 ani_double value)
2306 {
2307 ANI_DEBUG_TRACE(env);
2308
2309 return ClassSetStaticFieldByName(env, cls, name, value);
2310 }
2311 // NOLINTNEXTLINE(readability-identifier-naming)
Class_SetStaticFieldByName_Ref(ani_env * env,ani_class cls,const char * name,ani_ref value)2312 NO_UB_SANITIZE static ani_status Class_SetStaticFieldByName_Ref(ani_env *env, ani_class cls, const char *name,
2313 ani_ref value)
2314 {
2315 ANI_DEBUG_TRACE(env);
2316 CHECK_ENV(env);
2317 CHECK_PTR_ARG(cls);
2318 CHECK_PTR_ARG(name);
2319 CHECK_PTR_ARG(value);
2320
2321 ScopedManagedCodeFix s(env);
2322 EtsClass *klass = s.ToInternalType(cls);
2323
2324 EtsField *etsField = klass->GetStaticFieldIDByName(name, nullptr);
2325 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
2326 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2327
2328 ani_status status = InitializeClass(s, klass);
2329 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
2330
2331 EtsObject *etsValue = s.ToInternalType(value);
2332 klass->SetStaticFieldObject(etsField, etsValue);
2333 return ANI_OK;
2334 }
2335
2336 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindSetter(ani_env * env,ani_class cls,const char * name,ani_method * result)2337 ani_status Class_FindSetter(ani_env *env, ani_class cls, const char *name, ani_method *result)
2338 {
2339 PandaString setterName("<set>");
2340 setterName += name;
2341 return Class_FindMethod(env, cls, setterName.c_str(), nullptr, result);
2342 }
2343
2344 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindGetter(ani_env * env,ani_class cls,const char * name,ani_method * result)2345 ani_status Class_FindGetter(ani_env *env, ani_class cls, const char *name, ani_method *result)
2346 {
2347 PandaString getterName("<get>");
2348 getterName += name;
2349 return Class_FindMethod(env, cls, getterName.c_str(), nullptr, result);
2350 }
2351
2352 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindIndexableSetter(ani_env * env,ani_class cls,const char * signature,ani_method * result)2353 ani_status Class_FindIndexableSetter(ani_env *env, ani_class cls, const char *signature, ani_method *result)
2354 {
2355 return Class_FindMethod(env, cls, "$_set", signature, result);
2356 }
2357
2358 // NOLINTNEXTLINE(readability-identifier-naming)
Class_FindIndexableGetter(ani_env * env,ani_class cls,const char * signature,ani_method * result)2359 ani_status Class_FindIndexableGetter(ani_env *env, ani_class cls, const char *signature, ani_method *result)
2360 {
2361 return Class_FindMethod(env, cls, "$_get", signature, result);
2362 }
2363
2364 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Boolean_V(ani_env * env,ani_class cls,ani_static_method method,ani_boolean * result,va_list args)2365 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Boolean_V(ani_env *env, ani_class cls, ani_static_method method,
2366 ani_boolean *result, va_list args)
2367 {
2368 ANI_DEBUG_TRACE(env);
2369 CHECK_ENV(env);
2370 CHECK_PTR_ARG(cls);
2371 CHECK_PTR_ARG(method);
2372 CHECK_PTR_ARG(result);
2373
2374 CheckStaticMethodReturnType(method, EtsType::BOOLEAN);
2375 return GeneralMethodCall<EtsBoolean>(env, nullptr, method, result, args);
2376 }
2377
2378 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Boolean(ani_env * env,ani_class cls,ani_static_method method,ani_boolean * result,...)2379 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Boolean(ani_env *env, ani_class cls, ani_static_method method,
2380 ani_boolean *result, ...)
2381 {
2382 ANI_DEBUG_TRACE(env);
2383
2384 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2385 va_start(args, result);
2386 ani_status status = Class_CallStaticMethod_Boolean_V(env, cls, method, result, args);
2387 va_end(args);
2388 return status;
2389 }
2390
2391 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Boolean_A(ani_env * env,ani_class cls,ani_static_method method,ani_boolean * result,const ani_value * args)2392 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Boolean_A(ani_env *env, ani_class cls, ani_static_method method,
2393 ani_boolean *result, const ani_value *args)
2394 {
2395 ANI_DEBUG_TRACE(env);
2396 CHECK_ENV(env);
2397 CHECK_PTR_ARG(cls);
2398 CHECK_PTR_ARG(method);
2399 CHECK_PTR_ARG(result);
2400 CHECK_PTR_ARG(args);
2401
2402 CheckStaticMethodReturnType(method, EtsType::BOOLEAN);
2403 return GeneralMethodCall<EtsBoolean>(env, nullptr, method, result, args);
2404 }
2405
2406 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Char_V(ani_env * env,ani_class cls,ani_static_method method,ani_char * result,va_list args)2407 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Char_V(ani_env *env, ani_class cls, ani_static_method method,
2408 ani_char *result, va_list args)
2409 {
2410 ANI_DEBUG_TRACE(env);
2411 CHECK_ENV(env);
2412 CHECK_PTR_ARG(cls);
2413 CHECK_PTR_ARG(method);
2414 CHECK_PTR_ARG(result);
2415
2416 CheckStaticMethodReturnType(method, EtsType::CHAR);
2417 return GeneralMethodCall<EtsChar>(env, nullptr, method, result, args);
2418 }
2419
2420 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Char(ani_env * env,ani_class cls,ani_static_method method,ani_char * result,...)2421 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Char(ani_env *env, ani_class cls, ani_static_method method,
2422 ani_char *result, ...)
2423 {
2424 ANI_DEBUG_TRACE(env);
2425
2426 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2427 va_start(args, result);
2428 ani_status status = Class_CallStaticMethod_Char_V(env, cls, method, result, args);
2429 va_end(args);
2430 return status;
2431 }
2432
2433 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Char_A(ani_env * env,ani_class cls,ani_static_method method,ani_char * result,const ani_value * args)2434 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Char_A(ani_env *env, ani_class cls, ani_static_method method,
2435 ani_char *result, const ani_value *args)
2436 {
2437 ANI_DEBUG_TRACE(env);
2438 CHECK_ENV(env);
2439 CHECK_PTR_ARG(cls);
2440 CHECK_PTR_ARG(method);
2441 CHECK_PTR_ARG(result);
2442 CHECK_PTR_ARG(args);
2443
2444 CheckStaticMethodReturnType(method, EtsType::CHAR);
2445 return GeneralMethodCall<EtsChar>(env, nullptr, method, result, args);
2446 }
2447
2448 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Byte_V(ani_env * env,ani_class cls,ani_static_method method,ani_byte * result,va_list args)2449 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Byte_V(ani_env *env, ani_class cls, ani_static_method method,
2450 ani_byte *result, va_list args)
2451 {
2452 ANI_DEBUG_TRACE(env);
2453 CHECK_ENV(env);
2454 CHECK_PTR_ARG(cls);
2455 CHECK_PTR_ARG(method);
2456 CHECK_PTR_ARG(result);
2457
2458 CheckStaticMethodReturnType(method, EtsType::BYTE);
2459 return GeneralMethodCall<EtsByte>(env, nullptr, method, result, args);
2460 }
2461
2462 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Byte(ani_env * env,ani_class cls,ani_static_method method,ani_byte * result,...)2463 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Byte(ani_env *env, ani_class cls, ani_static_method method,
2464 ani_byte *result, ...)
2465 {
2466 ANI_DEBUG_TRACE(env);
2467
2468 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2469 va_start(args, result);
2470 ani_status status = Class_CallStaticMethod_Byte_V(env, cls, method, result, args);
2471 va_end(args);
2472 return status;
2473 }
2474
2475 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Byte_A(ani_env * env,ani_class cls,ani_static_method method,ani_byte * result,const ani_value * args)2476 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Byte_A(ani_env *env, ani_class cls, ani_static_method method,
2477 ani_byte *result, const ani_value *args)
2478 {
2479 ANI_DEBUG_TRACE(env);
2480 CHECK_ENV(env);
2481 CHECK_PTR_ARG(cls);
2482 CHECK_PTR_ARG(method);
2483 CHECK_PTR_ARG(result);
2484 CHECK_PTR_ARG(args);
2485
2486 CheckStaticMethodReturnType(method, EtsType::BYTE);
2487 return GeneralMethodCall<EtsByte>(env, nullptr, method, result, args);
2488 }
2489
2490 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Short_V(ani_env * env,ani_class cls,ani_static_method method,ani_short * result,va_list args)2491 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Short_V(ani_env *env, ani_class cls, ani_static_method method,
2492 ani_short *result, va_list args)
2493 {
2494 ANI_DEBUG_TRACE(env);
2495 CHECK_ENV(env);
2496 CHECK_PTR_ARG(cls);
2497 CHECK_PTR_ARG(method);
2498 CHECK_PTR_ARG(result);
2499
2500 CheckStaticMethodReturnType(method, EtsType::SHORT);
2501 return GeneralMethodCall<EtsShort>(env, nullptr, method, result, args);
2502 }
2503
2504 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Short(ani_env * env,ani_class cls,ani_static_method method,ani_short * result,...)2505 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Short(ani_env *env, ani_class cls, ani_static_method method,
2506 ani_short *result, ...)
2507 {
2508 ANI_DEBUG_TRACE(env);
2509
2510 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2511 va_start(args, result);
2512 ani_status status = Class_CallStaticMethod_Short_V(env, cls, method, result, args);
2513 va_end(args);
2514 return status;
2515 }
2516
2517 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Short_A(ani_env * env,ani_class cls,ani_static_method method,ani_short * result,const ani_value * args)2518 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Short_A(ani_env *env, ani_class cls, ani_static_method method,
2519 ani_short *result, const ani_value *args)
2520 {
2521 ANI_DEBUG_TRACE(env);
2522 CHECK_ENV(env);
2523 CHECK_PTR_ARG(cls);
2524 CHECK_PTR_ARG(method);
2525 CHECK_PTR_ARG(result);
2526 CHECK_PTR_ARG(args);
2527
2528 CheckStaticMethodReturnType(method, EtsType::SHORT);
2529 return GeneralMethodCall<EtsShort>(env, nullptr, method, result, args);
2530 }
2531
2532 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Int_V(ani_env * env,ani_class cls,ani_static_method method,ani_int * result,va_list args)2533 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Int_V(ani_env *env, ani_class cls, ani_static_method method,
2534 ani_int *result, va_list args)
2535 {
2536 ANI_DEBUG_TRACE(env);
2537 CHECK_ENV(env);
2538 CHECK_PTR_ARG(cls);
2539 CHECK_PTR_ARG(method);
2540 CHECK_PTR_ARG(result);
2541
2542 CheckStaticMethodReturnType(method, EtsType::INT);
2543 return GeneralMethodCall<EtsInt>(env, nullptr, method, result, args);
2544 }
2545
2546 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Int(ani_env * env,ani_class cls,ani_static_method method,ani_int * result,...)2547 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Int(ani_env *env, ani_class cls, ani_static_method method,
2548 ani_int *result, ...)
2549 {
2550 ANI_DEBUG_TRACE(env);
2551
2552 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2553 va_start(args, result);
2554 ani_status status = Class_CallStaticMethod_Int_V(env, cls, method, result, args);
2555 va_end(args);
2556 return status;
2557 }
2558
2559 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Int_A(ani_env * env,ani_class cls,ani_static_method method,ani_int * result,const ani_value * args)2560 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Int_A(ani_env *env, ani_class cls, ani_static_method method,
2561 ani_int *result, const ani_value *args)
2562 {
2563 ANI_DEBUG_TRACE(env);
2564 CHECK_ENV(env);
2565 CHECK_PTR_ARG(cls);
2566 CHECK_PTR_ARG(method);
2567 CHECK_PTR_ARG(result);
2568 CHECK_PTR_ARG(args);
2569
2570 CheckStaticMethodReturnType(method, EtsType::INT);
2571 return GeneralMethodCall<EtsInt>(env, nullptr, method, result, args);
2572 }
2573
2574 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Long_V(ani_env * env,ani_class cls,ani_static_method method,ani_long * result,va_list args)2575 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Long_V(ani_env *env, ani_class cls, ani_static_method method,
2576 ani_long *result, va_list args)
2577 {
2578 ANI_DEBUG_TRACE(env);
2579 CHECK_ENV(env);
2580 CHECK_PTR_ARG(cls);
2581 CHECK_PTR_ARG(method);
2582 CHECK_PTR_ARG(result);
2583
2584 CheckStaticMethodReturnType(method, EtsType::LONG);
2585 return GeneralMethodCall<EtsLong>(env, nullptr, method, result, args);
2586 }
2587
2588 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Long(ani_env * env,ani_class cls,ani_static_method method,ani_long * result,...)2589 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Long(ani_env *env, ani_class cls, ani_static_method method,
2590 ani_long *result, ...)
2591 {
2592 ANI_DEBUG_TRACE(env);
2593
2594 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2595 va_start(args, result);
2596 ani_status status = Class_CallStaticMethod_Long_V(env, cls, method, result, args);
2597 va_end(args);
2598 return status;
2599 }
2600
2601 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Long_A(ani_env * env,ani_class cls,ani_static_method method,ani_long * result,const ani_value * args)2602 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Long_A(ani_env *env, ani_class cls, ani_static_method method,
2603 ani_long *result, const ani_value *args)
2604 {
2605 ANI_DEBUG_TRACE(env);
2606 CHECK_ENV(env);
2607 CHECK_PTR_ARG(cls);
2608 CHECK_PTR_ARG(method);
2609 CHECK_PTR_ARG(result);
2610 CHECK_PTR_ARG(args);
2611
2612 CheckStaticMethodReturnType(method, EtsType::LONG);
2613 return GeneralMethodCall<EtsLong>(env, nullptr, method, result, args);
2614 }
2615
2616 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Float_V(ani_env * env,ani_class cls,ani_static_method method,ani_float * result,va_list args)2617 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Float_V(ani_env *env, ani_class cls, ani_static_method method,
2618 ani_float *result, va_list args)
2619 {
2620 ANI_DEBUG_TRACE(env);
2621 CHECK_ENV(env);
2622 CHECK_PTR_ARG(cls);
2623 CHECK_PTR_ARG(method);
2624 CHECK_PTR_ARG(result);
2625
2626 CheckStaticMethodReturnType(method, EtsType::FLOAT);
2627 return GeneralMethodCall<EtsFloat>(env, nullptr, method, result, args);
2628 }
2629
2630 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Float(ani_env * env,ani_class cls,ani_static_method method,ani_float * result,...)2631 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Float(ani_env *env, ani_class cls, ani_static_method method,
2632 ani_float *result, ...)
2633 {
2634 ANI_DEBUG_TRACE(env);
2635
2636 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2637 va_start(args, result);
2638 ani_status status = Class_CallStaticMethod_Float_V(env, cls, method, result, args);
2639 va_end(args);
2640 return status;
2641 }
2642
2643 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Float_A(ani_env * env,ani_class cls,ani_static_method method,ani_float * result,const ani_value * args)2644 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Float_A(ani_env *env, ani_class cls, ani_static_method method,
2645 ani_float *result, const ani_value *args)
2646 {
2647 ANI_DEBUG_TRACE(env);
2648 CHECK_ENV(env);
2649 CHECK_PTR_ARG(cls);
2650 CHECK_PTR_ARG(method);
2651 CHECK_PTR_ARG(result);
2652 CHECK_PTR_ARG(args);
2653
2654 CheckStaticMethodReturnType(method, EtsType::FLOAT);
2655 return GeneralMethodCall<EtsFloat>(env, nullptr, method, result, args);
2656 }
2657
2658 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Double_V(ani_env * env,ani_class cls,ani_static_method method,ani_double * result,va_list args)2659 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Double_V(ani_env *env, ani_class cls, ani_static_method method,
2660 ani_double *result, va_list args)
2661 {
2662 ANI_DEBUG_TRACE(env);
2663 CHECK_ENV(env);
2664 CHECK_PTR_ARG(cls);
2665 CHECK_PTR_ARG(method);
2666 CHECK_PTR_ARG(result);
2667
2668 CheckStaticMethodReturnType(method, EtsType::DOUBLE);
2669 return GeneralMethodCall<EtsDouble>(env, nullptr, method, result, args);
2670 }
2671
2672 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Double(ani_env * env,ani_class cls,ani_static_method method,ani_double * result,...)2673 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Double(ani_env *env, ani_class cls, ani_static_method method,
2674 ani_double *result, ...)
2675 {
2676 ANI_DEBUG_TRACE(env);
2677
2678 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
2679 va_start(args, result);
2680 ani_status status = Class_CallStaticMethod_Double_V(env, cls, method, result, args);
2681 va_end(args);
2682 return status;
2683 }
2684
2685 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Double_A(ani_env * env,ani_class cls,ani_static_method method,ani_double * result,const ani_value * args)2686 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Double_A(ani_env *env, ani_class cls, ani_static_method method,
2687 ani_double *result, const ani_value *args)
2688 {
2689 ANI_DEBUG_TRACE(env);
2690 CHECK_ENV(env);
2691 CHECK_PTR_ARG(cls);
2692 CHECK_PTR_ARG(method);
2693 CHECK_PTR_ARG(result);
2694 CHECK_PTR_ARG(args);
2695
2696 CheckStaticMethodReturnType(method, EtsType::DOUBLE);
2697 return GeneralMethodCall<EtsDouble>(env, nullptr, method, result, args);
2698 }
2699
2700 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Boolean(ani_env * env,ani_object object,ani_field field,ani_boolean * result)2701 NO_UB_SANITIZE static ani_status Object_GetField_Boolean(ani_env *env, ani_object object, ani_field field,
2702 ani_boolean *result)
2703 {
2704 ANI_DEBUG_TRACE(env);
2705
2706 return GetPrimitiveTypeField(env, object, field, result);
2707 }
2708
2709 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Char(ani_env * env,ani_object object,ani_field field,ani_char * result)2710 NO_UB_SANITIZE static ani_status Object_GetField_Char(ani_env *env, ani_object object, ani_field field,
2711 ani_char *result)
2712 {
2713 ANI_DEBUG_TRACE(env);
2714
2715 return GetPrimitiveTypeField(env, object, field, result);
2716 }
2717
2718 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Byte(ani_env * env,ani_object object,ani_field field,ani_byte * result)2719 NO_UB_SANITIZE static ani_status Object_GetField_Byte(ani_env *env, ani_object object, ani_field field,
2720 ani_byte *result)
2721 {
2722 ANI_DEBUG_TRACE(env);
2723
2724 return GetPrimitiveTypeField(env, object, field, result);
2725 }
2726
2727 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Short(ani_env * env,ani_object object,ani_field field,ani_short * result)2728 NO_UB_SANITIZE static ani_status Object_GetField_Short(ani_env *env, ani_object object, ani_field field,
2729 ani_short *result)
2730 {
2731 ANI_DEBUG_TRACE(env);
2732
2733 return GetPrimitiveTypeField(env, object, field, result);
2734 }
2735
2736 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Int(ani_env * env,ani_object object,ani_field field,ani_int * result)2737 NO_UB_SANITIZE static ani_status Object_GetField_Int(ani_env *env, ani_object object, ani_field field, ani_int *result)
2738 {
2739 ANI_DEBUG_TRACE(env);
2740
2741 return GetPrimitiveTypeField(env, object, field, result);
2742 }
2743
2744 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Long(ani_env * env,ani_object object,ani_field field,ani_long * result)2745 NO_UB_SANITIZE static ani_status Object_GetField_Long(ani_env *env, ani_object object, ani_field field,
2746 ani_long *result)
2747 {
2748 ANI_DEBUG_TRACE(env);
2749
2750 return GetPrimitiveTypeField(env, object, field, result);
2751 }
2752
2753 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Float(ani_env * env,ani_object object,ani_field field,ani_float * result)2754 NO_UB_SANITIZE static ani_status Object_GetField_Float(ani_env *env, ani_object object, ani_field field,
2755 ani_float *result)
2756 {
2757 ANI_DEBUG_TRACE(env);
2758
2759 return GetPrimitiveTypeField(env, object, field, result);
2760 }
2761
2762 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Double(ani_env * env,ani_object object,ani_field field,ani_double * result)2763 NO_UB_SANITIZE static ani_status Object_GetField_Double(ani_env *env, ani_object object, ani_field field,
2764 ani_double *result)
2765 {
2766 ANI_DEBUG_TRACE(env);
2767
2768 return GetPrimitiveTypeField(env, object, field, result);
2769 }
2770
2771 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetField_Ref(ani_env * env,ani_object object,ani_field field,ani_ref * result)2772 NO_UB_SANITIZE static ani_status Object_GetField_Ref(ani_env *env, ani_object object, ani_field field, ani_ref *result)
2773 {
2774 ANI_DEBUG_TRACE(env);
2775 CHECK_ENV(env);
2776 CHECK_PTR_ARG(object);
2777 CHECK_PTR_ARG(field);
2778 CHECK_PTR_ARG(result);
2779
2780 EtsField *etsField = ToInternalField(field);
2781 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2782
2783 ScopedManagedCodeFix s(env);
2784 EtsObject *etsObject = s.ToInternalType(object);
2785 EtsObject *etsRes = etsObject->GetFieldObject(etsField);
2786 return s.AddLocalRef(etsRes, result);
2787 }
2788
2789 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Boolean(ani_env * env,ani_object object,ani_field field,ani_boolean value)2790 NO_UB_SANITIZE static ani_status Object_SetField_Boolean(ani_env *env, ani_object object, ani_field field,
2791 ani_boolean value)
2792 {
2793 ANI_DEBUG_TRACE(env);
2794
2795 return SetPrimitiveTypeField(env, object, field, value);
2796 }
2797
2798 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Char(ani_env * env,ani_object object,ani_field field,ani_char value)2799 NO_UB_SANITIZE static ani_status Object_SetField_Char(ani_env *env, ani_object object, ani_field field, ani_char value)
2800 {
2801 ANI_DEBUG_TRACE(env);
2802
2803 return SetPrimitiveTypeField(env, object, field, value);
2804 }
2805
2806 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Byte(ani_env * env,ani_object object,ani_field field,ani_byte value)2807 NO_UB_SANITIZE static ani_status Object_SetField_Byte(ani_env *env, ani_object object, ani_field field, ani_byte value)
2808 {
2809 ANI_DEBUG_TRACE(env);
2810
2811 return SetPrimitiveTypeField(env, object, field, value);
2812 }
2813
2814 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Short(ani_env * env,ani_object object,ani_field field,ani_short value)2815 NO_UB_SANITIZE static ani_status Object_SetField_Short(ani_env *env, ani_object object, ani_field field,
2816 ani_short value)
2817 {
2818 ANI_DEBUG_TRACE(env);
2819
2820 return SetPrimitiveTypeField(env, object, field, value);
2821 }
2822
2823 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Int(ani_env * env,ani_object object,ani_field field,ani_int value)2824 NO_UB_SANITIZE static ani_status Object_SetField_Int(ani_env *env, ani_object object, ani_field field, ani_int value)
2825 {
2826 ANI_DEBUG_TRACE(env);
2827
2828 return SetPrimitiveTypeField(env, object, field, value);
2829 }
2830
2831 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Long(ani_env * env,ani_object object,ani_field field,ani_long value)2832 NO_UB_SANITIZE static ani_status Object_SetField_Long(ani_env *env, ani_object object, ani_field field, ani_long value)
2833 {
2834 ANI_DEBUG_TRACE(env);
2835
2836 return SetPrimitiveTypeField(env, object, field, value);
2837 }
2838
2839 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Float(ani_env * env,ani_object object,ani_field field,ani_float value)2840 NO_UB_SANITIZE static ani_status Object_SetField_Float(ani_env *env, ani_object object, ani_field field,
2841 ani_float value)
2842 {
2843 ANI_DEBUG_TRACE(env);
2844
2845 return SetPrimitiveTypeField(env, object, field, value);
2846 }
2847
2848 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Double(ani_env * env,ani_object object,ani_field field,ani_double value)2849 NO_UB_SANITIZE static ani_status Object_SetField_Double(ani_env *env, ani_object object, ani_field field,
2850 ani_double value)
2851 {
2852 ANI_DEBUG_TRACE(env);
2853
2854 return SetPrimitiveTypeField(env, object, field, value);
2855 }
2856
2857 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetField_Ref(ani_env * env,ani_object object,ani_field field,ani_ref value)2858 NO_UB_SANITIZE static ani_status Object_SetField_Ref(ani_env *env, ani_object object, ani_field field, ani_ref value)
2859 {
2860 ANI_DEBUG_TRACE(env);
2861 CHECK_ENV(env);
2862 CHECK_PTR_ARG(object);
2863 CHECK_PTR_ARG(field);
2864 CHECK_PTR_ARG(value);
2865
2866 EtsField *etsField = ToInternalField(field);
2867 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2868
2869 ScopedManagedCodeFix s(env);
2870 EtsObject *etsObject = s.ToInternalType(object);
2871 EtsObject *etsValue = s.ToInternalType(value);
2872 etsObject->SetFieldObject(etsField, etsValue);
2873 return ANI_OK;
2874 }
2875
2876 template <typename R>
DoGetFieldByName(ani_env * env,ani_object object,const char * name,R * result)2877 static ani_status DoGetFieldByName(ani_env *env, ani_object object, const char *name, R *result)
2878 {
2879 ANI_DEBUG_TRACE(env);
2880 CHECK_ENV(env);
2881 CHECK_PTR_ARG(object);
2882 CHECK_PTR_ARG(name);
2883 CHECK_PTR_ARG(result);
2884
2885 static constexpr auto IS_REF = std::is_same_v<R, ani_ref>;
2886 using Res = std::conditional_t<IS_REF, EtsObject *, R>;
2887
2888 ScopedManagedCodeFix s(env);
2889 EtsCoroutine *coroutine = s.GetCoroutine();
2890 EtsHandleScope scope(coroutine);
2891 EtsHandle<EtsObject> etsObject(coroutine, s.ToInternalType(object));
2892 ASSERT(etsObject.GetPtr() != nullptr);
2893 EtsField *etsField = etsObject->GetClass()->GetFieldIDByName(name, nullptr);
2894 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
2895 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2896
2897 Res etsRes {};
2898 if constexpr (IS_REF) {
2899 etsRes = etsObject->GetFieldObject(etsField);
2900 return s.AddLocalRef(etsRes, result);
2901 } else {
2902 etsRes = etsObject->GetFieldPrimitive<R>(etsField);
2903 *result = etsRes;
2904 return ANI_OK;
2905 }
2906 }
2907
2908 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Boolean(ani_env * env,ani_object object,const char * name,ani_boolean * result)2909 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Boolean(ani_env *env, ani_object object, const char *name,
2910 ani_boolean *result)
2911 {
2912 return DoGetFieldByName(env, object, name, result);
2913 }
2914
2915 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Char(ani_env * env,ani_object object,const char * name,ani_char * result)2916 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Char(ani_env *env, ani_object object, const char *name,
2917 ani_char *result)
2918 {
2919 return DoGetFieldByName(env, object, name, result);
2920 }
2921
2922 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Byte(ani_env * env,ani_object object,const char * name,ani_byte * result)2923 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Byte(ani_env *env, ani_object object, const char *name,
2924 ani_byte *result)
2925 {
2926 return DoGetFieldByName(env, object, name, result);
2927 }
2928
2929 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Short(ani_env * env,ani_object object,const char * name,ani_short * result)2930 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Short(ani_env *env, ani_object object, const char *name,
2931 ani_short *result)
2932 {
2933 return DoGetFieldByName(env, object, name, result);
2934 }
2935
2936 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Int(ani_env * env,ani_object object,const char * name,ani_int * result)2937 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Int(ani_env *env, ani_object object, const char *name,
2938 ani_int *result)
2939 {
2940 return DoGetFieldByName(env, object, name, result);
2941 }
2942
2943 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Long(ani_env * env,ani_object object,const char * name,ani_long * result)2944 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Long(ani_env *env, ani_object object, const char *name,
2945 ani_long *result)
2946 {
2947 return DoGetFieldByName(env, object, name, result);
2948 }
2949
2950 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Float(ani_env * env,ani_object object,const char * name,ani_float * result)2951 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Float(ani_env *env, ani_object object, const char *name,
2952 ani_float *result)
2953 {
2954 return DoGetFieldByName(env, object, name, result);
2955 }
2956
2957 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Double(ani_env * env,ani_object object,const char * name,ani_double * result)2958 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Double(ani_env *env, ani_object object, const char *name,
2959 ani_double *result)
2960 {
2961 return DoGetFieldByName(env, object, name, result);
2962 }
2963
2964 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetFieldByName_Ref(ani_env * env,ani_object object,const char * name,ani_ref * result)2965 NO_UB_SANITIZE static ani_status Object_GetFieldByName_Ref(ani_env *env, ani_object object, const char *name,
2966 ani_ref *result)
2967 {
2968 return DoGetFieldByName(env, object, name, result);
2969 }
2970
2971 template <typename T>
ObjectSetFieldByNamePrimitive(ani_env * env,ani_object object,const char * name,T value)2972 NO_UB_SANITIZE ani_status ObjectSetFieldByNamePrimitive(ani_env *env, ani_object object, const char *name, T value)
2973 {
2974 ANI_DEBUG_TRACE(env);
2975 CHECK_ENV(env);
2976 CHECK_PTR_ARG(object);
2977 CHECK_PTR_ARG(name);
2978
2979 ScopedManagedCodeFix s(env);
2980 EtsCoroutine *coroutine = s.GetCoroutine();
2981 EtsHandleScope scope(coroutine);
2982 EtsHandle<EtsObject> etsObject(coroutine, s.ToInternalType(object));
2983 ASSERT(etsObject.GetPtr() != nullptr);
2984 EtsField *etsField = etsObject->GetClass()->GetFieldIDByName(name, nullptr);
2985 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
2986 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<T>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
2987
2988 etsObject->SetFieldPrimitive(etsField, value);
2989 return ANI_OK;
2990 }
2991
2992 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Boolean(ani_env * env,ani_object object,const char * name,ani_boolean value)2993 NO_UB_SANITIZE ani_status Object_SetFieldByName_Boolean(ani_env *env, ani_object object, const char *name,
2994 ani_boolean value)
2995 {
2996 ANI_DEBUG_TRACE(env);
2997
2998 return ObjectSetFieldByNamePrimitive(env, object, name, value);
2999 }
3000
3001 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Char(ani_env * env,ani_object object,const char * name,ani_char value)3002 NO_UB_SANITIZE ani_status Object_SetFieldByName_Char(ani_env *env, ani_object object, const char *name, ani_char value)
3003 {
3004 ANI_DEBUG_TRACE(env);
3005
3006 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3007 }
3008
3009 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Byte(ani_env * env,ani_object object,const char * name,ani_byte value)3010 NO_UB_SANITIZE ani_status Object_SetFieldByName_Byte(ani_env *env, ani_object object, const char *name, ani_byte value)
3011 {
3012 ANI_DEBUG_TRACE(env);
3013
3014 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3015 }
3016
3017 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Short(ani_env * env,ani_object object,const char * name,ani_short value)3018 NO_UB_SANITIZE ani_status Object_SetFieldByName_Short(ani_env *env, ani_object object, const char *name,
3019 ani_short value)
3020 {
3021 ANI_DEBUG_TRACE(env);
3022
3023 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3024 }
3025
3026 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Int(ani_env * env,ani_object object,const char * name,ani_int value)3027 NO_UB_SANITIZE ani_status Object_SetFieldByName_Int(ani_env *env, ani_object object, const char *name, ani_int value)
3028 {
3029 ANI_DEBUG_TRACE(env);
3030
3031 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3032 }
3033
3034 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Long(ani_env * env,ani_object object,const char * name,ani_long value)3035 NO_UB_SANITIZE ani_status Object_SetFieldByName_Long(ani_env *env, ani_object object, const char *name, ani_long value)
3036 {
3037 ANI_DEBUG_TRACE(env);
3038
3039 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3040 }
3041
3042 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Float(ani_env * env,ani_object object,const char * name,ani_float value)3043 NO_UB_SANITIZE ani_status Object_SetFieldByName_Float(ani_env *env, ani_object object, const char *name,
3044 ani_float value)
3045 {
3046 ANI_DEBUG_TRACE(env);
3047
3048 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3049 }
3050
3051 // NOLINTNEXTLINE(readability-identifier-naming,-warnings-as-errors)
Object_SetFieldByName_Double(ani_env * env,ani_object object,const char * name,ani_double value)3052 NO_UB_SANITIZE ani_status Object_SetFieldByName_Double(ani_env *env, ani_object object, const char *name,
3053 ani_double value)
3054 {
3055 ANI_DEBUG_TRACE(env);
3056
3057 return ObjectSetFieldByNamePrimitive(env, object, name, value);
3058 }
3059
3060 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetFieldByName_Ref(ani_env * env,ani_object object,const char * name,ani_ref value)3061 NO_UB_SANITIZE static ani_status Object_SetFieldByName_Ref(ani_env *env, ani_object object, const char *name,
3062 ani_ref value)
3063 {
3064 ANI_DEBUG_TRACE(env);
3065 CHECK_ENV(env);
3066 CHECK_PTR_ARG(object);
3067 CHECK_PTR_ARG(name);
3068 CHECK_PTR_ARG(value);
3069
3070 ScopedManagedCodeFix s(env);
3071 EtsCoroutine *coroutine = s.GetCoroutine();
3072 EtsHandleScope scope(coroutine);
3073 EtsHandle<EtsObject> etsObject(coroutine, s.ToInternalType(object));
3074 ASSERT(etsObject.GetPtr() != nullptr);
3075 EtsField *etsField = etsObject->GetClass()->GetFieldIDByName(name, nullptr);
3076 EtsObject *etsValue = s.ToInternalType(value);
3077 ANI_CHECK_RETURN_IF_EQ(etsField, nullptr, ANI_NOT_FOUND);
3078 ANI_CHECK_RETURN_IF_NE(etsField->GetEtsType(), AniTypeInfo<ani_ref>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
3079
3080 etsObject->SetFieldObject(etsField, etsValue);
3081 return ANI_OK;
3082 }
3083
3084 template <typename R>
DoGetPropertyByName(ani_env * env,ani_object object,const char * name,R * result)3085 static ani_status DoGetPropertyByName(ani_env *env, ani_object object, const char *name, R *result)
3086 {
3087 static constexpr auto IS_REF = std::is_same_v<R, ani_ref>;
3088 using Res = std::conditional_t<IS_REF, EtsObject *, R>;
3089
3090 ASSERT(name != nullptr);
3091 ASSERT(result != nullptr);
3092
3093 ScopedManagedCodeFix s(env);
3094 EtsCoroutine *coroutine = s.GetCoroutine();
3095 EtsHandleScope scope(coroutine);
3096 Res etsRes {};
3097 EtsHandle<EtsObject> etsObject(coroutine, s.ToInternalType(object));
3098 EtsHandle<EtsClass> klass(coroutine, etsObject->GetClass());
3099 EtsField *field = klass->GetFieldIDByName(name, nullptr);
3100 if (field != nullptr) {
3101 // Property as field
3102 ANI_CHECK_RETURN_IF_NE(field->GetEtsType(), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
3103 if constexpr (IS_REF) {
3104 etsRes = etsObject->GetFieldObject(field);
3105 } else {
3106 etsRes = etsObject->GetFieldPrimitive<R>(field);
3107 }
3108 } else {
3109 // Property as getter
3110 EtsMethod *method = klass->GetInstanceMethod((PandaString(GETTER_BEGIN) + name).c_str(), nullptr);
3111 ANI_CHECK_RETURN_IF_EQ(method, nullptr, ANI_NOT_FOUND);
3112 ANI_CHECK_RETURN_IF_EQ(method->IsStatic(), true, ANI_NOT_FOUND);
3113 ANI_CHECK_RETURN_IF_NE(method->GetNumArgs(), 1, ANI_NOT_FOUND);
3114 ANI_CHECK_RETURN_IF_NE(method->GetArgType(0), EtsType::OBJECT, ANI_NOT_FOUND);
3115 ANI_CHECK_RETURN_IF_NE(method->GetReturnValueType(), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
3116
3117 std::array args = {Value {etsObject->GetCoreType()}};
3118 Value res = method->GetPandaMethod()->Invoke(coroutine, args.data());
3119 ANI_CHECK_RETURN_IF_EQ(coroutine->HasPendingException(), true, ANI_PENDING_ERROR);
3120
3121 if constexpr (IS_REF) {
3122 etsRes = EtsObject::FromCoreType(res.GetAs<ObjectHeader *>());
3123 } else {
3124 etsRes = res.GetAs<R>();
3125 }
3126 }
3127 if constexpr (IS_REF) {
3128 return s.AddLocalRef(etsRes, result);
3129 } else {
3130 *result = etsRes;
3131 return ANI_OK;
3132 }
3133 }
3134
3135 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Boolean(ani_env * env,ani_object object,const char * name,ani_boolean * result)3136 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Boolean(ani_env *env, ani_object object, const char *name,
3137 ani_boolean *result)
3138 {
3139 ANI_DEBUG_TRACE(env);
3140 CHECK_ENV(env);
3141 CHECK_PTR_ARG(object);
3142 CHECK_PTR_ARG(name);
3143 CHECK_PTR_ARG(result);
3144
3145 return DoGetPropertyByName(env, object, name, result);
3146 }
3147
3148 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Char(ani_env * env,ani_object object,const char * name,ani_char * result)3149 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Char(ani_env *env, ani_object object, const char *name,
3150 ani_char *result)
3151 {
3152 ANI_DEBUG_TRACE(env);
3153 CHECK_ENV(env);
3154 CHECK_PTR_ARG(object);
3155 CHECK_PTR_ARG(name);
3156 CHECK_PTR_ARG(result);
3157
3158 return DoGetPropertyByName(env, object, name, result);
3159 }
3160
3161 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Byte(ani_env * env,ani_object object,const char * name,ani_byte * result)3162 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Byte(ani_env *env, ani_object object, const char *name,
3163 ani_byte *result)
3164 {
3165 ANI_DEBUG_TRACE(env);
3166 CHECK_ENV(env);
3167 CHECK_PTR_ARG(object);
3168 CHECK_PTR_ARG(name);
3169 CHECK_PTR_ARG(result);
3170
3171 return DoGetPropertyByName(env, object, name, result);
3172 }
3173
3174 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Short(ani_env * env,ani_object object,const char * name,ani_short * result)3175 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Short(ani_env *env, ani_object object, const char *name,
3176 ani_short *result)
3177 {
3178 ANI_DEBUG_TRACE(env);
3179 CHECK_ENV(env);
3180 CHECK_PTR_ARG(object);
3181 CHECK_PTR_ARG(name);
3182 CHECK_PTR_ARG(result);
3183
3184 return DoGetPropertyByName(env, object, name, result);
3185 }
3186
3187 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Int(ani_env * env,ani_object object,const char * name,ani_int * result)3188 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Int(ani_env *env, ani_object object, const char *name,
3189 ani_int *result)
3190 {
3191 ANI_DEBUG_TRACE(env);
3192 CHECK_ENV(env);
3193 CHECK_PTR_ARG(object);
3194 CHECK_PTR_ARG(name);
3195 CHECK_PTR_ARG(result);
3196
3197 return DoGetPropertyByName(env, object, name, result);
3198 }
3199
3200 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Long(ani_env * env,ani_object object,const char * name,ani_long * result)3201 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Long(ani_env *env, ani_object object, const char *name,
3202 ani_long *result)
3203 {
3204 ANI_DEBUG_TRACE(env);
3205 CHECK_ENV(env);
3206 CHECK_PTR_ARG(object);
3207 CHECK_PTR_ARG(name);
3208 CHECK_PTR_ARG(result);
3209
3210 return DoGetPropertyByName(env, object, name, result);
3211 }
3212
3213 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Float(ani_env * env,ani_object object,const char * name,ani_float * result)3214 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Float(ani_env *env, ani_object object, const char *name,
3215 ani_float *result)
3216 {
3217 ANI_DEBUG_TRACE(env);
3218 CHECK_ENV(env);
3219 CHECK_PTR_ARG(object);
3220 CHECK_PTR_ARG(name);
3221 CHECK_PTR_ARG(result);
3222
3223 return DoGetPropertyByName(env, object, name, result);
3224 }
3225
3226 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Double(ani_env * env,ani_object object,const char * name,ani_double * result)3227 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Double(ani_env *env, ani_object object, const char *name,
3228 ani_double *result)
3229 {
3230 ANI_DEBUG_TRACE(env);
3231 CHECK_ENV(env);
3232 CHECK_PTR_ARG(object);
3233 CHECK_PTR_ARG(name);
3234 CHECK_PTR_ARG(result);
3235
3236 return DoGetPropertyByName(env, object, name, result);
3237 }
3238
3239 // NOLINTNEXTLINE(readability-identifier-naming)
Object_GetPropertyByName_Ref(ani_env * env,ani_object object,const char * name,ani_ref * result)3240 NO_UB_SANITIZE static ani_status Object_GetPropertyByName_Ref(ani_env *env, ani_object object, const char *name,
3241 ani_ref *result)
3242 {
3243 ANI_DEBUG_TRACE(env);
3244 CHECK_ENV(env);
3245 CHECK_PTR_ARG(object);
3246 CHECK_PTR_ARG(name);
3247 CHECK_PTR_ARG(result);
3248
3249 return DoGetPropertyByName(env, object, name, result);
3250 }
3251
3252 template <typename R>
DoSetPropertyByName(ani_env * env,ani_object object,const char * name,R value)3253 static ani_status DoSetPropertyByName(ani_env *env, ani_object object, const char *name, R value)
3254 {
3255 static constexpr auto IS_REF = std::is_same_v<R, ani_ref>;
3256
3257 ASSERT(name != nullptr);
3258
3259 ScopedManagedCodeFix s(env);
3260 EtsCoroutine *coroutine = s.GetCoroutine();
3261 EtsHandleScope scope(coroutine);
3262 EtsHandle<EtsObject> etsObject(coroutine, s.ToInternalType(object));
3263 EtsHandle<EtsClass> klass(coroutine, etsObject->GetClass());
3264 EtsField *field = klass->GetFieldIDByName(name, nullptr);
3265 if (field != nullptr) {
3266 // Property as field
3267 ANI_CHECK_RETURN_IF_NE(field->GetEtsType(), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
3268 if constexpr (IS_REF) {
3269 EtsObject *etsValue = s.ToInternalType(value);
3270 etsObject->SetFieldObject(field, etsValue);
3271 } else {
3272 etsObject->SetFieldPrimitive<R>(field, value);
3273 }
3274 } else {
3275 // Property as setter
3276 EtsMethod *method = klass->GetInstanceMethod((PandaString(SETTER_BEGIN) + name).c_str(), nullptr);
3277 ANI_CHECK_RETURN_IF_EQ(method, nullptr, ANI_NOT_FOUND);
3278 ANI_CHECK_RETURN_IF_EQ(method->IsStatic(), true, ANI_NOT_FOUND);
3279 ANI_CHECK_RETURN_IF_NE(method->GetNumArgs(), 2U, ANI_NOT_FOUND);
3280 ANI_CHECK_RETURN_IF_NE(method->GetArgType(0), EtsType::OBJECT, ANI_NOT_FOUND);
3281 ANI_CHECK_RETURN_IF_NE(method->GetArgType(1U), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
3282 ANI_CHECK_RETURN_IF_NE(method->GetReturnValueType(), EtsType::VOID, ANI_INVALID_TYPE);
3283
3284 std::array<Value, 2U> args;
3285 args.at(0) = Value {etsObject->GetCoreType()};
3286 if constexpr (IS_REF) {
3287 EtsObject *etsValue = s.ToInternalType(value);
3288 args.at(1U) = Value {etsValue->GetCoreType()};
3289 } else {
3290 args.at(1U) = Value {value};
3291 }
3292
3293 method->GetPandaMethod()->Invoke(coroutine, args.data());
3294 ANI_CHECK_RETURN_IF_EQ(coroutine->HasPendingException(), true, ANI_PENDING_ERROR);
3295 }
3296 return ANI_OK;
3297 }
3298
3299 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Boolean(ani_env * env,ani_object object,const char * name,ani_boolean value)3300 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Boolean(ani_env *env, ani_object object, const char *name,
3301 ani_boolean value)
3302 {
3303 ANI_DEBUG_TRACE(env);
3304 CHECK_ENV(env);
3305 CHECK_PTR_ARG(object);
3306 CHECK_PTR_ARG(name);
3307
3308 return DoSetPropertyByName(env, object, name, value);
3309 }
3310
3311 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Char(ani_env * env,ani_object object,const char * name,ani_char value)3312 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Char(ani_env *env, ani_object object, const char *name,
3313 ani_char value)
3314 {
3315 ANI_DEBUG_TRACE(env);
3316 CHECK_ENV(env);
3317 CHECK_PTR_ARG(object);
3318 CHECK_PTR_ARG(name);
3319
3320 return DoSetPropertyByName(env, object, name, value);
3321 }
3322
3323 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Byte(ani_env * env,ani_object object,const char * name,ani_byte value)3324 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Byte(ani_env *env, ani_object object, const char *name,
3325 ani_byte value)
3326 {
3327 ANI_DEBUG_TRACE(env);
3328 CHECK_ENV(env);
3329 CHECK_PTR_ARG(object);
3330 CHECK_PTR_ARG(name);
3331
3332 return DoSetPropertyByName(env, object, name, value);
3333 }
3334
3335 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Short(ani_env * env,ani_object object,const char * name,ani_short value)3336 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Short(ani_env *env, ani_object object, const char *name,
3337 ani_short value)
3338 {
3339 ANI_DEBUG_TRACE(env);
3340 CHECK_ENV(env);
3341 CHECK_PTR_ARG(object);
3342 CHECK_PTR_ARG(name);
3343
3344 return DoSetPropertyByName(env, object, name, value);
3345 }
3346
3347 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Int(ani_env * env,ani_object object,const char * name,ani_int value)3348 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Int(ani_env *env, ani_object object, const char *name,
3349 ani_int value)
3350 {
3351 ANI_DEBUG_TRACE(env);
3352 CHECK_ENV(env);
3353 CHECK_PTR_ARG(object);
3354 CHECK_PTR_ARG(name);
3355
3356 return DoSetPropertyByName(env, object, name, value);
3357 }
3358
3359 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Long(ani_env * env,ani_object object,const char * name,ani_long value)3360 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Long(ani_env *env, ani_object object, const char *name,
3361 ani_long value)
3362 {
3363 ANI_DEBUG_TRACE(env);
3364 CHECK_ENV(env);
3365 CHECK_PTR_ARG(object);
3366 CHECK_PTR_ARG(name);
3367
3368 return DoSetPropertyByName(env, object, name, value);
3369 }
3370
3371 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Float(ani_env * env,ani_object object,const char * name,ani_float value)3372 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Float(ani_env *env, ani_object object, const char *name,
3373 ani_float value)
3374 {
3375 ANI_DEBUG_TRACE(env);
3376 CHECK_ENV(env);
3377 CHECK_PTR_ARG(object);
3378 CHECK_PTR_ARG(name);
3379
3380 return DoSetPropertyByName(env, object, name, value);
3381 }
3382
3383 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Double(ani_env * env,ani_object object,const char * name,ani_double value)3384 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Double(ani_env *env, ani_object object, const char *name,
3385 ani_double value)
3386 {
3387 ANI_DEBUG_TRACE(env);
3388 CHECK_ENV(env);
3389 CHECK_PTR_ARG(object);
3390 CHECK_PTR_ARG(name);
3391
3392 return DoSetPropertyByName(env, object, name, value);
3393 }
3394
3395 // NOLINTNEXTLINE(readability-identifier-naming)
Object_SetPropertyByName_Ref(ani_env * env,ani_object object,const char * name,ani_ref value)3396 NO_UB_SANITIZE static ani_status Object_SetPropertyByName_Ref(ani_env *env, ani_object object, const char *name,
3397 ani_ref value)
3398 {
3399 ANI_DEBUG_TRACE(env);
3400 CHECK_ENV(env);
3401 CHECK_PTR_ARG(object);
3402 CHECK_PTR_ARG(name);
3403
3404 return DoSetPropertyByName(env, object, name, value);
3405 }
3406
ExistUnhandledError(ani_env * env,ani_boolean * result)3407 NO_UB_SANITIZE static ani_status ExistUnhandledError(ani_env *env, ani_boolean *result)
3408 {
3409 ANI_DEBUG_TRACE(env);
3410 CHECK_PTR_ARG(env);
3411 CHECK_PTR_ARG(result);
3412
3413 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
3414 ScopedManagedCodeFix s(pandaEnv);
3415 *result = pandaEnv->HasPendingException() ? ANI_TRUE : ANI_FALSE;
3416 return ANI_OK;
3417 }
3418
ResetError(ani_env * env)3419 NO_UB_SANITIZE static ani_status ResetError(ani_env *env)
3420 {
3421 ANI_DEBUG_TRACE(env);
3422 CHECK_PTR_ARG(env);
3423
3424 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
3425 ScopedManagedCodeFix s(pandaEnv);
3426 pandaEnv->ClearException();
3427 return ANI_OK;
3428 }
3429
3430 // NOLINTNEXTLINE(readability-identifier-naming)
ThrowError(ani_env * env,ani_error err)3431 NO_UB_SANITIZE static ani_status ThrowError(ani_env *env, ani_error err)
3432 {
3433 ANI_DEBUG_TRACE(env);
3434 CHECK_PTR_ARG(env);
3435 CHECK_PTR_ARG(err);
3436
3437 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
3438 ScopedManagedCodeFix s(pandaEnv);
3439 EtsThrowable *exception = s.ToInternalType(err);
3440 ANI_CHECK_RETURN_IF_EQ(exception, nullptr, ANI_ERROR);
3441 PandaEnv::ToPandaEtsEnv(pandaEnv)->SetException(exception);
3442 return ANI_OK;
3443 }
3444
3445 class ClearExceptionScope {
3446 public:
ClearExceptionScope(ani_env * env)3447 explicit ClearExceptionScope(ani_env *env) : env_(env)
3448 {
3449 [[maybe_unused]] ani_status status = env_->GetUnhandledError(&error_);
3450 ASSERT(status == ANI_OK);
3451 ASSERT(error_ != nullptr);
3452
3453 status = env_->ResetError();
3454 ASSERT(status == ANI_OK);
3455 }
3456
3457 NO_COPY_SEMANTIC(ClearExceptionScope);
3458 NO_MOVE_SEMANTIC(ClearExceptionScope);
3459
~ClearExceptionScope()3460 ~ClearExceptionScope()
3461 {
3462 [[maybe_unused]] ani_status status = ANI_OK;
3463 #ifndef NDEBUG
3464 ani_boolean exists = ANI_FALSE;
3465 status = env_->ExistUnhandledError(&exists);
3466 ASSERT(status == ANI_OK);
3467 ASSERT(exists == ANI_FALSE);
3468 #endif // NDEBUG
3469 status = env_->ThrowError(error_);
3470 ASSERT(status == ANI_OK);
3471 }
3472
GetError()3473 ani_error GetError()
3474 {
3475 return error_;
3476 }
3477
3478 private:
3479 ani_env *env_ {nullptr};
3480 ani_error error_ {nullptr};
3481 };
3482
FindClassByName(ani_env * env,const char * name,ani_class * cls)3483 static ani_status FindClassByName(ani_env *env, const char *name, ani_class *cls)
3484 {
3485 // NOTE(dslynko, #23447): use cache of well-known classes
3486 auto status = env->FindClass(name, cls);
3487 ASSERT(status == ANI_OK);
3488 return status;
3489 }
3490
FindMethodByName(ani_env * env,ani_class cls,const char * name,const char * sig,ani_method * res)3491 static ani_status FindMethodByName(ani_env *env, ani_class cls, const char *name, const char *sig, ani_method *res)
3492 {
3493 auto status = env->Class_FindMethod(cls, name, sig, res);
3494 ASSERT(status == ANI_OK);
3495 return status;
3496 }
3497
CallParameterlessCtor(ani_env * env,ani_class cls,ani_object * obj)3498 static ani_status CallParameterlessCtor(ani_env *env, ani_class cls, ani_object *obj)
3499 {
3500 ani_method ctor {};
3501 // NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
3502 auto status = env->Class_FindMethod(cls, "<ctor>", ":V", &ctor);
3503 ASSERT(status == ANI_OK);
3504
3505 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3506 status = env->Object_New(cls, ctor, obj);
3507 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
3508 return status;
3509 }
3510
3511 // NOLINTBEGIN(clang-analyzer-deadcode.DeadStores)
GetErrorDescriptionLines(ani_env * env,ani_error error,ani_string * errDesc)3512 static ani_status GetErrorDescriptionLines(ani_env *env, ani_error error, ani_string *errDesc)
3513 {
3514 ani_type errorType = nullptr;
3515 auto status = env->Object_GetType(error, &errorType);
3516 ASSERT(status == ANI_OK);
3517
3518 // Get error message
3519 ani_ref errorMessage = nullptr;
3520 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3521 status = env->Object_CallMethodByName_Ref(error, "toString", ":Lstd/core/String;", &errorMessage);
3522 ASSERT(status == ANI_OK);
3523
3524 // Add newline between error message and stack trace
3525 ani_string newlineString = nullptr;
3526 std::string_view newline = "\n";
3527 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3528 status = env->String_NewUTF8(newline.data(), newline.size(), &newlineString);
3529 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
3530
3531 // Get stack trace
3532 ani_method getterMethod = nullptr;
3533 status = env->Class_FindGetter(static_cast<ani_class>(errorType), "stack", &getterMethod);
3534 ASSERT(status == ANI_OK);
3535 ani_ref stackTrace = nullptr;
3536 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3537 status = env->Object_CallMethod_Ref(error, getterMethod, &stackTrace);
3538 ASSERT(status == ANI_OK);
3539
3540 ani_boolean isUndefined = ANI_FALSE;
3541 status = env->Reference_IsUndefined(stackTrace, &isUndefined);
3542 ASSERT(status == ANI_OK);
3543 if (isUndefined == ANI_TRUE) {
3544 std::string_view errorInfo = "unable to get stack trace";
3545 ani_string createdString;
3546 status = env->String_NewUTF8(errorInfo.data(), errorInfo.size(), &createdString);
3547 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
3548 stackTrace = createdString;
3549 }
3550
3551 ani_class sbCls = nullptr;
3552 FindClassByName(env, "Lstd/core/StringBuilder;", &sbCls);
3553
3554 // assemble error message, newline and trace into a single string
3555 ani_method sbAppend = nullptr;
3556 status =
3557 FindMethodByName(env, sbCls, "append",
3558 "Lstd/core/String;Lstd/core/String;Lstd/core/String;:Lstd/core/StringBuilder;", &sbAppend);
3559 ASSERT(status == ANI_OK);
3560
3561 ani_object sbObj = nullptr;
3562 status = CallParameterlessCtor(env, sbCls, &sbObj);
3563 ASSERT(status == ANI_OK);
3564
3565 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3566 status = env->Object_CallMethod_Ref(sbObj, sbAppend, reinterpret_cast<ani_ref *>(&sbObj), errorMessage,
3567 newlineString, stackTrace);
3568 ASSERT(status == ANI_OK);
3569
3570 ani_method sbToString = nullptr;
3571 status = FindMethodByName(env, sbCls, "toString", ":Lstd/core/String;", &sbToString);
3572 ASSERT(status == ANI_OK);
3573
3574 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3575 status = env->Object_CallMethod_Ref(sbObj, sbToString, reinterpret_cast<ani_ref *>(errDesc));
3576 ASSERT(status == ANI_OK);
3577 return status;
3578 }
3579
DescribeError(ani_env * env)3580 NO_UB_SANITIZE static ani_status DescribeError(ani_env *env)
3581 {
3582 ANI_DEBUG_TRACE(env);
3583 CHECK_PTR_ARG(env);
3584
3585 ani_boolean errorExists = ANI_FALSE;
3586 auto status = env->ExistUnhandledError(&errorExists);
3587 ASSERT(status == ANI_OK);
3588 if (errorExists == ANI_FALSE) {
3589 return ANI_OK;
3590 }
3591 ClearExceptionScope s(env);
3592
3593 ani_string errorDescription = nullptr;
3594 status = GetErrorDescriptionLines(env, s.GetError(), &errorDescription);
3595 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
3596
3597 // Get `std.core.console` global variable [Lstd/core/Object
3598 ani_module stdCoreModule = nullptr;
3599 status = env->FindModule("Lstd/core;", &stdCoreModule);
3600 ASSERT(status == ANI_OK);
3601
3602 ani_variable consoleVar = nullptr;
3603 status = env->Module_FindVariable(stdCoreModule, "console", &consoleVar);
3604 ASSERT(status == ANI_OK);
3605
3606 ani_ref console = nullptr;
3607 status = env->Variable_GetValue_Ref(consoleVar, &console);
3608 ASSERT(status == ANI_OK);
3609
3610 ani_type strTyp = nullptr;
3611 status = env->Object_GetType(errorDescription, &strTyp);
3612 ASSERT(status == ANI_OK);
3613
3614 ani_array_ref arr = nullptr;
3615 status = env->Array_New_Ref(strTyp, 1, errorDescription, &arr);
3616 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
3617
3618 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
3619 status = env->Object_CallMethodByName_Void(static_cast<ani_object>(console), "error", "Lescompat/Array;:V", arr);
3620 ASSERT(status == ANI_OK);
3621 return status;
3622 }
3623 // NOLINTEND(clang-analyzer-deadcode.DeadStores)
3624
GetUnhandledError(ani_env * env,ani_error * result)3625 NO_UB_SANITIZE static ani_status GetUnhandledError(ani_env *env, ani_error *result)
3626 {
3627 ANI_DEBUG_TRACE(env);
3628 CHECK_PTR_ARG(env);
3629 CHECK_PTR_ARG(result);
3630
3631 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
3632 ScopedManagedCodeFix s(pandaEnv);
3633 EtsThrowable *throwable = pandaEnv->GetThrowable();
3634 ANI_CHECK_RETURN_IF_EQ(throwable, nullptr, ANI_ERROR);
3635 return s.AddLocalRef(throwable, reinterpret_cast<ani_ref *>(result));
3636 }
3637
Abort(ani_env * env,const char * message)3638 NO_UB_SANITIZE static ani_status Abort([[maybe_unused]] ani_env *env, const char *message)
3639 {
3640 ANI_DEBUG_TRACE(env);
3641 LOG(FATAL, ANI) << "EtsAniError: " << message;
3642 return ANI_OK;
3643 }
3644
GetNull(ani_env * env,ani_ref * result)3645 NO_UB_SANITIZE static ani_status GetNull(ani_env *env, ani_ref *result)
3646 {
3647 ANI_DEBUG_TRACE(env);
3648 CHECK_ENV(env);
3649 CHECK_PTR_ARG(result);
3650
3651 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
3652 ScopedManagedCodeFix s(pandaEnv);
3653 return s.GetNullRef(result);
3654 }
3655
GetUndefined(ani_env * env,ani_ref * result)3656 NO_UB_SANITIZE static ani_status GetUndefined(ani_env *env, ani_ref *result)
3657 {
3658 ANI_DEBUG_TRACE(env);
3659 CHECK_ENV(env);
3660 CHECK_PTR_ARG(result);
3661
3662 return ManagedCodeAccessor::GetUndefinedRef(result);
3663 }
3664
3665 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_IsNull(ani_env * env,ani_ref ref,ani_boolean * result)3666 NO_UB_SANITIZE static ani_status Reference_IsNull(ani_env *env, ani_ref ref, ani_boolean *result)
3667 {
3668 ANI_DEBUG_TRACE(env);
3669 CHECK_ENV(env);
3670 CHECK_PTR_ARG(result);
3671
3672 // Fast path
3673 if (IsUndefined(ref)) {
3674 *result = ANI_FALSE;
3675 return ANI_OK;
3676 }
3677 // Slow path
3678 ScopedManagedCodeFix s(env);
3679 *result = s.IsNull(ref) ? ANI_TRUE : ANI_FALSE;
3680 return ANI_OK;
3681 }
3682
3683 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_IsUndefined(ani_env * env,ani_ref ref,ani_boolean * result)3684 NO_UB_SANITIZE static ani_status Reference_IsUndefined(ani_env *env, ani_ref ref, ani_boolean *result)
3685 {
3686 ANI_DEBUG_TRACE(env);
3687 CHECK_ENV(env);
3688 CHECK_PTR_ARG(result);
3689
3690 *result = IsUndefined(ref) ? ANI_TRUE : ANI_FALSE;
3691 return ANI_OK;
3692 }
3693
3694 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_IsNullishValue(ani_env * env,ani_ref ref,ani_boolean * result)3695 NO_UB_SANITIZE static ani_status Reference_IsNullishValue(ani_env *env, ani_ref ref, ani_boolean *result)
3696 {
3697 ANI_DEBUG_TRACE(env);
3698 CHECK_ENV(env);
3699 CHECK_PTR_ARG(result);
3700
3701 // Fast path
3702 if (IsUndefined(ref)) {
3703 *result = ANI_TRUE;
3704 return ANI_OK;
3705 }
3706 // Slow path
3707 ScopedManagedCodeFix s(env);
3708 *result = s.IsNull(ref) ? ANI_TRUE : ANI_FALSE;
3709 return ANI_OK;
3710 }
3711
3712 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_Equals(ani_env * env,ani_ref ref0,ani_ref ref1,ani_boolean * result)3713 NO_UB_SANITIZE static ani_status Reference_Equals(ani_env *env, ani_ref ref0, ani_ref ref1, ani_boolean *result)
3714 {
3715 ANI_DEBUG_TRACE(env);
3716 CHECK_ENV(env);
3717 CHECK_PTR_ARG(result);
3718
3719 // Fast path
3720 if (IsUndefined(ref0) && IsUndefined(ref1)) {
3721 *result = ANI_TRUE;
3722 return ANI_OK;
3723 }
3724 // Slow path
3725 ScopedManagedCodeFix s(env);
3726 bool isEquals = EtsReferenceEquals<false>(s.GetCoroutine(), s.ToInternalType(ref0), s.ToInternalType(ref1));
3727 *result = isEquals ? ANI_TRUE : ANI_FALSE;
3728 return ANI_OK;
3729 }
3730
3731 // NOLINTNEXTLINE(readability-identifier-naming)
Reference_StrictEquals(ani_env * env,ani_ref ref0,ani_ref ref1,ani_boolean * result)3732 NO_UB_SANITIZE static ani_status Reference_StrictEquals(ani_env *env, ani_ref ref0, ani_ref ref1, ani_boolean *result)
3733 {
3734 ANI_DEBUG_TRACE(env);
3735 CHECK_ENV(env);
3736 CHECK_PTR_ARG(result);
3737
3738 // Fast path
3739 if (IsUndefined(ref0) && IsUndefined(ref1)) {
3740 *result = ANI_TRUE;
3741 return ANI_OK;
3742 }
3743 // Slow path
3744 ScopedManagedCodeFix s(env);
3745 bool isStrictEquals = EtsReferenceEquals<true>(s.GetCoroutine(), s.ToInternalType(ref0), s.ToInternalType(ref1));
3746 *result = isStrictEquals ? ANI_TRUE : ANI_FALSE;
3747 return ANI_OK;
3748 }
3749
3750 // NOLINTNEXTLINE(readability-identifier-naming)
Object_InstanceOf(ani_env * env,ani_object object,ani_type type,ani_boolean * result)3751 NO_UB_SANITIZE static ani_status Object_InstanceOf(ani_env *env, ani_object object, ani_type type, ani_boolean *result)
3752 {
3753 ANI_DEBUG_TRACE(env);
3754 CHECK_ENV(env);
3755 CHECK_PTR_ARG(type);
3756 CHECK_PTR_ARG(object);
3757 CHECK_PTR_ARG(result);
3758
3759 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
3760 EtsClass *internalClass = s.ToInternalType(type);
3761 EtsObject *internalObject = s.ToInternalType(object);
3762
3763 // NOTE: Update implementation when all types will be supported. #22003
3764 *result = internalObject->IsInstanceOf(internalClass) ? ANI_TRUE : ANI_FALSE;
3765 return ANI_OK;
3766 }
3767
3768 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Ref_V(ani_env * env,ani_class cls,ani_static_method method,ani_ref * result,va_list args)3769 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Ref_V(ani_env *env, ani_class cls, ani_static_method method,
3770 ani_ref *result, va_list args)
3771 {
3772 ANI_DEBUG_TRACE(env);
3773 CHECK_ENV(env);
3774 CHECK_PTR_ARG(cls);
3775 CHECK_PTR_ARG(method);
3776 CHECK_PTR_ARG(result);
3777
3778 CheckStaticMethodReturnType(method, EtsType::OBJECT);
3779 return GeneralMethodCall<ani_ref>(env, nullptr, method, result, args);
3780 }
3781
3782 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Ref(ani_env * env,ani_class cls,ani_static_method method,ani_ref * result,...)3783 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Ref(ani_env *env, ani_class cls, ani_static_method method,
3784 ani_ref *result, ...)
3785 {
3786 ANI_DEBUG_TRACE(env);
3787
3788 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3789 va_start(args, result);
3790 ani_status status = Class_CallStaticMethod_Ref_V(env, cls, method, result, args);
3791 va_end(args);
3792 return status;
3793 }
3794
3795 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Ref_A(ani_env * env,ani_class cls,ani_static_method method,ani_ref * result,const ani_value * args)3796 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Ref_A(ani_env *env, ani_class cls, ani_static_method method,
3797 ani_ref *result, const ani_value *args)
3798 {
3799 ANI_DEBUG_TRACE(env);
3800 CHECK_ENV(env);
3801 CHECK_PTR_ARG(cls);
3802 CHECK_PTR_ARG(method);
3803 CHECK_PTR_ARG(result);
3804 CHECK_PTR_ARG(args);
3805
3806 CheckStaticMethodReturnType(method, EtsType::OBJECT);
3807 return GeneralMethodCall<ani_ref>(env, nullptr, method, result, args);
3808 }
3809
3810 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Void_V(ani_env * env,ani_class cls,ani_static_method method,va_list args)3811 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Void_V(ani_env *env, ani_class cls, ani_static_method method,
3812 va_list args)
3813 {
3814 ANI_DEBUG_TRACE(env);
3815 CHECK_ENV(env);
3816 CHECK_PTR_ARG(cls);
3817 CHECK_PTR_ARG(method);
3818
3819 CheckStaticMethodReturnType(method, EtsType::VOID);
3820 ani_boolean result;
3821 // Use any primitive type as template parameter and just ignore the result
3822 return GeneralMethodCall<EtsBoolean>(env, nullptr, method, &result, args);
3823 }
3824
3825 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Void(ani_env * env,ani_class cls,ani_static_method method,...)3826 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Void(ani_env *env, ani_class cls, ani_static_method method, ...)
3827 {
3828 ANI_DEBUG_TRACE(env);
3829
3830 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3831 va_start(args, method);
3832 ani_status status = Class_CallStaticMethod_Void_V(env, cls, method, args);
3833 va_end(args);
3834 return status;
3835 }
3836
3837 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethod_Void_A(ani_env * env,ani_class cls,ani_static_method method,const ani_value * args)3838 NO_UB_SANITIZE static ani_status Class_CallStaticMethod_Void_A(ani_env *env, ani_class cls, ani_static_method method,
3839 const ani_value *args)
3840 {
3841 ANI_DEBUG_TRACE(env);
3842 CHECK_ENV(env);
3843 CHECK_PTR_ARG(cls);
3844 CHECK_PTR_ARG(method);
3845 CHECK_PTR_ARG(args);
3846
3847 CheckStaticMethodReturnType(method, EtsType::VOID);
3848 ani_boolean result;
3849 // Use any primitive type as template parameter and just ignore the result
3850 return GeneralMethodCall<EtsBoolean>(env, nullptr, method, &result, args);
3851 }
3852
3853 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Boolean_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_boolean * result,va_list args)3854 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Boolean_V(ani_env *env, ani_class cls, const char *name,
3855 const char *signature, ani_boolean *result,
3856 va_list args)
3857 {
3858 ANI_DEBUG_TRACE(env);
3859
3860 return ClassCallMethodByName<EtsBoolean, EtsType::BOOLEAN>(env, cls, name, signature, result, args);
3861 }
3862
3863 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Boolean(ani_env * env,ani_class cls,const char * name,const char * signature,ani_boolean * result,...)3864 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Boolean(ani_env *env, ani_class cls, const char *name,
3865 const char *signature, ani_boolean *result, ...)
3866 {
3867 ANI_DEBUG_TRACE(env);
3868 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3869 va_start(args, result);
3870 ani_status status = Class_CallStaticMethodByName_Boolean_V(env, cls, name, signature, result, args);
3871 va_end(args);
3872 return status;
3873 }
3874
3875 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Boolean_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_boolean * result,const ani_value * args)3876 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Boolean_A(ani_env *env, ani_class cls, const char *name,
3877 const char *signature, ani_boolean *result,
3878 const ani_value *args)
3879 {
3880 ANI_DEBUG_TRACE(env);
3881
3882 CHECK_PTR_ARG(args);
3883 return ClassCallMethodByName<EtsBoolean, EtsType::BOOLEAN>(env, cls, name, signature, result, args);
3884 }
3885
3886 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Char_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_char * result,va_list args)3887 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Char_V(ani_env *env, ani_class cls, const char *name,
3888 const char *signature, ani_char *result,
3889 va_list args)
3890 {
3891 ANI_DEBUG_TRACE(env);
3892
3893 return ClassCallMethodByName<EtsChar, EtsType::CHAR>(env, cls, name, signature, result, args);
3894 }
3895
3896 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Char(ani_env * env,ani_class cls,const char * name,const char * signature,ani_char * result,...)3897 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Char(ani_env *env, ani_class cls, const char *name,
3898 const char *signature, ani_char *result, ...)
3899 {
3900 ANI_DEBUG_TRACE(env);
3901 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3902 va_start(args, result);
3903 ani_status status = Class_CallStaticMethodByName_Char_V(env, cls, name, signature, result, args);
3904 va_end(args);
3905 return status;
3906 }
3907
3908 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Char_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_char * result,const ani_value * args)3909 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Char_A(ani_env *env, ani_class cls, const char *name,
3910 const char *signature, ani_char *result,
3911 const ani_value *args)
3912 {
3913 ANI_DEBUG_TRACE(env);
3914
3915 CHECK_PTR_ARG(args);
3916 return ClassCallMethodByName<EtsChar, EtsType::CHAR>(env, cls, name, signature, result, args);
3917 }
3918
3919 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Byte_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_byte * result,va_list args)3920 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Byte_V(ani_env *env, ani_class cls, const char *name,
3921 const char *signature, ani_byte *result,
3922 va_list args)
3923 {
3924 ANI_DEBUG_TRACE(env);
3925
3926 return ClassCallMethodByName<EtsByte, EtsType::BYTE>(env, cls, name, signature, result, args);
3927 }
3928
3929 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Byte(ani_env * env,ani_class cls,const char * name,const char * signature,ani_byte * result,...)3930 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Byte(ani_env *env, ani_class cls, const char *name,
3931 const char *signature, ani_byte *result, ...)
3932 {
3933 ANI_DEBUG_TRACE(env);
3934 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3935 va_start(args, result);
3936 ani_status status = Class_CallStaticMethodByName_Byte_V(env, cls, name, signature, result, args);
3937 va_end(args);
3938 return status;
3939 }
3940
3941 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Byte_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_byte * result,const ani_value * args)3942 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Byte_A(ani_env *env, ani_class cls, const char *name,
3943 const char *signature, ani_byte *result,
3944 const ani_value *args)
3945 {
3946 ANI_DEBUG_TRACE(env);
3947
3948 CHECK_PTR_ARG(args);
3949 return ClassCallMethodByName<EtsByte, EtsType::BYTE>(env, cls, name, signature, result, args);
3950 }
3951
3952 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Short_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_short * result,va_list args)3953 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Short_V(ani_env *env, ani_class cls, const char *name,
3954 const char *signature, ani_short *result,
3955 va_list args)
3956 {
3957 ANI_DEBUG_TRACE(env);
3958
3959 return ClassCallMethodByName<EtsShort, EtsType::SHORT>(env, cls, name, signature, result, args);
3960 }
3961
3962 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Short(ani_env * env,ani_class cls,const char * name,const char * signature,ani_short * result,...)3963 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Short(ani_env *env, ani_class cls, const char *name,
3964 const char *signature, ani_short *result, ...)
3965 {
3966 ANI_DEBUG_TRACE(env);
3967 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
3968 va_start(args, result);
3969 ani_status status = Class_CallStaticMethodByName_Short_V(env, cls, name, signature, result, args);
3970 va_end(args);
3971 return status;
3972 }
3973
3974 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Short_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_short * result,const ani_value * args)3975 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Short_A(ani_env *env, ani_class cls, const char *name,
3976 const char *signature, ani_short *result,
3977 const ani_value *args)
3978 {
3979 ANI_DEBUG_TRACE(env);
3980
3981 CHECK_PTR_ARG(args);
3982 return ClassCallMethodByName<EtsShort, EtsType::SHORT>(env, cls, name, signature, result, args);
3983 }
3984
3985 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Int_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_int * result,const ani_value * args)3986 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Int_A(ani_env *env, ani_class cls, const char *name,
3987 const char *signature, ani_int *result,
3988 const ani_value *args)
3989 {
3990 ANI_DEBUG_TRACE(env);
3991
3992 CHECK_PTR_ARG(args);
3993 return ClassCallMethodByName<EtsInt, EtsType::INT>(env, cls, name, signature, result, args);
3994 }
3995
3996 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Int_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_int * result,va_list args)3997 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Int_V(ani_env *env, ani_class cls, const char *name,
3998 const char *signature, ani_int *result,
3999 va_list args)
4000 {
4001 ANI_DEBUG_TRACE(env);
4002
4003 return ClassCallMethodByName<EtsInt, EtsType::INT>(env, cls, name, signature, result, args);
4004 }
4005
4006 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Int(ani_env * env,ani_class cls,const char * name,const char * signature,ani_int * result,...)4007 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Int(ani_env *env, ani_class cls, const char *name,
4008 const char *signature, ani_int *result, ...)
4009 {
4010 ANI_DEBUG_TRACE(env);
4011
4012 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4013 va_start(args, result);
4014 ani_status status = Class_CallStaticMethodByName_Int_V(env, cls, name, signature, result, args);
4015 va_end(args);
4016 return status;
4017 }
4018
4019 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Long_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_long * result,const ani_value * args)4020 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Long_A(ani_env *env, ani_class cls, const char *name,
4021 const char *signature, ani_long *result,
4022 const ani_value *args)
4023 {
4024 ANI_DEBUG_TRACE(env);
4025
4026 CHECK_PTR_ARG(args);
4027 return ClassCallMethodByName<EtsLong, EtsType::LONG>(env, cls, name, signature, result, args);
4028 }
4029
4030 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Long_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_long * result,va_list args)4031 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Long_V(ani_env *env, ani_class cls, const char *name,
4032 const char *signature, ani_long *result,
4033 va_list args)
4034 {
4035 ANI_DEBUG_TRACE(env);
4036
4037 return ClassCallMethodByName<EtsLong, EtsType::LONG>(env, cls, name, signature, result, args);
4038 }
4039
4040 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Long(ani_env * env,ani_class cls,const char * name,const char * signature,ani_long * result,...)4041 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Long(ani_env *env, ani_class cls, const char *name,
4042 const char *signature, ani_long *result, ...)
4043 {
4044 ANI_DEBUG_TRACE(env);
4045
4046 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4047 va_start(args, result);
4048 ani_status status = Class_CallStaticMethodByName_Long_V(env, cls, name, signature, result, args);
4049 va_end(args);
4050 return status;
4051 }
4052
4053 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Float_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_float * result,const ani_value * args)4054 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Float_A(ani_env *env, ani_class cls, const char *name,
4055 const char *signature, ani_float *result,
4056 const ani_value *args)
4057 {
4058 ANI_DEBUG_TRACE(env);
4059
4060 CHECK_PTR_ARG(args);
4061 return ClassCallMethodByName<EtsFloat, EtsType::FLOAT>(env, cls, name, signature, result, args);
4062 }
4063
4064 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Float_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_float * result,va_list args)4065 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Float_V(ani_env *env, ani_class cls, const char *name,
4066 const char *signature, ani_float *result,
4067 va_list args)
4068 {
4069 ANI_DEBUG_TRACE(env);
4070
4071 return ClassCallMethodByName<EtsFloat, EtsType::FLOAT>(env, cls, name, signature, result, args);
4072 }
4073
4074 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Float(ani_env * env,ani_class cls,const char * name,const char * signature,ani_float * result,...)4075 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Float(ani_env *env, ani_class cls, const char *name,
4076 const char *signature, ani_float *result, ...)
4077 {
4078 ANI_DEBUG_TRACE(env);
4079
4080 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4081 va_start(args, result);
4082 ani_status status = Class_CallStaticMethodByName_Float_V(env, cls, name, signature, result, args);
4083 va_end(args);
4084 return status;
4085 }
4086
4087 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Double_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_double * result,const ani_value * args)4088 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Double_A(ani_env *env, ani_class cls, const char *name,
4089 const char *signature, ani_double *result,
4090 const ani_value *args)
4091 {
4092 ANI_DEBUG_TRACE(env);
4093
4094 CHECK_PTR_ARG(args);
4095 return ClassCallMethodByName<EtsDouble, EtsType::DOUBLE>(env, cls, name, signature, result, args);
4096 }
4097
4098 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Double_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_double * result,va_list args)4099 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Double_V(ani_env *env, ani_class cls, const char *name,
4100 const char *signature, ani_double *result,
4101 va_list args)
4102 {
4103 ANI_DEBUG_TRACE(env);
4104
4105 return ClassCallMethodByName<EtsDouble, EtsType::DOUBLE>(env, cls, name, signature, result, args);
4106 }
4107
4108 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Double(ani_env * env,ani_class cls,const char * name,const char * signature,ani_double * result,...)4109 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Double(ani_env *env, ani_class cls, const char *name,
4110 const char *signature, ani_double *result, ...)
4111 {
4112 ANI_DEBUG_TRACE(env);
4113
4114 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4115 va_start(args, result);
4116 ani_status status = Class_CallStaticMethodByName_Double_V(env, cls, name, signature, result, args);
4117 va_end(args);
4118 return status;
4119 }
4120
4121 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Ref_A(ani_env * env,ani_class cls,const char * name,const char * signature,ani_ref * result,const ani_value * args)4122 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Ref_A(ani_env *env, ani_class cls, const char *name,
4123 const char *signature, ani_ref *result,
4124 const ani_value *args)
4125 {
4126 ANI_DEBUG_TRACE(env);
4127
4128 CHECK_PTR_ARG(args);
4129 return ClassCallMethodByName<ani_ref, EtsType::OBJECT>(env, cls, name, signature, result, args);
4130 }
4131
4132 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Ref_V(ani_env * env,ani_class cls,const char * name,const char * signature,ani_ref * result,va_list args)4133 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Ref_V(ani_env *env, ani_class cls, const char *name,
4134 const char *signature, ani_ref *result,
4135 va_list args)
4136 {
4137 ANI_DEBUG_TRACE(env);
4138
4139 return ClassCallMethodByName<ani_ref, EtsType::OBJECT>(env, cls, name, signature, result, args);
4140 }
4141
4142 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Ref(ani_env * env,ani_class cls,const char * name,const char * signature,ani_ref * result,...)4143 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Ref(ani_env *env, ani_class cls, const char *name,
4144 const char *signature, ani_ref *result, ...)
4145 {
4146 ANI_DEBUG_TRACE(env);
4147
4148 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4149 va_start(args, result);
4150 ani_status status = Class_CallStaticMethodByName_Ref_V(env, cls, name, signature, result, args);
4151 va_end(args);
4152 return status;
4153 }
4154
4155 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Void_A(ani_env * env,ani_class cls,const char * name,const char * signature,const ani_value * args)4156 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Void_A(ani_env *env, ani_class cls, const char *name,
4157 const char *signature, const ani_value *args)
4158 {
4159 ANI_DEBUG_TRACE(env);
4160
4161 CHECK_PTR_ARG(args);
4162 ani_boolean result;
4163 return ClassCallMethodByName<EtsBoolean, EtsType::VOID>(env, cls, name, signature, &result, args);
4164 }
4165
4166 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Void_V(ani_env * env,ani_class cls,const char * name,const char * signature,va_list args)4167 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Void_V(ani_env *env, ani_class cls, const char *name,
4168 const char *signature, va_list args)
4169 {
4170 ANI_DEBUG_TRACE(env);
4171
4172 ani_boolean result;
4173 return ClassCallMethodByName<EtsBoolean, EtsType::VOID>(env, cls, name, signature, &result, args);
4174 }
4175
4176 // NOLINTNEXTLINE(readability-identifier-naming)
Class_CallStaticMethodByName_Void(ani_env * env,ani_class cls,const char * name,const char * signature,...)4177 NO_UB_SANITIZE static ani_status Class_CallStaticMethodByName_Void(ani_env *env, ani_class cls, const char *name,
4178 const char *signature, ...)
4179 {
4180 ANI_DEBUG_TRACE(env);
4181
4182 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4183 va_start(args, signature);
4184 ani_status status = Class_CallStaticMethodByName_Void_V(env, cls, name, signature, args);
4185 va_end(args);
4186 return status;
4187 }
4188
4189 // NOLINTNEXTLINE(readability-identifier-naming)
String_NewUTF8(ani_env * env,const char * utf8_string,ani_size size,ani_string * result)4190 NO_UB_SANITIZE static ani_status String_NewUTF8(ani_env *env, const char *utf8_string, ani_size size,
4191 ani_string *result)
4192 {
4193 ANI_DEBUG_TRACE(env);
4194 CHECK_ENV(env);
4195 CHECK_PTR_ARG(utf8_string);
4196 CHECK_PTR_ARG(result);
4197
4198 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
4199 auto internalString = EtsString::CreateFromUtf8(utf8_string, size);
4200 ANI_CHECK_RETURN_IF_EQ(internalString, nullptr, ANI_OUT_OF_MEMORY);
4201 return s.AddLocalRef(internalString->AsObject(), reinterpret_cast<ani_ref *>(result));
4202 }
4203
4204 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF8Size(ani_env * env,ani_string string,ani_size * result)4205 NO_UB_SANITIZE static ani_status String_GetUTF8Size(ani_env *env, ani_string string, ani_size *result)
4206 {
4207 ANI_DEBUG_TRACE(env);
4208 CHECK_ENV(env);
4209 CHECK_PTR_ARG(string);
4210 CHECK_PTR_ARG(result);
4211
4212 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
4213 auto internalString = s.ToInternalType(string);
4214 *result = internalString->GetUtf8Length();
4215 return ANI_OK;
4216 }
4217 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF8(ani_env * env,ani_string string,char * utf8Buffer,ani_size utf8BufferSize,ani_size * result)4218 NO_UB_SANITIZE static ani_status String_GetUTF8(ani_env *env, ani_string string, char *utf8Buffer,
4219 ani_size utf8BufferSize, ani_size *result)
4220 {
4221 ANI_DEBUG_TRACE(env);
4222 CHECK_ENV(env);
4223 CHECK_PTR_ARG(string);
4224 CHECK_PTR_ARG(utf8Buffer);
4225 CHECK_PTR_ARG(result);
4226
4227 ScopedManagedCodeFix s(env);
4228 auto internalString = s.ToInternalType(string);
4229 auto utf8Length = internalString->GetUtf8Length();
4230 if (UNLIKELY(utf8BufferSize < utf8Length || (utf8BufferSize - utf8Length) < 1)) {
4231 return ANI_BUFFER_TO_SMALL;
4232 }
4233 ani_size actualCopiedSize = internalString->CopyDataRegionUtf8(utf8Buffer, 0, utf8Length, utf8Length);
4234 ANI_CHECK_RETURN_IF_NE(actualCopiedSize, utf8Length, ANI_ERROR);
4235 utf8Buffer[actualCopiedSize] = '\0'; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
4236 *result = actualCopiedSize;
4237 return ANI_OK;
4238 }
4239
4240 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF8SubString(ani_env * env,ani_string string,ani_size substr_offset,ani_size substrSize,char * utfBuffer,ani_size utfBufferSize,ani_size * result)4241 NO_UB_SANITIZE static ani_status String_GetUTF8SubString(ani_env *env, ani_string string, ani_size substr_offset,
4242 ani_size substrSize, char *utfBuffer, ani_size utfBufferSize,
4243 ani_size *result)
4244 {
4245 ANI_DEBUG_TRACE(env);
4246 CHECK_ENV(env);
4247 CHECK_PTR_ARG(string);
4248 CHECK_PTR_ARG(utfBuffer);
4249 CHECK_PTR_ARG(result);
4250
4251 if (UNLIKELY(utfBufferSize < substrSize || (utfBufferSize - substrSize) < 1)) {
4252 return ANI_BUFFER_TO_SMALL;
4253 }
4254
4255 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
4256 EtsString *internalString = s.ToInternalType(string);
4257 auto utf8Length = internalString->GetUtf8Length();
4258 if (UNLIKELY(substr_offset > utf8Length || substrSize > (utf8Length - substr_offset))) {
4259 return ANI_OUT_OF_RANGE;
4260 }
4261 ani_size actualCopiedSize = internalString->CopyDataRegionUtf8(utfBuffer, substr_offset, substrSize, substrSize);
4262 utfBuffer[actualCopiedSize] = '\0'; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
4263 *result = actualCopiedSize;
4264 return ANI_OK;
4265 }
4266
4267 // NOLINTNEXTLINE(readability-identifier-naming)
String_NewUTF16(ani_env * env,const uint16_t * utf16_string,ani_size utf16_size,ani_string * result)4268 NO_UB_SANITIZE static ani_status String_NewUTF16(ani_env *env, const uint16_t *utf16_string, ani_size utf16_size,
4269 ani_string *result)
4270 {
4271 ANI_DEBUG_TRACE(env);
4272 CHECK_ENV(env);
4273 CHECK_PTR_ARG(utf16_string);
4274 CHECK_PTR_ARG(result);
4275
4276 ScopedManagedCodeFix s(env);
4277 auto internalString = EtsString::CreateFromUtf16(utf16_string, utf16_size);
4278 ANI_CHECK_RETURN_IF_EQ(internalString, nullptr, ANI_OUT_OF_MEMORY);
4279 return s.AddLocalRef(internalString->AsObject(), reinterpret_cast<ani_ref *>(result));
4280 }
4281
4282 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF16Size(ani_env * env,ani_string string,ani_size * result)4283 NO_UB_SANITIZE static ani_status String_GetUTF16Size(ani_env *env, ani_string string, ani_size *result)
4284 {
4285 ANI_DEBUG_TRACE(env);
4286 CHECK_ENV(env);
4287 CHECK_PTR_ARG(string);
4288 CHECK_PTR_ARG(result);
4289
4290 ScopedManagedCodeFix s(PandaEnv::FromAniEnv(env));
4291 auto internalString = s.ToInternalType(string);
4292 *result = internalString->GetUtf16Length();
4293 return ANI_OK;
4294 }
4295
4296 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF16(ani_env * env,ani_string string,uint16_t * utf16Buffer,ani_size utf16BufferSize,ani_size * result)4297 NO_UB_SANITIZE static ani_status String_GetUTF16(ani_env *env, ani_string string, uint16_t *utf16Buffer,
4298 ani_size utf16BufferSize, ani_size *result)
4299 {
4300 ANI_DEBUG_TRACE(env);
4301 CHECK_ENV(env);
4302 CHECK_PTR_ARG(string);
4303 CHECK_PTR_ARG(utf16Buffer);
4304 CHECK_PTR_ARG(result);
4305
4306 ScopedManagedCodeFix s(env);
4307 EtsString *internalString = s.ToInternalType(string);
4308 auto utf16Length = internalString->GetUtf16Length();
4309 if (UNLIKELY(utf16BufferSize < utf16Length || (utf16BufferSize - utf16Length) < 1)) {
4310 return ANI_BUFFER_TO_SMALL;
4311 }
4312 ani_size actualCopiedSize = internalString->CopyDataRegionUtf16(utf16Buffer, 0, utf16Length, utf16BufferSize);
4313 ANI_CHECK_RETURN_IF_NE(actualCopiedSize, utf16Length, ANI_ERROR);
4314 utf16Buffer[actualCopiedSize] = 0; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
4315 *result = actualCopiedSize;
4316 return ANI_OK;
4317 }
4318
4319 // NOLINTNEXTLINE(readability-identifier-naming)
String_GetUTF16SubString(ani_env * env,ani_string string,ani_size substr_offset,ani_size substrSize,uint16_t * utf16Buffer,ani_size utf16BufferSize,ani_size * result)4320 NO_UB_SANITIZE static ani_status String_GetUTF16SubString(ani_env *env, ani_string string, ani_size substr_offset,
4321 ani_size substrSize, uint16_t *utf16Buffer,
4322 ani_size utf16BufferSize, ani_size *result)
4323 {
4324 ANI_DEBUG_TRACE(env);
4325 CHECK_ENV(env);
4326 CHECK_PTR_ARG(string);
4327 CHECK_PTR_ARG(utf16Buffer);
4328 CHECK_PTR_ARG(result);
4329 if (UNLIKELY(utf16BufferSize < substrSize) || (utf16BufferSize - substrSize) < 1) {
4330 return ANI_BUFFER_TO_SMALL;
4331 }
4332 ScopedManagedCodeFix s(env);
4333 EtsString *internalString = s.ToInternalType(string);
4334 auto utf16Length = internalString->GetUtf16Length();
4335 if (UNLIKELY(substr_offset > utf16Length || substrSize > (utf16Length - substr_offset))) {
4336 return ANI_OUT_OF_RANGE;
4337 }
4338 ani_size actualCopiedSize = internalString->CopyDataRegionUtf16(utf16Buffer, substr_offset, substrSize, substrSize);
4339 ANI_CHECK_RETURN_IF_NE(actualCopiedSize, substrSize, ANI_ERROR);
4340 utf16Buffer[actualCopiedSize] = 0; // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
4341 *result = actualCopiedSize;
4342 return ANI_OK;
4343 }
4344
4345 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Boolean_V(ani_env * env,ani_object object,ani_method method,ani_boolean * result,va_list args)4346 NO_UB_SANITIZE static ani_status Object_CallMethod_Boolean_V(ani_env *env, ani_object object, ani_method method,
4347 ani_boolean *result, va_list args)
4348 {
4349 ANI_DEBUG_TRACE(env);
4350 CHECK_ENV(env);
4351 CHECK_PTR_ARG(object);
4352 CHECK_PTR_ARG(method);
4353 CHECK_PTR_ARG(result);
4354
4355 CheckMethodReturnType(method, EtsType::BOOLEAN);
4356 return GeneralMethodCall<EtsBoolean>(env, object, method, result, args);
4357 }
4358
4359 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Boolean(ani_env * env,ani_object object,ani_method method,ani_boolean * result,...)4360 NO_UB_SANITIZE static ani_status Object_CallMethod_Boolean(ani_env *env, ani_object object, ani_method method,
4361 ani_boolean *result, ...)
4362 {
4363 ANI_DEBUG_TRACE(env);
4364
4365 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4366 va_start(args, result);
4367 ani_status res = Object_CallMethod_Boolean_V(env, object, method, result, args);
4368 va_end(args);
4369 return res;
4370 }
4371
4372 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Boolean_A(ani_env * env,ani_object object,ani_method method,ani_boolean * result,const ani_value * args)4373 NO_UB_SANITIZE static ani_status Object_CallMethod_Boolean_A(ani_env *env, ani_object object, ani_method method,
4374 ani_boolean *result, const ani_value *args)
4375 {
4376 ANI_DEBUG_TRACE(env);
4377 CHECK_ENV(env);
4378 CHECK_PTR_ARG(object);
4379 CHECK_PTR_ARG(method);
4380 CHECK_PTR_ARG(result);
4381 CHECK_PTR_ARG(args);
4382
4383 CheckMethodReturnType(method, EtsType::BOOLEAN);
4384 return GeneralMethodCall<EtsBoolean>(env, object, method, result, args);
4385 }
4386
4387 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Char_V(ani_env * env,ani_object object,ani_method method,ani_char * result,va_list args)4388 NO_UB_SANITIZE static ani_status Object_CallMethod_Char_V(ani_env *env, ani_object object, ani_method method,
4389 ani_char *result, va_list args)
4390 {
4391 ANI_DEBUG_TRACE(env);
4392 CHECK_ENV(env);
4393 CHECK_PTR_ARG(object);
4394 CHECK_PTR_ARG(method);
4395 CHECK_PTR_ARG(result);
4396
4397 CheckMethodReturnType(method, EtsType::CHAR);
4398 return GeneralMethodCall<EtsChar>(env, object, method, result, args);
4399 }
4400
4401 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Char(ani_env * env,ani_object object,ani_method method,ani_char * result,...)4402 NO_UB_SANITIZE static ani_status Object_CallMethod_Char(ani_env *env, ani_object object, ani_method method,
4403 ani_char *result, ...)
4404 {
4405 ANI_DEBUG_TRACE(env);
4406
4407 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4408 va_start(args, result);
4409 ani_status status = Object_CallMethod_Char_V(env, object, method, result, args);
4410 va_end(args);
4411 return status;
4412 }
4413
4414 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Char_A(ani_env * env,ani_object object,ani_method method,ani_char * result,const ani_value * args)4415 NO_UB_SANITIZE static ani_status Object_CallMethod_Char_A(ani_env *env, ani_object object, ani_method method,
4416 ani_char *result, const ani_value *args)
4417 {
4418 ANI_DEBUG_TRACE(env);
4419 CHECK_ENV(env);
4420 CHECK_PTR_ARG(object);
4421 CHECK_PTR_ARG(method);
4422 CHECK_PTR_ARG(result);
4423 CHECK_PTR_ARG(args);
4424
4425 CheckMethodReturnType(method, EtsType::CHAR);
4426 return GeneralMethodCall<EtsChar>(env, object, method, result, args);
4427 }
4428
4429 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Byte_V(ani_env * env,ani_object object,ani_method method,ani_byte * result,va_list args)4430 NO_UB_SANITIZE static ani_status Object_CallMethod_Byte_V(ani_env *env, ani_object object, ani_method method,
4431 ani_byte *result, va_list args)
4432 {
4433 ANI_DEBUG_TRACE(env);
4434 CHECK_ENV(env);
4435 CHECK_PTR_ARG(object);
4436 CHECK_PTR_ARG(method);
4437 CHECK_PTR_ARG(result);
4438
4439 CheckMethodReturnType(method, EtsType::BYTE);
4440 return GeneralMethodCall<EtsByte>(env, object, method, result, args);
4441 }
4442
4443 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Byte(ani_env * env,ani_object object,ani_method method,ani_byte * result,...)4444 NO_UB_SANITIZE static ani_status Object_CallMethod_Byte(ani_env *env, ani_object object, ani_method method,
4445 ani_byte *result, ...)
4446 {
4447 ANI_DEBUG_TRACE(env);
4448
4449 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4450 va_start(args, result);
4451 ani_status status = Object_CallMethod_Byte_V(env, object, method, result, args);
4452 va_end(args);
4453 return status;
4454 }
4455
4456 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Byte_A(ani_env * env,ani_object object,ani_method method,ani_byte * result,const ani_value * args)4457 NO_UB_SANITIZE static ani_status Object_CallMethod_Byte_A(ani_env *env, ani_object object, ani_method method,
4458 ani_byte *result, const ani_value *args)
4459 {
4460 ANI_DEBUG_TRACE(env);
4461 CHECK_ENV(env);
4462 CHECK_PTR_ARG(object);
4463 CHECK_PTR_ARG(method);
4464 CHECK_PTR_ARG(result);
4465 CHECK_PTR_ARG(args);
4466
4467 CheckMethodReturnType(method, EtsType::BYTE);
4468 return GeneralMethodCall<EtsByte>(env, object, method, result, args);
4469 }
4470
4471 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Short_V(ani_env * env,ani_object object,ani_method method,ani_short * result,va_list args)4472 NO_UB_SANITIZE static ani_status Object_CallMethod_Short_V(ani_env *env, ani_object object, ani_method method,
4473 ani_short *result, va_list args)
4474 {
4475 ANI_DEBUG_TRACE(env);
4476 CHECK_ENV(env);
4477 CHECK_PTR_ARG(object);
4478 CHECK_PTR_ARG(method);
4479 CHECK_PTR_ARG(result);
4480
4481 CheckMethodReturnType(method, EtsType::SHORT);
4482 return GeneralMethodCall<EtsShort>(env, object, method, result, args);
4483 }
4484
4485 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Short(ani_env * env,ani_object object,ani_method method,ani_short * result,...)4486 NO_UB_SANITIZE static ani_status Object_CallMethod_Short(ani_env *env, ani_object object, ani_method method,
4487 ani_short *result, ...)
4488 {
4489 ANI_DEBUG_TRACE(env);
4490
4491 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4492 va_start(args, result);
4493 ani_status status = Object_CallMethod_Short_V(env, object, method, result, args);
4494 va_end(args);
4495 return status;
4496 }
4497
4498 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Short_A(ani_env * env,ani_object object,ani_method method,ani_short * result,const ani_value * args)4499 NO_UB_SANITIZE static ani_status Object_CallMethod_Short_A(ani_env *env, ani_object object, ani_method method,
4500 ani_short *result, const ani_value *args)
4501 {
4502 ANI_DEBUG_TRACE(env);
4503 CHECK_ENV(env);
4504 CHECK_PTR_ARG(object);
4505 CHECK_PTR_ARG(method);
4506 CHECK_PTR_ARG(result);
4507 CHECK_PTR_ARG(args);
4508
4509 CheckMethodReturnType(method, EtsType::SHORT);
4510 return GeneralMethodCall<EtsShort>(env, object, method, result, args);
4511 }
4512
4513 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Int_V(ani_env * env,ani_object object,ani_method method,ani_int * result,va_list args)4514 NO_UB_SANITIZE static ani_status Object_CallMethod_Int_V(ani_env *env, ani_object object, ani_method method,
4515 ani_int *result, va_list args)
4516 {
4517 ANI_DEBUG_TRACE(env);
4518 CHECK_ENV(env);
4519 CHECK_PTR_ARG(object);
4520 CHECK_PTR_ARG(method);
4521 CHECK_PTR_ARG(result);
4522
4523 CheckMethodReturnType(method, EtsType::INT);
4524 return GeneralMethodCall<EtsInt>(env, object, method, result, args);
4525 }
4526
4527 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Int(ani_env * env,ani_object object,ani_method method,ani_int * result,...)4528 NO_UB_SANITIZE static ani_status Object_CallMethod_Int(ani_env *env, ani_object object, ani_method method,
4529 ani_int *result, ...)
4530 {
4531 ANI_DEBUG_TRACE(env);
4532
4533 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4534 va_start(args, result);
4535 ani_status status = Object_CallMethod_Int_V(env, object, method, result, args);
4536 va_end(args);
4537 return status;
4538 }
4539
4540 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Int_A(ani_env * env,ani_object object,ani_method method,ani_int * result,const ani_value * args)4541 NO_UB_SANITIZE static ani_status Object_CallMethod_Int_A(ani_env *env, ani_object object, ani_method method,
4542 ani_int *result, const ani_value *args)
4543 {
4544 ANI_DEBUG_TRACE(env);
4545 CHECK_ENV(env);
4546 CHECK_PTR_ARG(object);
4547 CHECK_PTR_ARG(method);
4548 CHECK_PTR_ARG(result);
4549 CHECK_PTR_ARG(args);
4550
4551 CheckMethodReturnType(method, EtsType::INT);
4552 return GeneralMethodCall<EtsInt>(env, object, method, result, args);
4553 }
4554
4555 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Long_A(ani_env * env,ani_object object,ani_method method,ani_long * result,const ani_value * args)4556 NO_UB_SANITIZE static ani_status Object_CallMethod_Long_A(ani_env *env, ani_object object, ani_method method,
4557 ani_long *result, const ani_value *args)
4558 {
4559 ANI_DEBUG_TRACE(env);
4560 CHECK_ENV(env);
4561 CHECK_PTR_ARG(object);
4562 CHECK_PTR_ARG(method);
4563 CHECK_PTR_ARG(result);
4564 CHECK_PTR_ARG(args);
4565
4566 CheckMethodReturnType(method, EtsType::LONG);
4567 return GeneralMethodCall<EtsLong>(env, object, method, result, args);
4568 }
4569
4570 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Long_V(ani_env * env,ani_object object,ani_method method,ani_long * result,va_list args)4571 NO_UB_SANITIZE static ani_status Object_CallMethod_Long_V(ani_env *env, ani_object object, ani_method method,
4572 ani_long *result, va_list args)
4573 {
4574 ANI_DEBUG_TRACE(env);
4575 CHECK_ENV(env);
4576 CHECK_PTR_ARG(object);
4577 CHECK_PTR_ARG(method);
4578 CHECK_PTR_ARG(result);
4579
4580 CheckMethodReturnType(method, EtsType::LONG);
4581 return GeneralMethodCall<EtsLong>(env, object, method, result, args);
4582 }
4583
4584 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Long(ani_env * env,ani_object object,ani_method method,ani_long * result,...)4585 NO_UB_SANITIZE static ani_status Object_CallMethod_Long(ani_env *env, ani_object object, ani_method method,
4586 ani_long *result, ...)
4587 {
4588 ANI_DEBUG_TRACE(env);
4589
4590 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4591 va_start(args, result);
4592 ani_status aniResult = Object_CallMethod_Long_V(env, object, method, result, args);
4593 va_end(args);
4594 return aniResult;
4595 }
4596
4597 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Float_V(ani_env * env,ani_object object,ani_method method,ani_float * result,va_list args)4598 NO_UB_SANITIZE static ani_status Object_CallMethod_Float_V(ani_env *env, ani_object object, ani_method method,
4599 ani_float *result, va_list args)
4600 {
4601 ANI_DEBUG_TRACE(env);
4602 CHECK_ENV(env);
4603 CHECK_PTR_ARG(object);
4604 CHECK_PTR_ARG(method);
4605 CHECK_PTR_ARG(result);
4606
4607 CheckMethodReturnType(method, EtsType::FLOAT);
4608 return GeneralMethodCall<EtsFloat>(env, object, method, result, args);
4609 }
4610
4611 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Float(ani_env * env,ani_object object,ani_method method,ani_float * result,...)4612 NO_UB_SANITIZE static ani_status Object_CallMethod_Float(ani_env *env, ani_object object, ani_method method,
4613 ani_float *result, ...)
4614 {
4615 ANI_DEBUG_TRACE(env);
4616
4617 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4618 va_start(args, result);
4619 ani_status status = Object_CallMethod_Float_V(env, object, method, result, args);
4620 va_end(args);
4621 return status;
4622 }
4623
4624 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Float_A(ani_env * env,ani_object object,ani_method method,ani_float * result,const ani_value * args)4625 NO_UB_SANITIZE static ani_status Object_CallMethod_Float_A(ani_env *env, ani_object object, ani_method method,
4626 ani_float *result, const ani_value *args)
4627 {
4628 ANI_DEBUG_TRACE(env);
4629 CHECK_ENV(env);
4630 CHECK_PTR_ARG(object);
4631 CHECK_PTR_ARG(method);
4632 CHECK_PTR_ARG(result);
4633 CHECK_PTR_ARG(args);
4634
4635 CheckMethodReturnType(method, EtsType::FLOAT);
4636 return GeneralMethodCall<EtsFloat>(env, object, method, result, args);
4637 }
4638
4639 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Double_V(ani_env * env,ani_object object,ani_method method,ani_double * result,va_list args)4640 NO_UB_SANITIZE static ani_status Object_CallMethod_Double_V(ani_env *env, ani_object object, ani_method method,
4641 ani_double *result, va_list args)
4642 {
4643 ANI_DEBUG_TRACE(env);
4644 CHECK_ENV(env);
4645 CHECK_PTR_ARG(object);
4646 CHECK_PTR_ARG(method);
4647 CHECK_PTR_ARG(result);
4648
4649 CheckMethodReturnType(method, EtsType::DOUBLE);
4650 return GeneralMethodCall<EtsDouble>(env, object, method, result, args);
4651 }
4652
4653 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Double(ani_env * env,ani_object object,ani_method method,ani_double * result,...)4654 NO_UB_SANITIZE static ani_status Object_CallMethod_Double(ani_env *env, ani_object object, ani_method method,
4655 ani_double *result, ...)
4656 {
4657 ANI_DEBUG_TRACE(env);
4658
4659 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4660 va_start(args, result);
4661 ani_status status = Object_CallMethod_Double_V(env, object, method, result, args);
4662 va_end(args);
4663 return status;
4664 }
4665
4666 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Double_A(ani_env * env,ani_object object,ani_method method,ani_double * result,const ani_value * args)4667 NO_UB_SANITIZE static ani_status Object_CallMethod_Double_A(ani_env *env, ani_object object, ani_method method,
4668 ani_double *result, const ani_value *args)
4669 {
4670 ANI_DEBUG_TRACE(env);
4671 CHECK_ENV(env);
4672 CHECK_PTR_ARG(object);
4673 CHECK_PTR_ARG(method);
4674 CHECK_PTR_ARG(result);
4675 CHECK_PTR_ARG(args);
4676
4677 CheckMethodReturnType(method, EtsType::DOUBLE);
4678 return GeneralMethodCall<EtsDouble>(env, object, method, result, args);
4679 }
4680
4681 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Ref_V(ani_env * env,ani_object object,ani_method method,ani_ref * result,va_list args)4682 NO_UB_SANITIZE static ani_status Object_CallMethod_Ref_V(ani_env *env, ani_object object, ani_method method,
4683 ani_ref *result, va_list args)
4684 {
4685 ANI_DEBUG_TRACE(env);
4686 CHECK_ENV(env);
4687 CHECK_PTR_ARG(object);
4688 CHECK_PTR_ARG(method);
4689 CHECK_PTR_ARG(result);
4690
4691 CheckMethodReturnType(method, EtsType::OBJECT);
4692 return GeneralMethodCall<ani_ref>(env, object, method, result, args);
4693 }
4694
4695 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Ref(ani_env * env,ani_object object,ani_method method,ani_ref * result,...)4696 NO_UB_SANITIZE static ani_status Object_CallMethod_Ref(ani_env *env, ani_object object, ani_method method,
4697 ani_ref *result, ...)
4698 {
4699 ANI_DEBUG_TRACE(env);
4700
4701 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4702 va_start(args, result);
4703 ani_status status = Object_CallMethod_Ref_V(env, object, method, result, args);
4704 va_end(args);
4705 return status;
4706 }
4707
4708 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Ref_A(ani_env * env,ani_object object,ani_method method,ani_ref * result,const ani_value * args)4709 NO_UB_SANITIZE static ani_status Object_CallMethod_Ref_A(ani_env *env, ani_object object, ani_method method,
4710 ani_ref *result, const ani_value *args)
4711 {
4712 ANI_DEBUG_TRACE(env);
4713 CHECK_ENV(env);
4714 CHECK_PTR_ARG(object);
4715 CHECK_PTR_ARG(method);
4716 CHECK_PTR_ARG(result);
4717 CHECK_PTR_ARG(args);
4718
4719 CheckMethodReturnType(method, EtsType::OBJECT);
4720 return GeneralMethodCall<ani_ref>(env, object, method, result, args);
4721 }
4722
4723 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Void_A(ani_env * env,ani_object object,ani_method method,const ani_value * args)4724 NO_UB_SANITIZE static ani_status Object_CallMethod_Void_A(ani_env *env, ani_object object, ani_method method,
4725 const ani_value *args)
4726 {
4727 ANI_DEBUG_TRACE(env);
4728 CHECK_ENV(env);
4729 CHECK_PTR_ARG(object);
4730 CHECK_PTR_ARG(method);
4731 CHECK_PTR_ARG(args);
4732
4733 CheckMethodReturnType(method, EtsType::VOID);
4734 ani_boolean result;
4735 // Use any primitive type as template parameter and just ignore the result
4736 return GeneralMethodCall<EtsBoolean>(env, object, method, &result, args);
4737 }
4738
4739 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Void_V(ani_env * env,ani_object object,ani_method method,va_list args)4740 NO_UB_SANITIZE static ani_status Object_CallMethod_Void_V(ani_env *env, ani_object object, ani_method method,
4741 va_list args)
4742 {
4743 ANI_DEBUG_TRACE(env);
4744 CHECK_ENV(env);
4745 CHECK_PTR_ARG(object);
4746 CHECK_PTR_ARG(method);
4747
4748 CheckMethodReturnType(method, EtsType::VOID);
4749 ani_boolean result;
4750 // Use any primitive type as template parameter and just ignore the result
4751 return GeneralMethodCall<EtsBoolean>(env, object, method, &result, args);
4752 }
4753
4754 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethod_Void(ani_env * env,ani_object object,ani_method method,...)4755 NO_UB_SANITIZE static ani_status Object_CallMethod_Void(ani_env *env, ani_object object, ani_method method, ...)
4756 {
4757 ANI_DEBUG_TRACE(env);
4758
4759 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4760 va_start(args, method);
4761 ani_status status = Object_CallMethod_Void_V(env, object, method, args);
4762 va_end(args);
4763 return status;
4764 }
4765
4766 template <typename R>
DoVariableGetValue(ani_env * env,ani_variable variable,R * result)4767 static ani_status DoVariableGetValue(ani_env *env, ani_variable variable, R *result)
4768 {
4769 CHECK_ENV(env);
4770 CHECK_PTR_ARG(variable);
4771 CHECK_PTR_ARG(result);
4772
4773 static constexpr auto IS_REF = std::is_same_v<R, ani_ref>;
4774 using Res = std::conditional_t<IS_REF, EtsObject *, R>;
4775
4776 ScopedManagedCodeFix s(env);
4777 EtsVariable *internalVariable = ToInternalVariable(variable);
4778 EtsField *field = internalVariable->AsField();
4779 ANI_CHECK_RETURN_IF_NE(field->GetEtsType(), AniTypeInfo<R>::ETS_TYPE_VALUE, ANI_INVALID_TYPE);
4780
4781 EtsClass *cls = field->GetDeclaringClass();
4782 ani_status status = InitializeClass(s, cls);
4783 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
4784
4785 Res etsRes {};
4786 if constexpr (IS_REF) {
4787 etsRes = cls->GetStaticFieldObject(field);
4788 return s.AddLocalRef(etsRes, result);
4789 } else {
4790 etsRes = cls->GetStaticFieldPrimitive<R>(field);
4791 *result = etsRes;
4792 return ANI_OK;
4793 }
4794 }
4795
4796 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Boolean(ani_env * env,ani_variable variable,ani_boolean * result)4797 NO_UB_SANITIZE static ani_status Variable_GetValue_Boolean(ani_env *env, ani_variable variable, ani_boolean *result)
4798 {
4799 ANI_DEBUG_TRACE(env);
4800 return DoVariableGetValue(env, variable, result);
4801 }
4802
4803 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Char(ani_env * env,ani_variable variable,ani_char * result)4804 NO_UB_SANITIZE static ani_status Variable_GetValue_Char(ani_env *env, ani_variable variable, ani_char *result)
4805 {
4806 ANI_DEBUG_TRACE(env);
4807 return DoVariableGetValue(env, variable, result);
4808 }
4809
4810 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Byte(ani_env * env,ani_variable variable,ani_byte * result)4811 NO_UB_SANITIZE static ani_status Variable_GetValue_Byte(ani_env *env, ani_variable variable, ani_byte *result)
4812 {
4813 ANI_DEBUG_TRACE(env);
4814 return DoVariableGetValue(env, variable, result);
4815 }
4816
4817 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Short(ani_env * env,ani_variable variable,ani_short * result)4818 NO_UB_SANITIZE static ani_status Variable_GetValue_Short(ani_env *env, ani_variable variable, ani_short *result)
4819 {
4820 ANI_DEBUG_TRACE(env);
4821 return DoVariableGetValue(env, variable, result);
4822 }
4823
4824 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Int(ani_env * env,ani_variable variable,ani_int * result)4825 NO_UB_SANITIZE static ani_status Variable_GetValue_Int(ani_env *env, ani_variable variable, ani_int *result)
4826 {
4827 ANI_DEBUG_TRACE(env);
4828 return DoVariableGetValue(env, variable, result);
4829 }
4830
4831 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Long(ani_env * env,ani_variable variable,ani_long * result)4832 NO_UB_SANITIZE static ani_status Variable_GetValue_Long(ani_env *env, ani_variable variable, ani_long *result)
4833 {
4834 ANI_DEBUG_TRACE(env);
4835 return DoVariableGetValue(env, variable, result);
4836 }
4837
4838 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Float(ani_env * env,ani_variable variable,ani_float * result)4839 NO_UB_SANITIZE static ani_status Variable_GetValue_Float(ani_env *env, ani_variable variable, ani_float *result)
4840 {
4841 ANI_DEBUG_TRACE(env);
4842 return DoVariableGetValue(env, variable, result);
4843 }
4844
4845 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Double(ani_env * env,ani_variable variable,ani_double * result)4846 NO_UB_SANITIZE static ani_status Variable_GetValue_Double(ani_env *env, ani_variable variable, ani_double *result)
4847 {
4848 ANI_DEBUG_TRACE(env);
4849 return DoVariableGetValue(env, variable, result);
4850 }
4851
4852 // NOLINTNEXTLINE(readability-identifier-naming)
Variable_GetValue_Ref(ani_env * env,ani_variable variable,ani_ref * result)4853 NO_UB_SANITIZE static ani_status Variable_GetValue_Ref(ani_env *env, ani_variable variable, ani_ref *result)
4854 {
4855 ANI_DEBUG_TRACE(env);
4856 return DoVariableGetValue(env, variable, result);
4857 }
4858
4859 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Boolean_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_boolean * result,const ani_value * args)4860 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Boolean_A(ani_env *env, ani_object object, const char *name,
4861 const char *signature, ani_boolean *result,
4862 const ani_value *args)
4863 {
4864 ANI_DEBUG_TRACE(env);
4865
4866 CHECK_PTR_ARG(args);
4867 return ObjectCallMethodByName<EtsBoolean, EtsType::BOOLEAN>(env, object, name, signature, result, args);
4868 }
4869
4870 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Boolean_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_boolean * result,va_list args)4871 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Boolean_V(ani_env *env, ani_object object, const char *name,
4872 const char *signature, ani_boolean *result,
4873 va_list args)
4874 {
4875 ANI_DEBUG_TRACE(env);
4876
4877 return ObjectCallMethodByName<EtsBoolean, EtsType::BOOLEAN>(env, object, name, signature, result, args);
4878 }
4879
4880 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Boolean(ani_env * env,ani_object object,const char * name,const char * signature,ani_boolean * result,...)4881 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Boolean(ani_env *env, ani_object object, const char *name,
4882 const char *signature, ani_boolean *result, ...)
4883 {
4884 ANI_DEBUG_TRACE(env);
4885 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4886 va_start(args, result);
4887 ani_status status = Object_CallMethodByName_Boolean_V(env, object, name, signature, result, args);
4888 va_end(args);
4889 return status;
4890 }
4891
4892 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Char_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_char * result,const ani_value * args)4893 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Char_A(ani_env *env, ani_object object, const char *name,
4894 const char *signature, ani_char *result,
4895 const ani_value *args)
4896 {
4897 ANI_DEBUG_TRACE(env);
4898 CHECK_PTR_ARG(args);
4899 return ObjectCallMethodByName<EtsChar, EtsType::CHAR>(env, object, name, signature, result, args);
4900 }
4901
4902 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Char_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_char * result,va_list args)4903 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Char_V(ani_env *env, ani_object object, const char *name,
4904 const char *signature, ani_char *result, va_list args)
4905 {
4906 ANI_DEBUG_TRACE(env);
4907 return ObjectCallMethodByName<EtsChar, EtsType::CHAR>(env, object, name, signature, result, args);
4908 }
4909
4910 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Char(ani_env * env,ani_object object,const char * name,const char * signature,ani_char * result,...)4911 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Char(ani_env *env, ani_object object, const char *name,
4912 const char *signature, ani_char *result, ...)
4913 {
4914 ANI_DEBUG_TRACE(env);
4915 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4916 va_start(args, result);
4917 ani_status status = Object_CallMethodByName_Char_V(env, object, name, signature, result, args);
4918 va_end(args);
4919 return status;
4920 }
4921
4922 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Byte_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_byte * result,const ani_value * args)4923 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Byte_A(ani_env *env, ani_object object, const char *name,
4924 const char *signature, ani_byte *result,
4925 const ani_value *args)
4926 {
4927 ANI_DEBUG_TRACE(env);
4928
4929 CHECK_PTR_ARG(args);
4930 return ObjectCallMethodByName<EtsByte, EtsType::BYTE>(env, object, name, signature, result, args);
4931 }
4932
4933 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Byte_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_byte * result,va_list args)4934 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Byte_V(ani_env *env, ani_object object, const char *name,
4935 const char *signature, ani_byte *result, va_list args)
4936 {
4937 ANI_DEBUG_TRACE(env);
4938
4939 return ObjectCallMethodByName<EtsByte, EtsType::BYTE>(env, object, name, signature, result, args);
4940 }
4941
4942 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Byte(ani_env * env,ani_object object,const char * name,const char * signature,ani_byte * result,...)4943 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Byte(ani_env *env, ani_object object, const char *name,
4944 const char *signature, ani_byte *result, ...)
4945 {
4946 ANI_DEBUG_TRACE(env);
4947 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4948 va_start(args, result);
4949 ani_status status = Object_CallMethodByName_Byte_V(env, object, name, signature, result, args);
4950 va_end(args);
4951 return status;
4952 }
4953
4954 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Short_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_short * result,const ani_value * args)4955 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Short_A(ani_env *env, ani_object object, const char *name,
4956 const char *signature, ani_short *result,
4957 const ani_value *args)
4958 {
4959 ANI_DEBUG_TRACE(env);
4960
4961 CHECK_PTR_ARG(args);
4962 return ObjectCallMethodByName<EtsShort, EtsType::SHORT>(env, object, name, signature, result, args);
4963 }
4964
4965 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Short_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_short * result,va_list args)4966 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Short_V(ani_env *env, ani_object object, const char *name,
4967 const char *signature, ani_short *result, va_list args)
4968 {
4969 ANI_DEBUG_TRACE(env);
4970
4971 return ObjectCallMethodByName<EtsShort, EtsType::SHORT>(env, object, name, signature, result, args);
4972 }
4973
4974 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Short(ani_env * env,ani_object object,const char * name,const char * signature,ani_short * result,...)4975 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Short(ani_env *env, ani_object object, const char *name,
4976 const char *signature, ani_short *result, ...)
4977 {
4978 ANI_DEBUG_TRACE(env);
4979 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
4980 va_start(args, result);
4981 ani_status status = Object_CallMethodByName_Short_V(env, object, name, signature, result, args);
4982 va_end(args);
4983 return status;
4984 }
4985
4986 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Int_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_int * result,const ani_value * args)4987 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Int_A(ani_env *env, ani_object object, const char *name,
4988 const char *signature, ani_int *result,
4989 const ani_value *args)
4990 {
4991 ANI_DEBUG_TRACE(env);
4992
4993 CHECK_PTR_ARG(args);
4994 return ObjectCallMethodByName<EtsInt, EtsType::INT>(env, object, name, signature, result, args);
4995 }
4996
4997 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Int_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_int * result,va_list args)4998 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Int_V(ani_env *env, ani_object object, const char *name,
4999 const char *signature, ani_int *result, va_list args)
5000 {
5001 ANI_DEBUG_TRACE(env);
5002
5003 return ObjectCallMethodByName<EtsInt, EtsType::INT>(env, object, name, signature, result, args);
5004 }
5005
5006 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Int(ani_env * env,ani_object object,const char * name,const char * signature,ani_int * result,...)5007 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Int(ani_env *env, ani_object object, const char *name,
5008 const char *signature, ani_int *result, ...)
5009 {
5010 ANI_DEBUG_TRACE(env);
5011 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5012 va_start(args, result);
5013 ani_status status = Object_CallMethodByName_Int_V(env, object, name, signature, result, args);
5014 va_end(args);
5015 return status;
5016 }
5017
5018 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Long_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_long * result,const ani_value * args)5019 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Long_A(ani_env *env, ani_object object, const char *name,
5020 const char *signature, ani_long *result,
5021 const ani_value *args)
5022 {
5023 ANI_DEBUG_TRACE(env);
5024
5025 CHECK_PTR_ARG(args);
5026 return ObjectCallMethodByName<EtsLong, EtsType::LONG>(env, object, name, signature, result, args);
5027 }
5028
5029 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Long_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_long * result,va_list args)5030 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Long_V(ani_env *env, ani_object object, const char *name,
5031 const char *signature, ani_long *result, va_list args)
5032 {
5033 ANI_DEBUG_TRACE(env);
5034
5035 return ObjectCallMethodByName<EtsLong, EtsType::LONG>(env, object, name, signature, result, args);
5036 }
5037
5038 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Long(ani_env * env,ani_object object,const char * name,const char * signature,ani_long * result,...)5039 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Long(ani_env *env, ani_object object, const char *name,
5040 const char *signature, ani_long *result, ...)
5041 {
5042 ANI_DEBUG_TRACE(env);
5043 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5044 va_start(args, result);
5045 ani_status status = Object_CallMethodByName_Long_V(env, object, name, signature, result, args);
5046 va_end(args);
5047 return status;
5048 }
5049
5050 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Float_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_float * result,const ani_value * args)5051 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Float_A(ani_env *env, ani_object object, const char *name,
5052 const char *signature, ani_float *result,
5053 const ani_value *args)
5054 {
5055 ANI_DEBUG_TRACE(env);
5056
5057 CHECK_PTR_ARG(args);
5058 return ObjectCallMethodByName<EtsFloat, EtsType::FLOAT>(env, object, name, signature, result, args);
5059 }
5060
5061 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Float_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_float * result,va_list args)5062 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Float_V(ani_env *env, ani_object object, const char *name,
5063 const char *signature, ani_float *result, va_list args)
5064 {
5065 ANI_DEBUG_TRACE(env);
5066
5067 return ObjectCallMethodByName<EtsFloat, EtsType::FLOAT>(env, object, name, signature, result, args);
5068 }
5069
5070 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Float(ani_env * env,ani_object object,const char * name,const char * signature,ani_float * result,...)5071 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Float(ani_env *env, ani_object object, const char *name,
5072 const char *signature, ani_float *result, ...)
5073 {
5074 ANI_DEBUG_TRACE(env);
5075 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5076 va_start(args, result);
5077 ani_status status = Object_CallMethodByName_Float_V(env, object, name, signature, result, args);
5078 va_end(args);
5079 return status;
5080 }
5081
5082 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Double_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_double * result,const ani_value * args)5083 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Double_A(ani_env *env, ani_object object, const char *name,
5084 const char *signature, ani_double *result,
5085 const ani_value *args)
5086 {
5087 ANI_DEBUG_TRACE(env);
5088
5089 CHECK_PTR_ARG(args);
5090 return ObjectCallMethodByName<EtsDouble, EtsType::DOUBLE>(env, object, name, signature, result, args);
5091 }
5092
5093 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Double_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_double * result,va_list args)5094 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Double_V(ani_env *env, ani_object object, const char *name,
5095 const char *signature, ani_double *result,
5096 va_list args)
5097 {
5098 ANI_DEBUG_TRACE(env);
5099
5100 return ObjectCallMethodByName<EtsDouble, EtsType::DOUBLE>(env, object, name, signature, result, args);
5101 }
5102
5103 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Double(ani_env * env,ani_object object,const char * name,const char * signature,ani_double * result,...)5104 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Double(ani_env *env, ani_object object, const char *name,
5105 const char *signature, ani_double *result, ...)
5106 {
5107 ANI_DEBUG_TRACE(env);
5108 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5109 va_start(args, result);
5110 ani_status status = Object_CallMethodByName_Double_V(env, object, name, signature, result, args);
5111 va_end(args);
5112 return status;
5113 }
5114
5115 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Ref_A(ani_env * env,ani_object object,const char * name,const char * signature,ani_ref * result,const ani_value * args)5116 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Ref_A(ani_env *env, ani_object object, const char *name,
5117 const char *signature, ani_ref *result,
5118 const ani_value *args)
5119 {
5120 ANI_DEBUG_TRACE(env);
5121
5122 CHECK_PTR_ARG(args);
5123 return ObjectCallMethodByName<ani_ref, EtsType::OBJECT>(env, object, name, signature, result, args);
5124 }
5125
5126 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Ref_V(ani_env * env,ani_object object,const char * name,const char * signature,ani_ref * result,va_list args)5127 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Ref_V(ani_env *env, ani_object object, const char *name,
5128 const char *signature, ani_ref *result, va_list args)
5129 {
5130 ANI_DEBUG_TRACE(env);
5131
5132 return ObjectCallMethodByName<ani_ref, EtsType::OBJECT>(env, object, name, signature, result, args);
5133 }
5134
5135 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Ref(ani_env * env,ani_object object,const char * name,const char * signature,ani_ref * result,...)5136 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Ref(ani_env *env, ani_object object, const char *name,
5137 const char *signature, ani_ref *result, ...)
5138 {
5139 ANI_DEBUG_TRACE(env);
5140 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5141 va_start(args, result);
5142 ani_status status = Object_CallMethodByName_Ref_V(env, object, name, signature, result, args);
5143 va_end(args);
5144 return status;
5145 }
5146
5147 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Void_A(ani_env * env,ani_object object,const char * name,const char * signature,const ani_value * args)5148 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Void_A(ani_env *env, ani_object object, const char *name,
5149 const char *signature, const ani_value *args)
5150 {
5151 ANI_DEBUG_TRACE(env);
5152
5153 CHECK_PTR_ARG(args);
5154 ani_boolean result;
5155 return ObjectCallMethodByName<EtsBoolean, EtsType::VOID>(env, object, name, signature, &result, args);
5156 }
5157
5158 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Void_V(ani_env * env,ani_object object,const char * name,const char * signature,va_list args)5159 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Void_V(ani_env *env, ani_object object, const char *name,
5160 const char *signature, va_list args)
5161 {
5162 ANI_DEBUG_TRACE(env);
5163 ani_boolean result;
5164 return ObjectCallMethodByName<EtsBoolean, EtsType::VOID>(env, object, name, signature, &result, args);
5165 }
5166
5167 // NOLINTNEXTLINE(readability-identifier-naming)
Object_CallMethodByName_Void(ani_env * env,ani_object object,const char * name,const char * signature,...)5168 NO_UB_SANITIZE static ani_status Object_CallMethodByName_Void(ani_env *env, ani_object object, const char *name,
5169 const char *signature, ...)
5170 {
5171 ANI_DEBUG_TRACE(env);
5172 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5173 va_start(args, signature);
5174 ani_status status = Object_CallMethodByName_Void_V(env, object, name, signature, args);
5175 va_end(args);
5176 return status;
5177 }
5178
DoGetTupleLength(EtsCoroutine * coroutine,EtsHandle<EtsObject> internalTuple)5179 static ani_size DoGetTupleLength(EtsCoroutine *coroutine, EtsHandle<EtsObject> internalTuple)
5180 {
5181 if (UNLIKELY(PlatformTypes(coroutine)->coreTupleN->IsAssignableFrom(internalTuple->GetClass()))) {
5182 EtsClass *klass = internalTuple->GetClass();
5183 EtsField *field = klass->GetFieldIDByName("$tupleValues", nullptr);
5184 ASSERT(field != nullptr);
5185
5186 auto *valuesArray = internalTuple->GetFieldObject(field);
5187 ASSERT(valuesArray->GetClass()->GetRuntimeClass()->IsObjectArrayClass());
5188
5189 auto *objectArray = EtsObjectArray::FromCoreType(valuesArray->GetCoreType());
5190 return objectArray->GetLength();
5191 }
5192
5193 return internalTuple->GetClass()->GetFieldsNumber();
5194 }
5195
5196 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetNumberOfItems(ani_env * env,ani_tuple_value tupleValue,ani_size * result)5197 NO_UB_SANITIZE static ani_status TupleValue_GetNumberOfItems(ani_env *env, ani_tuple_value tupleValue, ani_size *result)
5198 {
5199 ANI_DEBUG_TRACE(env);
5200 CHECK_ENV(env);
5201 CHECK_PTR_ARG(tupleValue);
5202 CHECK_PTR_ARG(result);
5203
5204 ScopedManagedCodeFix s(env);
5205 auto *coroutine = s.GetCoroutine();
5206 EtsHandleScope scope(coroutine);
5207 EtsHandle<EtsObject> internalTuple(coroutine, s.ToInternalType(tupleValue));
5208
5209 *result = DoGetTupleLength(coroutine, internalTuple);
5210
5211 return ANI_OK;
5212 }
5213
5214 template <typename ValueType>
IsCorrectBoxType(EtsCoroutine * coro,EtsObject * element)5215 static bool IsCorrectBoxType(EtsCoroutine *coro, EtsObject *element)
5216 {
5217 ASSERT(element != nullptr);
5218 ASSERT(element->GetClass() != nullptr);
5219 auto *boxPrimitiveClass = EtsBoxPrimitive<ValueType>::GetBoxClass(coro);
5220 return element->GetClass()->GetRuntimeClass() == boxPrimitiveClass;
5221 }
5222
5223 template <typename ValueType>
TupleValueGetItem(ani_env * env,ani_object tupleValue,ani_size index,ValueType * result)5224 static ani_status TupleValueGetItem(ani_env *env, ani_object tupleValue, ani_size index, ValueType *result)
5225 {
5226 CHECK_ENV(env);
5227 CHECK_PTR_ARG(tupleValue);
5228 CHECK_PTR_ARG(result);
5229
5230 ScopedManagedCodeFix s(env);
5231 auto coroutine = s.GetCoroutine();
5232 EtsHandleScope scope(coroutine);
5233 EtsHandle<EtsObject> internalTuple(coroutine, s.ToInternalType(tupleValue));
5234 ANI_CHECK_RETURN_IF_GE(index, DoGetTupleLength(coroutine, internalTuple), ANI_OUT_OF_RANGE);
5235
5236 EtsClass *klass = internalTuple->GetClass();
5237 // NOTE (#24962): Extend implementation to TupleN, when FE supports it
5238 EtsField *field = klass->GetFieldIDByName(("$" + std::to_string(index)).c_str(), nullptr);
5239 ASSERT(field != nullptr);
5240
5241 auto *resultField = internalTuple->GetFieldObject(field);
5242 ANI_CHECK_RETURN_IF_EQ(IsCorrectBoxType<ValueType>(coroutine, resultField), false, ANI_INVALID_TYPE);
5243
5244 EtsBoxPrimitive<ValueType> *boxedVal = EtsBoxPrimitive<ValueType>::FromCoreType(resultField);
5245 auto primitiveValue = boxedVal->GetValue();
5246 *result = primitiveValue;
5247
5248 return ANI_OK;
5249 }
5250
5251 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Boolean(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_boolean * result)5252 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Boolean(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5253 ani_boolean *result)
5254 {
5255 ANI_DEBUG_TRACE(env);
5256 return TupleValueGetItem<ani_boolean>(env, tupleValue, index, result);
5257 }
5258
5259 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Char(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_char * result)5260 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Char(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5261 ani_char *result)
5262 {
5263 ANI_DEBUG_TRACE(env);
5264 return TupleValueGetItem<ani_char>(env, tupleValue, index, result);
5265 }
5266
5267 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Byte(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_byte * result)5268 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Byte(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5269 ani_byte *result)
5270 {
5271 ANI_DEBUG_TRACE(env);
5272 return TupleValueGetItem<ani_byte>(env, tupleValue, index, result);
5273 }
5274
5275 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Short(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_short * result)5276 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Short(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5277 ani_short *result)
5278 {
5279 ANI_DEBUG_TRACE(env);
5280 return TupleValueGetItem<ani_short>(env, tupleValue, index, result);
5281 }
5282
5283 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Int(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_int * result)5284 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Int(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5285 ani_int *result)
5286 {
5287 ANI_DEBUG_TRACE(env);
5288 return TupleValueGetItem<ani_int>(env, tupleValue, index, result);
5289 }
5290
5291 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Long(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_long * result)5292 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Long(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5293 ani_long *result)
5294 {
5295 ANI_DEBUG_TRACE(env);
5296 return TupleValueGetItem<ani_long>(env, tupleValue, index, result);
5297 }
5298
5299 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Float(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_float * result)5300 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Float(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5301 ani_float *result)
5302 {
5303 ANI_DEBUG_TRACE(env);
5304 return TupleValueGetItem<ani_float>(env, tupleValue, index, result);
5305 }
5306
5307 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Double(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_double * result)5308 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Double(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5309 ani_double *result)
5310 {
5311 ANI_DEBUG_TRACE(env);
5312 return TupleValueGetItem<ani_double>(env, tupleValue, index, result);
5313 }
5314
5315 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_GetItem_Ref(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_ref * result)5316 NO_UB_SANITIZE static ani_status TupleValue_GetItem_Ref(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5317 ani_ref *result)
5318 {
5319 ANI_DEBUG_TRACE(env);
5320 CHECK_ENV(env);
5321 CHECK_PTR_ARG(tupleValue);
5322 CHECK_PTR_ARG(result);
5323
5324 ScopedManagedCodeFix s(env);
5325 auto coroutine = s.GetCoroutine();
5326 EtsHandleScope scope(coroutine);
5327
5328 EtsHandle<EtsObject> internalTuple(coroutine, s.ToInternalType(tupleValue));
5329 ANI_CHECK_RETURN_IF_GE(index, DoGetTupleLength(coroutine, internalTuple), ANI_OUT_OF_RANGE);
5330
5331 EtsClass *klass = internalTuple->GetClass();
5332 // NOTE (#24962): Extend implementation to TupleN, when FE supports it
5333 EtsField *field = klass->GetFieldIDByName(("$" + std::to_string(index)).c_str(), nullptr);
5334 ASSERT(field != nullptr);
5335
5336 auto element = internalTuple->GetFieldObject(field);
5337 return s.AddLocalRef(element, result);
5338 }
5339
5340 template <typename ValueType>
TupleValueSetItem(ani_env * env,ani_tuple_value tupleValue,ani_size index,ValueType value)5341 static ani_status TupleValueSetItem(ani_env *env, ani_tuple_value tupleValue, ani_size index, ValueType value)
5342 {
5343 CHECK_ENV(env);
5344 CHECK_PTR_ARG(tupleValue);
5345
5346 ScopedManagedCodeFix s(env);
5347 auto coroutine = s.GetCoroutine();
5348 EtsHandleScope scope(coroutine);
5349
5350 EtsHandle<EtsObject> internalTuple(coroutine, s.ToInternalType(tupleValue));
5351 ANI_CHECK_RETURN_IF_GE(index, DoGetTupleLength(coroutine, internalTuple), ANI_OUT_OF_RANGE);
5352
5353 EtsHandle<EtsObject> boxed(coroutine, EtsBoxPrimitive<ValueType>::Create(coroutine, value));
5354 ANI_CHECK_RETURN_IF_EQ(boxed.GetPtr(), nullptr, ANI_OUT_OF_MEMORY);
5355
5356 EtsHandle<EtsClass> klass(coroutine, internalTuple->GetClass());
5357 // NOTE (#24962): Extend implementation to TupleN, when FE supports it
5358 EtsField *field = klass->GetFieldIDByName(("$" + std::to_string(index)).c_str(), nullptr);
5359 ASSERT(field != nullptr);
5360
5361 internalTuple->SetFieldObject(field, boxed.GetPtr());
5362
5363 return ANI_OK;
5364 }
5365
5366 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Boolean(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_boolean value)5367 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Boolean(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5368 ani_boolean value)
5369 {
5370 ANI_DEBUG_TRACE(env);
5371 return TupleValueSetItem<ani_boolean>(env, tupleValue, index, value);
5372 }
5373
5374 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Char(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_char value)5375 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Char(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5376 ani_char value)
5377 {
5378 ANI_DEBUG_TRACE(env);
5379 return TupleValueSetItem<ani_char>(env, tupleValue, index, value);
5380 }
5381
5382 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Byte(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_byte value)5383 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Byte(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5384 ani_byte value)
5385 {
5386 ANI_DEBUG_TRACE(env);
5387 return TupleValueSetItem<ani_byte>(env, tupleValue, index, value);
5388 }
5389
5390 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Short(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_short value)5391 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Short(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5392 ani_short value)
5393 {
5394 ANI_DEBUG_TRACE(env);
5395 return TupleValueSetItem<ani_short>(env, tupleValue, index, value);
5396 }
5397
5398 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Int(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_int value)5399 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Int(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5400 ani_int value)
5401 {
5402 ANI_DEBUG_TRACE(env);
5403 return TupleValueSetItem<ani_int>(env, tupleValue, index, value);
5404 }
5405
5406 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Long(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_long value)5407 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Long(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5408 ani_long value)
5409 {
5410 ANI_DEBUG_TRACE(env);
5411 return TupleValueSetItem<ani_long>(env, tupleValue, index, value);
5412 }
5413
5414 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Float(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_float value)5415 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Float(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5416 ani_float value)
5417 {
5418 ANI_DEBUG_TRACE(env);
5419 return TupleValueSetItem<ani_float>(env, tupleValue, index, value);
5420 }
5421
5422 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Double(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_double value)5423 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Double(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5424 ani_double value)
5425 {
5426 ANI_DEBUG_TRACE(env);
5427 return TupleValueSetItem<ani_double>(env, tupleValue, index, value);
5428 }
5429
5430 // NOLINTNEXTLINE(readability-identifier-naming)
TupleValue_SetItem_Ref(ani_env * env,ani_tuple_value tupleValue,ani_size index,ani_ref value)5431 NO_UB_SANITIZE static ani_status TupleValue_SetItem_Ref(ani_env *env, ani_tuple_value tupleValue, ani_size index,
5432 ani_ref value)
5433 {
5434 ANI_DEBUG_TRACE(env);
5435 CHECK_ENV(env);
5436 CHECK_PTR_ARG(tupleValue);
5437 CHECK_PTR_ARG(value);
5438
5439 ScopedManagedCodeFix s(env);
5440 auto coroutine = s.GetCoroutine();
5441 EtsHandleScope scope(coroutine);
5442
5443 EtsHandle<EtsObject> internalTuple(coroutine, s.ToInternalType(tupleValue));
5444 ANI_CHECK_RETURN_IF_GE(index, DoGetTupleLength(coroutine, internalTuple), ANI_OUT_OF_RANGE);
5445
5446 EtsHandle<EtsClass> klass(coroutine, internalTuple->GetClass());
5447 // NOTE (#24962): Extend implementation to TupleN, when FE supports it
5448 EtsField *field = klass->GetFieldIDByName(("$" + std::to_string(index)).c_str(), nullptr);
5449 ASSERT(field != nullptr);
5450
5451 EtsObject *etsValue = s.ToInternalType(value);
5452 internalTuple->SetFieldObject(field, etsValue);
5453
5454 return ANI_OK;
5455 }
5456
5457 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Short_A(ani_env * env,ani_function fn,ani_short * result,const ani_value * args)5458 NO_UB_SANITIZE static ani_status Function_Call_Short_A(ani_env *env, ani_function fn, ani_short *result,
5459 const ani_value *args)
5460 {
5461 ANI_DEBUG_TRACE(env);
5462 CHECK_ENV(env);
5463 CHECK_PTR_ARG(fn);
5464 CHECK_PTR_ARG(result);
5465 CHECK_PTR_ARG(args);
5466
5467 CheckFunctionReturnType(fn, EtsType::SHORT);
5468 return GeneralFunctionCall<ani_short>(env, fn, result, args);
5469 }
5470
5471 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Short_V(ani_env * env,ani_function fn,ani_short * result,va_list args)5472 NO_UB_SANITIZE static ani_status Function_Call_Short_V(ani_env *env, ani_function fn, ani_short *result, va_list args)
5473 {
5474 ANI_DEBUG_TRACE(env);
5475 CHECK_ENV(env);
5476 CHECK_PTR_ARG(fn);
5477 CHECK_PTR_ARG(result);
5478
5479 CheckFunctionReturnType(fn, EtsType::SHORT);
5480 return GeneralFunctionCall<ani_short>(env, fn, result, args);
5481 }
5482
5483 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Short(ani_env * env,ani_function fn,ani_short * result,...)5484 NO_UB_SANITIZE static ani_status Function_Call_Short(ani_env *env, ani_function fn, ani_short *result, ...)
5485 {
5486 ANI_DEBUG_TRACE(env);
5487
5488 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5489 va_start(args, result);
5490 ani_status status = Function_Call_Short_V(env, fn, result, args);
5491 va_end(args);
5492 return status;
5493 }
5494
5495 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Int_A(ani_env * env,ani_function fn,ani_int * result,const ani_value * args)5496 NO_UB_SANITIZE static ani_status Function_Call_Int_A(ani_env *env, ani_function fn, ani_int *result,
5497 const ani_value *args)
5498 {
5499 ANI_DEBUG_TRACE(env);
5500 CHECK_ENV(env);
5501 CHECK_PTR_ARG(fn);
5502 CHECK_PTR_ARG(result);
5503 CHECK_PTR_ARG(args);
5504
5505 CheckFunctionReturnType(fn, EtsType::INT);
5506 return GeneralFunctionCall<ani_int>(env, fn, result, args);
5507 }
5508
5509 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Int_V(ani_env * env,ani_function fn,ani_int * result,va_list args)5510 NO_UB_SANITIZE static ani_status Function_Call_Int_V(ani_env *env, ani_function fn, ani_int *result, va_list args)
5511 {
5512 ANI_DEBUG_TRACE(env);
5513 CHECK_ENV(env);
5514 CHECK_PTR_ARG(fn);
5515 CHECK_PTR_ARG(result);
5516
5517 CheckFunctionReturnType(fn, EtsType::INT);
5518 return GeneralFunctionCall<ani_int>(env, fn, result, args);
5519 }
5520
5521 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Int(ani_env * env,ani_function fn,ani_int * result,...)5522 NO_UB_SANITIZE static ani_status Function_Call_Int(ani_env *env, ani_function fn, ani_int *result, ...)
5523 {
5524 ANI_DEBUG_TRACE(env);
5525
5526 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5527 va_start(args, result);
5528 ani_status status = Function_Call_Int_V(env, fn, result, args);
5529 va_end(args);
5530 return status;
5531 }
5532
5533 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Long_A(ani_env * env,ani_function fn,ani_long * result,const ani_value * args)5534 NO_UB_SANITIZE static ani_status Function_Call_Long_A(ani_env *env, ani_function fn, ani_long *result,
5535 const ani_value *args)
5536 {
5537 ANI_DEBUG_TRACE(env);
5538 CHECK_ENV(env);
5539 CHECK_PTR_ARG(fn);
5540 CHECK_PTR_ARG(result);
5541 CHECK_PTR_ARG(args);
5542
5543 CheckFunctionReturnType(fn, EtsType::LONG);
5544 return GeneralFunctionCall<ani_long>(env, fn, result, args);
5545 }
5546
5547 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Long_V(ani_env * env,ani_function fn,ani_long * result,va_list args)5548 NO_UB_SANITIZE static ani_status Function_Call_Long_V(ani_env *env, ani_function fn, ani_long *result, va_list args)
5549 {
5550 ANI_DEBUG_TRACE(env);
5551 CHECK_ENV(env);
5552 CHECK_PTR_ARG(fn);
5553 CHECK_PTR_ARG(result);
5554
5555 CheckFunctionReturnType(fn, EtsType::LONG);
5556 return GeneralFunctionCall<ani_long>(env, fn, result, args);
5557 }
5558
5559 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Long(ani_env * env,ani_function fn,ani_long * result,...)5560 NO_UB_SANITIZE static ani_status Function_Call_Long(ani_env *env, ani_function fn, ani_long *result, ...)
5561 {
5562 ANI_DEBUG_TRACE(env);
5563
5564 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5565 va_start(args, result);
5566 ani_status status = Function_Call_Long_V(env, fn, result, args);
5567 va_end(args);
5568 return status;
5569 }
5570
5571 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Float_A(ani_env * env,ani_function fn,ani_float * result,const ani_value * args)5572 NO_UB_SANITIZE static ani_status Function_Call_Float_A(ani_env *env, ani_function fn, ani_float *result,
5573 const ani_value *args)
5574 {
5575 ANI_DEBUG_TRACE(env);
5576 CHECK_ENV(env);
5577 CHECK_PTR_ARG(fn);
5578 CHECK_PTR_ARG(result);
5579 CHECK_PTR_ARG(args);
5580
5581 CheckFunctionReturnType(fn, EtsType::FLOAT);
5582 return GeneralFunctionCall<EtsFloat>(env, fn, result, args);
5583 }
5584
5585 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Float_V(ani_env * env,ani_function fn,ani_float * result,va_list args)5586 NO_UB_SANITIZE static ani_status Function_Call_Float_V(ani_env *env, ani_function fn, ani_float *result, va_list args)
5587 {
5588 ANI_DEBUG_TRACE(env);
5589 CHECK_ENV(env);
5590 CHECK_PTR_ARG(fn);
5591 CHECK_PTR_ARG(result);
5592
5593 CheckFunctionReturnType(fn, EtsType::FLOAT);
5594 return GeneralFunctionCall<EtsFloat>(env, fn, result, args);
5595 }
5596
5597 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Float(ani_env * env,ani_function fn,ani_float * result,...)5598 NO_UB_SANITIZE static ani_status Function_Call_Float(ani_env *env, ani_function fn, ani_float *result, ...)
5599 {
5600 ANI_DEBUG_TRACE(env);
5601
5602 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5603 va_start(args, result);
5604 ani_status status = Function_Call_Float_V(env, fn, result, args);
5605 va_end(args);
5606 return status;
5607 }
5608
5609 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Boolean_A(ani_env * env,ani_function fn,ani_boolean * result,const ani_value * args)5610 NO_UB_SANITIZE static ani_status Function_Call_Boolean_A(ani_env *env, ani_function fn, ani_boolean *result,
5611 const ani_value *args)
5612 {
5613 ANI_DEBUG_TRACE(env);
5614 CHECK_ENV(env);
5615 CHECK_PTR_ARG(fn);
5616 CHECK_PTR_ARG(result);
5617 CHECK_PTR_ARG(args);
5618
5619 CheckFunctionReturnType(fn, EtsType::BOOLEAN);
5620 return GeneralFunctionCall<EtsBoolean>(env, fn, result, args);
5621 }
5622
5623 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Boolean_V(ani_env * env,ani_function fn,ani_boolean * result,va_list args)5624 NO_UB_SANITIZE static ani_status Function_Call_Boolean_V(ani_env *env, ani_function fn, ani_boolean *result,
5625 va_list args)
5626 {
5627 ANI_DEBUG_TRACE(env);
5628 CHECK_ENV(env);
5629 CHECK_PTR_ARG(fn);
5630 CHECK_PTR_ARG(result);
5631
5632 CheckFunctionReturnType(fn, EtsType::BOOLEAN);
5633 return GeneralFunctionCall<EtsBoolean>(env, fn, result, args);
5634 }
5635
5636 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Boolean(ani_env * env,ani_function fn,ani_boolean * result,...)5637 NO_UB_SANITIZE static ani_status Function_Call_Boolean(ani_env *env, ani_function fn, ani_boolean *result, ...)
5638 {
5639 ANI_DEBUG_TRACE(env);
5640
5641 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5642 va_start(args, result);
5643 ani_status status = Function_Call_Boolean_V(env, fn, result, args);
5644 va_end(args);
5645 return status;
5646 }
5647
5648 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Char_A(ani_env * env,ani_function fn,ani_char * result,const ani_value * args)5649 NO_UB_SANITIZE static ani_status Function_Call_Char_A(ani_env *env, ani_function fn, ani_char *result,
5650 const ani_value *args)
5651 {
5652 ANI_DEBUG_TRACE(env);
5653 CHECK_ENV(env);
5654 CHECK_PTR_ARG(fn);
5655 CHECK_PTR_ARG(result);
5656 CHECK_PTR_ARG(args);
5657
5658 CheckFunctionReturnType(fn, EtsType::CHAR);
5659 return GeneralFunctionCall<EtsChar>(env, fn, result, args);
5660 }
5661
5662 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Char_V(ani_env * env,ani_function fn,ani_char * result,va_list args)5663 NO_UB_SANITIZE static ani_status Function_Call_Char_V(ani_env *env, ani_function fn, ani_char *result, va_list args)
5664 {
5665 ANI_DEBUG_TRACE(env);
5666 CHECK_ENV(env);
5667 CHECK_PTR_ARG(fn);
5668 CHECK_PTR_ARG(result);
5669
5670 CheckFunctionReturnType(fn, EtsType::CHAR);
5671 return GeneralFunctionCall<EtsChar>(env, fn, result, args);
5672 }
5673
5674 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Char(ani_env * env,ani_function fn,ani_char * result,...)5675 NO_UB_SANITIZE static ani_status Function_Call_Char(ani_env *env, ani_function fn, ani_char *result, ...)
5676 {
5677 ANI_DEBUG_TRACE(env);
5678
5679 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5680 va_start(args, result);
5681 ani_status status = Function_Call_Char_V(env, fn, result, args);
5682 va_end(args);
5683 return status;
5684 }
5685
5686 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Byte_A(ani_env * env,ani_function fn,ani_byte * result,const ani_value * args)5687 NO_UB_SANITIZE static ani_status Function_Call_Byte_A(ani_env *env, ani_function fn, ani_byte *result,
5688 const ani_value *args)
5689 {
5690 ANI_DEBUG_TRACE(env);
5691 CHECK_ENV(env);
5692 CHECK_PTR_ARG(fn);
5693 CHECK_PTR_ARG(result);
5694 CHECK_PTR_ARG(args);
5695
5696 CheckFunctionReturnType(fn, EtsType::BYTE);
5697 return GeneralFunctionCall<EtsByte>(env, fn, result, args);
5698 }
5699
5700 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Byte_V(ani_env * env,ani_function fn,ani_byte * result,va_list args)5701 NO_UB_SANITIZE static ani_status Function_Call_Byte_V(ani_env *env, ani_function fn, ani_byte *result, va_list args)
5702 {
5703 ANI_DEBUG_TRACE(env);
5704 CHECK_ENV(env);
5705 CHECK_PTR_ARG(fn);
5706 CHECK_PTR_ARG(result);
5707
5708 CheckFunctionReturnType(fn, EtsType::BYTE);
5709 return GeneralFunctionCall<EtsByte>(env, fn, result, args);
5710 }
5711
5712 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Byte(ani_env * env,ani_function fn,ani_byte * result,...)5713 NO_UB_SANITIZE static ani_status Function_Call_Byte(ani_env *env, ani_function fn, ani_byte *result, ...)
5714 {
5715 ANI_DEBUG_TRACE(env);
5716
5717 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5718 va_start(args, result);
5719 ani_status status = Function_Call_Byte_V(env, fn, result, args);
5720 va_end(args);
5721 return status;
5722 }
5723
5724 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Double_A(ani_env * env,ani_function fn,ani_double * result,const ani_value * args)5725 NO_UB_SANITIZE static ani_status Function_Call_Double_A(ani_env *env, ani_function fn, ani_double *result,
5726 const ani_value *args)
5727 {
5728 ANI_DEBUG_TRACE(env);
5729 CHECK_ENV(env);
5730 CHECK_PTR_ARG(fn);
5731 CHECK_PTR_ARG(result);
5732 CHECK_PTR_ARG(args);
5733
5734 CheckFunctionReturnType(fn, EtsType::DOUBLE);
5735 return GeneralFunctionCall<EtsDouble>(env, fn, result, args);
5736 }
5737
5738 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Double_V(ani_env * env,ani_function fn,ani_double * result,va_list args)5739 NO_UB_SANITIZE static ani_status Function_Call_Double_V(ani_env *env, ani_function fn, ani_double *result, va_list args)
5740 {
5741 ANI_DEBUG_TRACE(env);
5742 CHECK_ENV(env);
5743 CHECK_PTR_ARG(fn);
5744 CHECK_PTR_ARG(result);
5745
5746 CheckFunctionReturnType(fn, EtsType::DOUBLE);
5747 return GeneralFunctionCall<EtsDouble>(env, fn, result, args);
5748 }
5749
5750 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Double(ani_env * env,ani_function fn,ani_double * result,...)5751 NO_UB_SANITIZE static ani_status Function_Call_Double(ani_env *env, ani_function fn, ani_double *result, ...)
5752 {
5753 ANI_DEBUG_TRACE(env);
5754
5755 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5756 va_start(args, result);
5757 ani_status status = Function_Call_Double_V(env, fn, result, args);
5758 va_end(args);
5759 return status;
5760 }
5761
5762 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Ref_A(ani_env * env,ani_function fn,ani_ref * result,const ani_value * args)5763 NO_UB_SANITIZE static ani_status Function_Call_Ref_A(ani_env *env, ani_function fn, ani_ref *result,
5764 const ani_value *args)
5765 {
5766 ANI_DEBUG_TRACE(env);
5767 CHECK_ENV(env);
5768 CHECK_PTR_ARG(fn);
5769 CHECK_PTR_ARG(result);
5770 CHECK_PTR_ARG(args);
5771
5772 CheckFunctionReturnType(fn, EtsType::OBJECT);
5773 return GeneralFunctionCall<ani_ref>(env, fn, result, args);
5774 }
5775
5776 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Ref_V(ani_env * env,ani_function fn,ani_ref * result,va_list args)5777 NO_UB_SANITIZE static ani_status Function_Call_Ref_V(ani_env *env, ani_function fn, ani_ref *result, va_list args)
5778 {
5779 ANI_DEBUG_TRACE(env);
5780 CHECK_ENV(env);
5781 CHECK_PTR_ARG(fn);
5782 CHECK_PTR_ARG(result);
5783
5784 CheckFunctionReturnType(fn, EtsType::OBJECT);
5785 return GeneralFunctionCall<ani_ref>(env, fn, result, args);
5786 }
5787
5788 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Ref(ani_env * env,ani_function fn,ani_ref * result,...)5789 NO_UB_SANITIZE static ani_status Function_Call_Ref(ani_env *env, ani_function fn, ani_ref *result, ...)
5790 {
5791 ANI_DEBUG_TRACE(env);
5792
5793 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5794 va_start(args, result);
5795 ani_status status = Function_Call_Ref_V(env, fn, result, args);
5796 va_end(args);
5797 return status;
5798 }
5799
5800 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Void_A(ani_env * env,ani_function fn,const ani_value * args)5801 NO_UB_SANITIZE static ani_status Function_Call_Void_A(ani_env *env, ani_function fn, const ani_value *args)
5802 {
5803 ANI_DEBUG_TRACE(env);
5804 CHECK_ENV(env);
5805 CHECK_PTR_ARG(fn);
5806 CHECK_PTR_ARG(args);
5807
5808 CheckFunctionReturnType(fn, EtsType::VOID);
5809 ani_boolean result;
5810 // Use any primitive type as template parameter and just ignore the result
5811 return GeneralFunctionCall<EtsBoolean>(env, fn, &result, args);
5812 }
5813
5814 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Void_V(ani_env * env,ani_function fn,va_list args)5815 NO_UB_SANITIZE static ani_status Function_Call_Void_V(ani_env *env, ani_function fn, va_list args)
5816 {
5817 ANI_DEBUG_TRACE(env);
5818 CHECK_ENV(env);
5819 CHECK_PTR_ARG(fn);
5820
5821 CheckFunctionReturnType(fn, EtsType::VOID);
5822 ani_boolean result;
5823 // Use any primitive type as template parameter and just ignore the result
5824 return GeneralFunctionCall<EtsBoolean>(env, fn, &result, args);
5825 }
5826
5827 // NOLINTNEXTLINE(readability-identifier-naming)
Function_Call_Void(ani_env * env,ani_function fn,...)5828 NO_UB_SANITIZE static ani_status Function_Call_Void(ani_env *env, ani_function fn, ...)
5829 {
5830 ANI_DEBUG_TRACE(env);
5831
5832 va_list args; // NOLINT(cppcoreguidelines-pro-type-vararg)
5833 va_start(args, fn);
5834 ani_status status = Function_Call_Void_V(env, fn, args);
5835 va_end(args);
5836 return status;
5837 }
5838
5839 // NOLINTNEXTLINE(readability-identifier-naming)
GlobalReference_Create(ani_env * env,ani_ref ref,ani_ref * result)5840 NO_UB_SANITIZE static ani_status GlobalReference_Create(ani_env *env, ani_ref ref, ani_ref *result)
5841 {
5842 ANI_DEBUG_TRACE(env);
5843 CHECK_ENV(env);
5844 CHECK_PTR_ARG(result);
5845
5846 ScopedManagedCodeFix s(env);
5847 return s.AddGlobalRef(ref, result);
5848 }
5849
5850 // NOLINTNEXTLINE(readability-identifier-naming)
GlobalReference_Delete(ani_env * env,ani_ref gref)5851 NO_UB_SANITIZE static ani_status GlobalReference_Delete(ani_env *env, ani_ref gref)
5852 {
5853 ANI_DEBUG_TRACE(env);
5854 CHECK_ENV(env);
5855
5856 ScopedManagedCodeFix s(env);
5857 return s.DelGlobalRef(gref);
5858 }
5859
5860 // NOLINTNEXTLINE(readability-identifier-naming)
WeakReference_Create(ani_env * env,ani_ref ref,ani_wref * result)5861 NO_UB_SANITIZE static ani_status WeakReference_Create(ani_env *env, ani_ref ref, ani_wref *result)
5862 {
5863 ANI_DEBUG_TRACE(env);
5864 CHECK_ENV(env);
5865 CHECK_PTR_ARG(result);
5866
5867 ScopedManagedCodeFix s(env);
5868 return s.AddWeakRef(ref, result);
5869 }
5870
5871 // NOLINTNEXTLINE(readability-identifier-naming)
WeakReference_Delete(ani_env * env,ani_wref wref)5872 NO_UB_SANITIZE static ani_status WeakReference_Delete(ani_env *env, ani_wref wref)
5873 {
5874 ANI_DEBUG_TRACE(env);
5875 CHECK_ENV(env);
5876
5877 ScopedManagedCodeFix s(env);
5878 return s.DelWeakRef(wref);
5879 }
5880
5881 // NOLINTNEXTLINE(readability-identifier-naming)
WeakReference_GetReference(ani_env * env,ani_wref wref,ani_boolean * wasReleasedResult,ani_ref * refResult)5882 NO_UB_SANITIZE static ani_status WeakReference_GetReference(ani_env *env, ani_wref wref, ani_boolean *wasReleasedResult,
5883 ani_ref *refResult)
5884 {
5885 ANI_DEBUG_TRACE(env);
5886 CHECK_ENV(env);
5887 CHECK_PTR_ARG(wasReleasedResult);
5888 CHECK_PTR_ARG(refResult);
5889
5890 ScopedManagedCodeFix s(env);
5891 return s.GetLocalRef(wref, wasReleasedResult, refResult);
5892 }
5893
5894 template <bool IS_EXTERNAL>
DoCreateArrayBuffer(ani_env * env,void * externalData,size_t length,void ** resultData,ani_arraybuffer * resultBuffer)5895 static ani_status DoCreateArrayBuffer(ani_env *env, [[maybe_unused]] void *externalData, size_t length,
5896 [[maybe_unused]] void **resultData, ani_arraybuffer *resultBuffer)
5897 {
5898 CHECK_PTR_ARG(resultBuffer);
5899 ANI_CHECK_RETURN_IF_GT(length, static_cast<size_t>(std::numeric_limits<ani_int>::max()), ANI_INVALID_ARGS);
5900
5901 ScopedManagedCodeFix s(env);
5902 EtsCoroutine *coro = s.GetCoroutine();
5903
5904 EtsEscompatArrayBuffer *internalArrayBuffer = nullptr;
5905 if constexpr (IS_EXTERNAL) {
5906 internalArrayBuffer = EtsEscompatArrayBuffer::Create(coro, externalData, length, nullptr, nullptr);
5907 } else {
5908 internalArrayBuffer = EtsEscompatArrayBuffer::Create(coro, length, resultData);
5909 }
5910
5911 ASSERT(coro->HasPendingException() == false);
5912 ANI_CHECK_RETURN_IF_EQ(internalArrayBuffer, nullptr, ANI_OUT_OF_MEMORY);
5913
5914 ani_ref arrayObject = nullptr;
5915 ani_status ret = s.AddLocalRef(internalArrayBuffer, &arrayObject);
5916 ANI_CHECK_RETURN_IF_NE(ret, ANI_OK, ret);
5917 ASSERT(arrayObject != nullptr);
5918
5919 *resultBuffer = reinterpret_cast<ani_arraybuffer>(arrayObject);
5920 return ret;
5921 }
5922
5923 // NOLINTNEXTLINE(readability-identifier-naming)
CreateArrayBuffer(ani_env * env,size_t length,void ** dataResult,ani_arraybuffer * arraybufferResult)5924 ani_status CreateArrayBuffer(ani_env *env, size_t length, void **dataResult, ani_arraybuffer *arraybufferResult)
5925 {
5926 ANI_DEBUG_TRACE(env);
5927 CHECK_ENV(env);
5928 CHECK_PTR_ARG(dataResult);
5929 CHECK_PTR_ARG(arraybufferResult);
5930
5931 return DoCreateArrayBuffer<false>(env, nullptr, length, dataResult, arraybufferResult);
5932 }
5933
5934 // NOLINTNEXTLINE(readability-identifier-naming)
ArrayBuffer_GetInfo(ani_env * env,ani_arraybuffer arraybuffer,void ** dataResult,size_t * lengthResult)5935 NO_UB_SANITIZE static ani_status ArrayBuffer_GetInfo(ani_env *env, ani_arraybuffer arraybuffer, void **dataResult,
5936 size_t *lengthResult)
5937 {
5938 ANI_DEBUG_TRACE(env);
5939 CHECK_ENV(env);
5940 CHECK_PTR_ARG(arraybuffer);
5941 CHECK_PTR_ARG(dataResult);
5942 CHECK_PTR_ARG(lengthResult);
5943
5944 ScopedManagedCodeFix s(env);
5945 auto *internalArrayBuffer = s.ToInternalType(arraybuffer);
5946 *dataResult = internalArrayBuffer->GetData();
5947 *lengthResult = internalArrayBuffer->GetByteLength();
5948 return ANI_OK;
5949 }
5950
5951 // NOLINTNEXTLINE(readability-identifier-naming)
EnsureEnoughReferences(ani_env * env,ani_size nrRefs)5952 NO_UB_SANITIZE static ani_status EnsureEnoughReferences(ani_env *env, ani_size nrRefs)
5953 {
5954 ANI_DEBUG_TRACE(env);
5955 CHECK_ENV(env);
5956
5957 ScopedManagedCodeFix s(env);
5958 return s.EnsureLocalEnoughRefs(nrRefs);
5959 }
5960
5961 // NOLINTNEXTLINE(readability-identifier-naming)
CreateLocalScope(ani_env * env,ani_size nrRefs)5962 NO_UB_SANITIZE static ani_status CreateLocalScope(ani_env *env, ani_size nrRefs)
5963 {
5964 ANI_DEBUG_TRACE(env);
5965 CHECK_ENV(env);
5966
5967 ScopedManagedCodeFix s(env);
5968 return s.CreateLocalScope(nrRefs);
5969 }
5970
5971 // NOLINTNEXTLINE(readability-identifier-naming)
DestroyLocalScope(ani_env * env)5972 NO_UB_SANITIZE ani_status DestroyLocalScope(ani_env *env)
5973 {
5974 ANI_DEBUG_TRACE(env);
5975 CHECK_ENV(env);
5976
5977 ScopedManagedCodeFix s(env);
5978 return s.DestroyLocalScope();
5979 }
5980
5981 // NOLINTNEXTLINE(readability-identifier-naming)
CreateEscapeLocalScope(ani_env * env,ani_size nrRefs)5982 NO_UB_SANITIZE static ani_status CreateEscapeLocalScope(ani_env *env, ani_size nrRefs)
5983 {
5984 ANI_DEBUG_TRACE(env);
5985 CHECK_ENV(env);
5986
5987 ScopedManagedCodeFix s(env);
5988 return s.CreateEscapeLocalScope(nrRefs);
5989 }
5990
5991 // NOLINTNEXTLINE(readability-identifier-naming)
DestroyEscapeLocalScope(ani_env * env,ani_ref ref,ani_ref * result)5992 NO_UB_SANITIZE static ani_status DestroyEscapeLocalScope(ani_env *env, ani_ref ref, ani_ref *result)
5993 {
5994 ANI_DEBUG_TRACE(env);
5995 CHECK_ENV(env);
5996 CHECK_PTR_ARG(result);
5997
5998 ScopedManagedCodeFix s(env);
5999 return s.DestroyEscapeLocalScope(ref, result);
6000 }
6001
6002 // NOLINTNEXTLINE(readability-identifier-naming)
FindEnum(ani_env * env,const char * enumDescriptor,ani_enum * result)6003 NO_UB_SANITIZE static ani_status FindEnum(ani_env *env, const char *enumDescriptor, ani_enum *result)
6004 {
6005 ANI_DEBUG_TRACE(env);
6006 CHECK_ENV(env);
6007 CHECK_PTR_ARG(enumDescriptor);
6008 CHECK_PTR_ARG(result);
6009
6010 PandaString enumDesc = Mangle::ConvertDescriptor(enumDescriptor);
6011 // NOTE: Check that result is enum, #22400
6012 return DoFind<false>(env, enumDesc.c_str(), result);
6013 }
6014
6015 // NOLINTNEXTLINE(readability-identifier-naming)
Namespace_FindEnum(ani_env * env,ani_namespace ns,const char * enumDescriptor,ani_enum * result)6016 NO_UB_SANITIZE static ani_status Namespace_FindEnum(ani_env *env, ani_namespace ns, const char *enumDescriptor,
6017 ani_enum *result)
6018 {
6019 ANI_DEBUG_TRACE(env);
6020 CHECK_ENV(env);
6021 CHECK_PTR_ARG(ns);
6022 CHECK_PTR_ARG(enumDescriptor);
6023 CHECK_PTR_ARG(result);
6024
6025 PandaEnv *pandaEnv = PandaEnv::FromAniEnv(env);
6026 ScopedManagedCodeFix s(env);
6027 EtsNamespace *etsNs = EtsNamespace::FromClass(s.ToInternalType(ns)->AsClass());
6028
6029 PandaString enumDescriptorPandStr = Mangle::ConvertDescriptor(enumDescriptor);
6030 if (!enumDescriptorPandStr.empty() && enumDescriptorPandStr[0] == 'L') {
6031 enumDescriptorPandStr[0] = '/';
6032 } else {
6033 return ANI_NOT_FOUND;
6034 }
6035
6036 PandaString etsNsDescriptorPandStr(etsNs->AsClass()->GetDescriptor());
6037 etsNsDescriptorPandStr.pop_back();
6038 etsNsDescriptorPandStr += enumDescriptorPandStr;
6039
6040 // NOTE: Check that result is enum, #22400
6041 return DoFind<false>(pandaEnv, etsNsDescriptorPandStr.c_str(), s, result);
6042 }
6043
6044 // NOLINTNEXTLINE(readability-identifier-naming)
Module_FindEnum(ani_env * env,ani_module module,const char * enumDescriptor,ani_enum * result)6045 NO_UB_SANITIZE static ani_status Module_FindEnum(ani_env *env, ani_module module, const char *enumDescriptor,
6046 ani_enum *result)
6047 {
6048 ANI_DEBUG_TRACE(env);
6049 CHECK_ENV(env);
6050 CHECK_PTR_ARG(module);
6051 CHECK_PTR_ARG(enumDescriptor);
6052 CHECK_PTR_ARG(result);
6053
6054 // NOTE: Check that result is enum, #22400
6055 return FindInModule<false>(env, module, enumDescriptor, result);
6056 }
6057
GetArrayFromEnum(ScopedManagedCodeFix & s,ani_enum enm,const char * name,EtsObjectArray ** result)6058 static ani_status GetArrayFromEnum(ScopedManagedCodeFix &s, ani_enum enm, const char *name, EtsObjectArray **result)
6059 {
6060 EtsField *field = nullptr;
6061 ani_status status = DoGetField<true>(s, reinterpret_cast<ani_class>(enm), name, &field);
6062 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6063
6064 EtsClass *cls = field->GetDeclaringClass();
6065 status = InitializeClass(s, cls);
6066 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6067
6068 EtsObject *etsObject = cls->GetStaticFieldObject(field);
6069 *result = EtsObjectArray::FromCoreType(etsObject->GetCoreType());
6070 return ANI_OK;
6071 }
6072
6073 // NOLINTNEXTLINE(readability-identifier-naming)
Enum_GetEnumItemByName(ani_env * env,ani_enum enm,const char * name,ani_enum_item * result)6074 NO_UB_SANITIZE static ani_status Enum_GetEnumItemByName(ani_env *env, ani_enum enm, const char *name,
6075 ani_enum_item *result)
6076 {
6077 ANI_DEBUG_TRACE(env);
6078 CHECK_ENV(env);
6079 CHECK_PTR_ARG(enm);
6080 CHECK_PTR_ARG(name);
6081 CHECK_PTR_ARG(result);
6082
6083 // Get index, then call unified function for Enum_GetEnumItemByIndex
6084 ScopedManagedCodeFix s(env);
6085 EtsObjectArray *namesArr;
6086 ani_status status = GetArrayFromEnum(s, enm, EnumArrayNames::NAMES.data(), &namesArr);
6087 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6088 size_t sz = namesArr->GetLength();
6089
6090 size_t index = 0;
6091 for (; index < sz; ++index) {
6092 EtsObject *etsElem = namesArr->Get(index);
6093 EtsString *etsStr = EtsString::FromEtsObject(etsElem);
6094 if (etsStr->IsEqual(name)) {
6095 break;
6096 }
6097 }
6098 if (index >= sz) {
6099 return ANI_NOT_FOUND;
6100 }
6101
6102 EtsObjectArray *itemsArr;
6103 status = GetArrayFromEnum(s, enm, EnumArrayNames::BOXED_ITEMS.data(), &itemsArr);
6104 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6105 EtsObject *res = itemsArr->Get(index);
6106
6107 return s.AddLocalRef(res, reinterpret_cast<ani_ref *>(result));
6108 }
6109
6110 // NOLINTNEXTLINE(readability-identifier-naming)
Enum_GetEnumItemByIndex(ani_env * env,ani_enum enm,ani_size index,ani_enum_item * result)6111 NO_UB_SANITIZE static ani_status Enum_GetEnumItemByIndex(ani_env *env, ani_enum enm, ani_size index,
6112 ani_enum_item *result)
6113 {
6114 ANI_DEBUG_TRACE(env);
6115 CHECK_ENV(env);
6116 CHECK_PTR_ARG(enm);
6117 CHECK_PTR_ARG(result);
6118
6119 ScopedManagedCodeFix s(env);
6120 EtsObjectArray *itemsArr;
6121 ani_status status = GetArrayFromEnum(s, enm, EnumArrayNames::BOXED_ITEMS.data(), &itemsArr);
6122 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6123
6124 if (index >= itemsArr->GetLength()) {
6125 return ANI_NOT_FOUND;
6126 }
6127 EtsObject *res = itemsArr->Get(index);
6128
6129 return s.AddLocalRef(res, reinterpret_cast<ani_ref *>(result));
6130 }
6131
6132 // NOLINTNEXTLINE(readability-identifier-naming)
EnumItem_GetEnum(ani_env * env,ani_enum_item enum_item,ani_enum * result)6133 NO_UB_SANITIZE static ani_status EnumItem_GetEnum(ani_env *env, ani_enum_item enum_item, ani_enum *result)
6134 {
6135 ANI_DEBUG_TRACE(env);
6136 CHECK_ENV(env);
6137 CHECK_PTR_ARG(enum_item);
6138 CHECK_PTR_ARG(result);
6139
6140 ScopedManagedCodeFix s(env);
6141 EtsObject *internalEnumItem = s.ToInternalType(enum_item);
6142 EtsClass *enumClass = internalEnumItem->GetClass();
6143
6144 ANI_CHECK_RETURN_IF_NE(enumClass->IsEtsEnum(), true, ANI_INVALID_TYPE);
6145
6146 return s.AddLocalRef(reinterpret_cast<EtsObject *>(enumClass), reinterpret_cast<ani_ref *>(result));
6147 }
6148
6149 template <typename T>
GetArrayFromInternalEnum(EtsHandle<EtsClass> enumClass,const char * name)6150 static T *GetArrayFromInternalEnum(EtsHandle<EtsClass> enumClass, const char *name)
6151 {
6152 ASSERT(enumClass.GetPtr() != nullptr);
6153 EtsField *field = enumClass->GetStaticFieldIDByName(name, nullptr);
6154 if (field == nullptr) {
6155 return nullptr;
6156 }
6157
6158 EtsClass *cls = field->GetDeclaringClass();
6159 EtsObject *etsObject = cls->GetStaticFieldObject(field);
6160 return reinterpret_cast<T *>(etsObject->GetCoreType());
6161 }
6162
6163 // NOLINTNEXTLINE(readability-identifier-naming)
EnumItem_GetValue_Int(ani_env * env,ani_enum_item enum_item,ani_int * result)6164 NO_UB_SANITIZE static ani_status EnumItem_GetValue_Int(ani_env *env, ani_enum_item enum_item, ani_int *result)
6165 {
6166 ANI_DEBUG_TRACE(env);
6167 CHECK_ENV(env);
6168 CHECK_PTR_ARG(enum_item);
6169 CHECK_PTR_ARG(result);
6170
6171 ScopedManagedCodeFix s(env);
6172 EtsCoroutine *coroutine = s.GetCoroutine();
6173 EtsHandleScope scope(coroutine);
6174 EtsHandle<EtsObject> internalEnumItem(coroutine, s.ToInternalType(enum_item));
6175 EtsHandle<EtsClass> enumClass(coroutine, internalEnumItem->GetClass());
6176 EtsField *etsField = enumClass->GetFieldIDByName("#ordinal", nullptr);
6177 auto ordinal = internalEnumItem->GetFieldPrimitive<int32_t>(etsField);
6178
6179 auto *itemsArr = GetArrayFromInternalEnum<EtsIntArray>(enumClass, EnumArrayNames::VALUES.data());
6180 // If enum values are strings, there is no ValuesArray array, so incorrect call to method
6181 if (itemsArr == nullptr) {
6182 return ANI_INVALID_ARGS;
6183 }
6184 *result = itemsArr->Get(ordinal);
6185 return ANI_OK;
6186 }
6187
GetStringArrayFromEnumItem(ani_env * env,ani_enum_item enumItem,const char * arrayName,ani_string * result)6188 static ani_status GetStringArrayFromEnumItem(ani_env *env, ani_enum_item enumItem, const char *arrayName,
6189 ani_string *result)
6190 {
6191 ScopedManagedCodeFix s(env);
6192 EtsCoroutine *coroutine = s.GetCoroutine();
6193 EtsHandleScope scope(coroutine);
6194 EtsHandle<EtsObject> internalEnumItem(coroutine, s.ToInternalType(enumItem));
6195 EtsHandle<EtsClass> enumClass(coroutine, internalEnumItem->GetClass());
6196 EtsField *etsField = enumClass->GetFieldIDByName("#ordinal", nullptr);
6197 auto ordinal = internalEnumItem->GetFieldPrimitive<int32_t>(etsField);
6198
6199 auto *itemsArr = GetArrayFromInternalEnum<EtsObjectArray>(enumClass, arrayName);
6200 EtsObject *stringObj = itemsArr->Get(ordinal);
6201 return s.AddLocalRef(stringObj, reinterpret_cast<ani_ref *>(result));
6202 }
6203
6204 // NOLINTNEXTLINE(readability-identifier-naming)
EnumItem_GetValue_String(ani_env * env,ani_enum_item enum_item,ani_string * result)6205 NO_UB_SANITIZE static ani_status EnumItem_GetValue_String(ani_env *env, ani_enum_item enum_item, ani_string *result)
6206 {
6207 ANI_DEBUG_TRACE(env);
6208 CHECK_ENV(env);
6209 CHECK_PTR_ARG(enum_item);
6210 CHECK_PTR_ARG(result);
6211
6212 return GetStringArrayFromEnumItem(env, enum_item, EnumArrayNames::STRING_VALUES.data(), result);
6213 }
6214
6215 // NOLINTNEXTLINE(readability-identifier-naming)
EnumItem_GetName(ani_env * env,ani_enum_item enum_item,ani_string * result)6216 NO_UB_SANITIZE static ani_status EnumItem_GetName(ani_env *env, ani_enum_item enum_item, ani_string *result)
6217 {
6218 ANI_DEBUG_TRACE(env);
6219 CHECK_ENV(env);
6220 CHECK_PTR_ARG(enum_item);
6221 CHECK_PTR_ARG(result);
6222
6223 return GetStringArrayFromEnumItem(env, enum_item, EnumArrayNames::NAMES.data(), result);
6224 }
6225
6226 // NOLINTNEXTLINE(readability-identifier-naming)
EnumItem_GetIndex(ani_env * env,ani_enum_item enum_item,ani_size * result)6227 NO_UB_SANITIZE static ani_status EnumItem_GetIndex(ani_env *env, ani_enum_item enum_item, ani_size *result)
6228 {
6229 ANI_DEBUG_TRACE(env);
6230 CHECK_ENV(env);
6231 CHECK_PTR_ARG(enum_item);
6232 CHECK_PTR_ARG(result);
6233
6234 ScopedManagedCodeFix s(env);
6235 EtsCoroutine *coroutine = s.GetCoroutine();
6236 EtsHandleScope scope(coroutine);
6237 EtsHandle<EtsObject> internalEnumItem(coroutine, s.ToInternalType(enum_item));
6238 EtsHandle<EtsClass> enumClass(coroutine, internalEnumItem->GetClass());
6239 EtsField *etsField = enumClass->GetFieldIDByName("#ordinal", nullptr);
6240 auto ordinal = internalEnumItem->GetFieldPrimitive<int32_t>(etsField);
6241
6242 *result = ordinal;
6243 return ANI_OK;
6244 }
6245
6246 // NOLINTNEXTLINE(readability-identifier-naming)
Promise_New(ani_env * env,ani_resolver * resultResolver,ani_object * resultPromise)6247 NO_UB_SANITIZE static ani_status Promise_New(ani_env *env, ani_resolver *resultResolver, ani_object *resultPromise)
6248 {
6249 ANI_DEBUG_TRACE(env);
6250 CHECK_ENV(env);
6251 CHECK_PTR_ARG(resultResolver);
6252 CHECK_PTR_ARG(resultPromise);
6253
6254 ScopedManagedCodeFix s(env);
6255 EtsPromise *promise = EtsPromise::Create(s.GetCoroutine());
6256 ANI_CHECK_RETURN_IF_EQ(promise, nullptr, ANI_OUT_OF_MEMORY);
6257 ani_status status = s.AddLocalRef(promise->AsObject(), reinterpret_cast<ani_ref *>(resultPromise));
6258 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6259 return s.AddGlobalRef(promise->AsObject(), reinterpret_cast<ani_ref *>(resultResolver));
6260 }
6261
6262 // NOLINTNEXTLINE(readability-identifier-naming)
PromiseResolver_Resolve(ani_env * env,ani_resolver resolver,ani_ref resolution)6263 NO_UB_SANITIZE static ani_status PromiseResolver_Resolve(ani_env *env, ani_resolver resolver, ani_ref resolution)
6264 {
6265 ANI_DEBUG_TRACE(env);
6266 CHECK_ENV(env);
6267
6268 ScopedManagedCodeFix s(env);
6269 EtsPromise *promise = s.ToInternalType(resolver);
6270 ANI_CHECK_RETURN_IF_EQ(promise, nullptr, ANI_INVALID_ARGS);
6271 ani_status status = s.DelGlobalRef(reinterpret_cast<ani_ref>(resolver));
6272 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6273 EtsObject *value = s.ToInternalType(resolution);
6274 promise->Resolve(s.GetCoroutine(), value);
6275 return ANI_OK;
6276 }
6277
6278 // NOLINTNEXTLINE(readability-identifier-naming)
PromiseResolver_Reject(ani_env * env,ani_resolver resolver,ani_error rejection)6279 NO_UB_SANITIZE static ani_status PromiseResolver_Reject(ani_env *env, ani_resolver resolver, ani_error rejection)
6280 {
6281 ANI_DEBUG_TRACE(env);
6282 CHECK_ENV(env);
6283
6284 ScopedManagedCodeFix s(env);
6285 EtsPromise *promise = s.ToInternalType(resolver);
6286 ANI_CHECK_RETURN_IF_EQ(promise, nullptr, ANI_INVALID_ARGS);
6287 ani_status status = s.DelGlobalRef(reinterpret_cast<ani_ref>(resolver));
6288 ANI_CHECK_RETURN_IF_NE(status, ANI_OK, status);
6289 EtsObject *error = s.ToInternalType(rejection);
6290 promise->Reject(s.GetCoroutine(), error);
6291 return ANI_OK;
6292 }
6293
6294 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Boolean(ani_env * env,ani_size length,ani_array_boolean * result)6295 NO_UB_SANITIZE static ani_status FixedArray_New_Boolean(ani_env *env, ani_size length, ani_array_boolean *result)
6296 {
6297 ANI_DEBUG_TRACE(env);
6298 CHECK_ENV(env);
6299 CHECK_PTR_ARG(result);
6300 return NewPrimitiveTypeArray<EtsBooleanArray>(env, length, result);
6301 }
6302
6303 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Char(ani_env * env,ani_size length,ani_array_char * result)6304 NO_UB_SANITIZE static ani_status FixedArray_New_Char(ani_env *env, ani_size length, ani_array_char *result)
6305 {
6306 ANI_DEBUG_TRACE(env);
6307 CHECK_ENV(env);
6308 CHECK_PTR_ARG(result);
6309 return NewPrimitiveTypeArray<EtsCharArray>(env, length, result);
6310 }
6311
6312 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Byte(ani_env * env,ani_size length,ani_array_byte * result)6313 NO_UB_SANITIZE static ani_status FixedArray_New_Byte(ani_env *env, ani_size length, ani_array_byte *result)
6314 {
6315 ANI_DEBUG_TRACE(env);
6316 CHECK_ENV(env);
6317 CHECK_PTR_ARG(result);
6318 return NewPrimitiveTypeArray<EtsByteArray>(env, length, result);
6319 }
6320
6321 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Short(ani_env * env,ani_size length,ani_array_short * result)6322 NO_UB_SANITIZE static ani_status FixedArray_New_Short(ani_env *env, ani_size length, ani_array_short *result)
6323 {
6324 ANI_DEBUG_TRACE(env);
6325 CHECK_ENV(env);
6326 CHECK_PTR_ARG(result);
6327 return NewPrimitiveTypeArray<EtsShortArray>(env, length, result);
6328 }
6329
6330 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Int(ani_env * env,ani_size length,ani_array_int * result)6331 NO_UB_SANITIZE static ani_status FixedArray_New_Int(ani_env *env, ani_size length, ani_array_int *result)
6332 {
6333 ANI_DEBUG_TRACE(env);
6334 CHECK_ENV(env);
6335 CHECK_PTR_ARG(result);
6336 return NewPrimitiveTypeArray<EtsIntArray>(env, length, result);
6337 }
6338
6339 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Long(ani_env * env,ani_size length,ani_array_long * result)6340 NO_UB_SANITIZE static ani_status FixedArray_New_Long(ani_env *env, ani_size length, ani_array_long *result)
6341 {
6342 ANI_DEBUG_TRACE(env);
6343 CHECK_ENV(env);
6344 CHECK_PTR_ARG(result);
6345 return NewPrimitiveTypeArray<EtsLongArray>(env, length, result);
6346 }
6347
6348 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Float(ani_env * env,ani_size length,ani_array_float * result)6349 NO_UB_SANITIZE static ani_status FixedArray_New_Float(ani_env *env, ani_size length, ani_array_float *result)
6350 {
6351 ANI_DEBUG_TRACE(env);
6352 CHECK_ENV(env);
6353 CHECK_PTR_ARG(result);
6354 return NewPrimitiveTypeArray<EtsFloatArray>(env, length, result);
6355 }
6356
6357 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Double(ani_env * env,ani_size length,ani_array_double * result)6358 NO_UB_SANITIZE static ani_status FixedArray_New_Double(ani_env *env, ani_size length, ani_array_double *result)
6359 {
6360 ANI_DEBUG_TRACE(env);
6361 CHECK_ENV(env);
6362 CHECK_PTR_ARG(result);
6363 return NewPrimitiveTypeArray<EtsDoubleArray>(env, length, result);
6364 }
6365
6366 // NOLINTNEXTLINE(readability-identifier-naming)
FixedArray_New_Ref(ani_env * env,ani_type type,ani_size length,ani_ref initialElement,ani_array_ref * result)6367 NO_UB_SANITIZE static ani_status FixedArray_New_Ref(ani_env *env, ani_type type, ani_size length,
6368 ani_ref initialElement, ani_array_ref *result)
6369 {
6370 ANI_DEBUG_TRACE(env);
6371 CHECK_ENV(env);
6372 ANI_CHECK_RETURN_IF_GT(length, std::numeric_limits<uint32_t>::max(), ANI_INVALID_ARGS);
6373 CHECK_PTR_ARG(type);
6374 CHECK_PTR_ARG(result);
6375
6376 ScopedManagedCodeFix s(env);
6377 EtsClass *internalClass = s.ToInternalType(type);
6378 EtsObjectArray *internalArray = EtsObjectArray::Create(internalClass, static_cast<uint32_t>(length));
6379 ANI_CHECK_RETURN_IF_EQ(internalArray, nullptr, ANI_OUT_OF_MEMORY);
6380 if (initialElement != nullptr) {
6381 EtsObject *obj = s.ToInternalType(initialElement);
6382 for (ani_size i = 0; i < length; i++) {
6383 internalArray->Set(static_cast<uint32_t>(i), obj);
6384 }
6385 }
6386 return s.AddLocalRef(reinterpret_cast<EtsObject *>(internalArray), reinterpret_cast<ani_ref *>(result));
6387 }
6388
NotImplementedAPI(int nr)6389 [[noreturn]] static void NotImplementedAPI(int nr)
6390 {
6391 LOG(FATAL, ANI) << "Not implemented interaction_api, nr=" << nr;
6392 UNREACHABLE();
6393 }
6394
6395 template <int NR, typename R, typename... Args>
NotImplementedAdapter(Args...args)6396 static R NotImplementedAdapter([[maybe_unused]] Args... args)
6397 {
6398 NotImplementedAPI(NR);
6399 }
6400
6401 template <int NR, typename R, typename... Args>
NotImplementedAdapterVargs(Args...args,...)6402 static R NotImplementedAdapterVargs([[maybe_unused]] Args... args, ...)
6403 {
6404 NotImplementedAPI(NR);
6405 }
6406
6407 // clang-format off
6408 const __ani_interaction_api INTERACTION_API = {
6409 nullptr,
6410 nullptr,
6411 nullptr,
6412 nullptr,
6413 GetVersion,
6414 GetVM,
6415 Object_New,
6416 Object_New_A,
6417 Object_New_V,
6418 Object_GetType,
6419 Object_InstanceOf,
6420 Type_GetSuperClass,
6421 Type_IsAssignableFrom,
6422 FindModule,
6423 FindNamespace,
6424 FindClass,
6425 FindEnum,
6426 Module_FindNamespace,
6427 Module_FindClass,
6428 Module_FindEnum,
6429 Module_FindFunction,
6430 Module_FindVariable,
6431 Namespace_FindNamespace,
6432 Namespace_FindClass,
6433 Namespace_FindEnum,
6434 Namespace_FindFunction,
6435 Namespace_FindVariable,
6436 Module_BindNativeFunctions,
6437 Namespace_BindNativeFunctions,
6438 Class_BindNativeMethods,
6439 Reference_Delete,
6440 EnsureEnoughReferences,
6441 CreateLocalScope,
6442 DestroyLocalScope,
6443 CreateEscapeLocalScope,
6444 DestroyEscapeLocalScope,
6445 ThrowError,
6446 ExistUnhandledError,
6447 GetUnhandledError,
6448 ResetError,
6449 DescribeError,
6450 Abort,
6451 GetNull,
6452 GetUndefined,
6453 Reference_IsNull,
6454 Reference_IsUndefined,
6455 Reference_IsNullishValue,
6456 Reference_Equals,
6457 Reference_StrictEquals,
6458 String_NewUTF16,
6459 String_GetUTF16Size,
6460 String_GetUTF16,
6461 String_GetUTF16SubString,
6462 String_NewUTF8,
6463 String_GetUTF8Size,
6464 String_GetUTF8,
6465 String_GetUTF8SubString,
6466 Array_GetLength,
6467 Array_New_Boolean,
6468 Array_New_Char,
6469 Array_New_Byte,
6470 Array_New_Short,
6471 Array_New_Int,
6472 Array_New_Long,
6473 Array_New_Float,
6474 Array_New_Double,
6475 Array_GetRegion_Boolean,
6476 Array_GetRegion_Char,
6477 Array_GetRegion_Byte,
6478 Array_GetRegion_Short,
6479 Array_GetRegion_Int,
6480 Array_GetRegion_Long,
6481 Array_GetRegion_Float,
6482 Array_GetRegion_Double,
6483 Array_SetRegion_Boolean,
6484 Array_SetRegion_Char,
6485 Array_SetRegion_Byte,
6486 Array_SetRegion_Short,
6487 Array_SetRegion_Int,
6488 Array_SetRegion_Long,
6489 Array_SetRegion_Float,
6490 Array_SetRegion_Double,
6491 Array_New_Ref,
6492 Array_Set_Ref,
6493 Array_Get_Ref,
6494 Enum_GetEnumItemByName,
6495 Enum_GetEnumItemByIndex,
6496 EnumItem_GetEnum,
6497 EnumItem_GetValue_Int,
6498 EnumItem_GetValue_String,
6499 EnumItem_GetName,
6500 EnumItem_GetIndex,
6501 FunctionalObject_Call,
6502 Variable_SetValue_Boolean,
6503 Variable_SetValue_Char,
6504 Variable_SetValue_Byte,
6505 Variable_SetValue_Short,
6506 Variable_SetValue_Int,
6507 Variable_SetValue_Long,
6508 Variable_SetValue_Float,
6509 Variable_SetValue_Double,
6510 Variable_SetValue_Ref,
6511 Variable_GetValue_Boolean,
6512 Variable_GetValue_Char,
6513 Variable_GetValue_Byte,
6514 Variable_GetValue_Short,
6515 Variable_GetValue_Int,
6516 Variable_GetValue_Long,
6517 Variable_GetValue_Float,
6518 Variable_GetValue_Double,
6519 Variable_GetValue_Ref,
6520 Function_Call_Boolean,
6521 Function_Call_Boolean_A,
6522 Function_Call_Boolean_V,
6523 Function_Call_Char,
6524 Function_Call_Char_A,
6525 Function_Call_Char_V,
6526 Function_Call_Byte,
6527 Function_Call_Byte_A,
6528 Function_Call_Byte_V,
6529 Function_Call_Short,
6530 Function_Call_Short_A,
6531 Function_Call_Short_V,
6532 Function_Call_Int,
6533 Function_Call_Int_A,
6534 Function_Call_Int_V,
6535 Function_Call_Long,
6536 Function_Call_Long_A,
6537 Function_Call_Long_V,
6538 Function_Call_Float,
6539 Function_Call_Float_A,
6540 Function_Call_Float_V,
6541 Function_Call_Double,
6542 Function_Call_Double_A,
6543 Function_Call_Double_V,
6544 Function_Call_Ref,
6545 Function_Call_Ref_A,
6546 Function_Call_Ref_V,
6547 Function_Call_Void,
6548 Function_Call_Void_A,
6549 Function_Call_Void_V,
6550 Class_FindField,
6551 Class_FindStaticField,
6552 Class_FindMethod,
6553 Class_FindStaticMethod,
6554 Class_FindSetter,
6555 Class_FindGetter,
6556 Class_FindIndexableGetter,
6557 Class_FindIndexableSetter,
6558 Class_FindIterator,
6559 Class_GetStaticField_Boolean,
6560 Class_GetStaticField_Char,
6561 Class_GetStaticField_Byte,
6562 Class_GetStaticField_Short,
6563 Class_GetStaticField_Int,
6564 Class_GetStaticField_Long,
6565 Class_GetStaticField_Float,
6566 Class_GetStaticField_Double,
6567 Class_GetStaticField_Ref,
6568 Class_SetStaticField_Boolean,
6569 Class_SetStaticField_Char,
6570 Class_SetStaticField_Byte,
6571 Class_SetStaticField_Short,
6572 Class_SetStaticField_Int,
6573 Class_SetStaticField_Long,
6574 Class_SetStaticField_Float,
6575 Class_SetStaticField_Double,
6576 Class_SetStaticField_Ref,
6577 Class_GetStaticFieldByName_Boolean,
6578 Class_GetStaticFieldByName_Char,
6579 Class_GetStaticFieldByName_Byte,
6580 Class_GetStaticFieldByName_Short,
6581 Class_GetStaticFieldByName_Int,
6582 Class_GetStaticFieldByName_Long,
6583 Class_GetStaticFieldByName_Float,
6584 Class_GetStaticFieldByName_Double,
6585 Class_GetStaticFieldByName_Ref,
6586 Class_SetStaticFieldByName_Boolean,
6587 Class_SetStaticFieldByName_Char,
6588 Class_SetStaticFieldByName_Byte,
6589 Class_SetStaticFieldByName_Short,
6590 Class_SetStaticFieldByName_Int,
6591 Class_SetStaticFieldByName_Long,
6592 Class_SetStaticFieldByName_Float,
6593 Class_SetStaticFieldByName_Double,
6594 Class_SetStaticFieldByName_Ref,
6595 Class_CallStaticMethod_Boolean,
6596 Class_CallStaticMethod_Boolean_A,
6597 Class_CallStaticMethod_Boolean_V,
6598 Class_CallStaticMethod_Char,
6599 Class_CallStaticMethod_Char_A,
6600 Class_CallStaticMethod_Char_V,
6601 Class_CallStaticMethod_Byte,
6602 Class_CallStaticMethod_Byte_A,
6603 Class_CallStaticMethod_Byte_V,
6604 Class_CallStaticMethod_Short,
6605 Class_CallStaticMethod_Short_A,
6606 Class_CallStaticMethod_Short_V,
6607 Class_CallStaticMethod_Int,
6608 Class_CallStaticMethod_Int_A,
6609 Class_CallStaticMethod_Int_V,
6610 Class_CallStaticMethod_Long,
6611 Class_CallStaticMethod_Long_A,
6612 Class_CallStaticMethod_Long_V,
6613 Class_CallStaticMethod_Float,
6614 Class_CallStaticMethod_Float_A,
6615 Class_CallStaticMethod_Float_V,
6616 Class_CallStaticMethod_Double,
6617 Class_CallStaticMethod_Double_A,
6618 Class_CallStaticMethod_Double_V,
6619 Class_CallStaticMethod_Ref,
6620 Class_CallStaticMethod_Ref_A,
6621 Class_CallStaticMethod_Ref_V,
6622 Class_CallStaticMethod_Void,
6623 Class_CallStaticMethod_Void_A,
6624 Class_CallStaticMethod_Void_V,
6625 Class_CallStaticMethodByName_Boolean,
6626 Class_CallStaticMethodByName_Boolean_A,
6627 Class_CallStaticMethodByName_Boolean_V,
6628 Class_CallStaticMethodByName_Char,
6629 Class_CallStaticMethodByName_Char_A,
6630 Class_CallStaticMethodByName_Char_V,
6631 Class_CallStaticMethodByName_Byte,
6632 Class_CallStaticMethodByName_Byte_A,
6633 Class_CallStaticMethodByName_Byte_V,
6634 Class_CallStaticMethodByName_Short,
6635 Class_CallStaticMethodByName_Short_A,
6636 Class_CallStaticMethodByName_Short_V,
6637 Class_CallStaticMethodByName_Int,
6638 Class_CallStaticMethodByName_Int_A,
6639 Class_CallStaticMethodByName_Int_V,
6640 Class_CallStaticMethodByName_Long,
6641 Class_CallStaticMethodByName_Long_A,
6642 Class_CallStaticMethodByName_Long_V,
6643 Class_CallStaticMethodByName_Float,
6644 Class_CallStaticMethodByName_Float_A,
6645 Class_CallStaticMethodByName_Float_V,
6646 Class_CallStaticMethodByName_Double,
6647 Class_CallStaticMethodByName_Double_A,
6648 Class_CallStaticMethodByName_Double_V,
6649 Class_CallStaticMethodByName_Ref,
6650 Class_CallStaticMethodByName_Ref_A,
6651 Class_CallStaticMethodByName_Ref_V,
6652 Class_CallStaticMethodByName_Void,
6653 Class_CallStaticMethodByName_Void_A,
6654 Class_CallStaticMethodByName_Void_V,
6655 Object_GetField_Boolean,
6656 Object_GetField_Char,
6657 Object_GetField_Byte,
6658 Object_GetField_Short,
6659 Object_GetField_Int,
6660 Object_GetField_Long,
6661 Object_GetField_Float,
6662 Object_GetField_Double,
6663 Object_GetField_Ref,
6664 Object_SetField_Boolean,
6665 Object_SetField_Char,
6666 Object_SetField_Byte,
6667 Object_SetField_Short,
6668 Object_SetField_Int,
6669 Object_SetField_Long,
6670 Object_SetField_Float,
6671 Object_SetField_Double,
6672 Object_SetField_Ref,
6673 Object_GetFieldByName_Boolean,
6674 Object_GetFieldByName_Char,
6675 Object_GetFieldByName_Byte,
6676 Object_GetFieldByName_Short,
6677 Object_GetFieldByName_Int,
6678 Object_GetFieldByName_Long,
6679 Object_GetFieldByName_Float,
6680 Object_GetFieldByName_Double,
6681 Object_GetFieldByName_Ref,
6682 Object_SetFieldByName_Boolean,
6683 Object_SetFieldByName_Char,
6684 Object_SetFieldByName_Byte,
6685 Object_SetFieldByName_Short,
6686 Object_SetFieldByName_Int,
6687 Object_SetFieldByName_Long,
6688 Object_SetFieldByName_Float,
6689 Object_SetFieldByName_Double,
6690 Object_SetFieldByName_Ref,
6691 Object_GetPropertyByName_Boolean,
6692 Object_GetPropertyByName_Char,
6693 Object_GetPropertyByName_Byte,
6694 Object_GetPropertyByName_Short,
6695 Object_GetPropertyByName_Int,
6696 Object_GetPropertyByName_Long,
6697 Object_GetPropertyByName_Float,
6698 Object_GetPropertyByName_Double,
6699 Object_GetPropertyByName_Ref,
6700 Object_SetPropertyByName_Boolean,
6701 Object_SetPropertyByName_Char,
6702 Object_SetPropertyByName_Byte,
6703 Object_SetPropertyByName_Short,
6704 Object_SetPropertyByName_Int,
6705 Object_SetPropertyByName_Long,
6706 Object_SetPropertyByName_Float,
6707 Object_SetPropertyByName_Double,
6708 Object_SetPropertyByName_Ref,
6709 Object_CallMethod_Boolean,
6710 Object_CallMethod_Boolean_A,
6711 Object_CallMethod_Boolean_V,
6712 Object_CallMethod_Char,
6713 Object_CallMethod_Char_A,
6714 Object_CallMethod_Char_V,
6715 Object_CallMethod_Byte,
6716 Object_CallMethod_Byte_A,
6717 Object_CallMethod_Byte_V,
6718 Object_CallMethod_Short,
6719 Object_CallMethod_Short_A,
6720 Object_CallMethod_Short_V,
6721 Object_CallMethod_Int,
6722 Object_CallMethod_Int_A,
6723 Object_CallMethod_Int_V,
6724 Object_CallMethod_Long,
6725 Object_CallMethod_Long_A,
6726 Object_CallMethod_Long_V,
6727 Object_CallMethod_Float,
6728 Object_CallMethod_Float_A,
6729 Object_CallMethod_Float_V,
6730 Object_CallMethod_Double,
6731 Object_CallMethod_Double_A,
6732 Object_CallMethod_Double_V,
6733 Object_CallMethod_Ref,
6734 Object_CallMethod_Ref_A,
6735 Object_CallMethod_Ref_V,
6736 Object_CallMethod_Void,
6737 Object_CallMethod_Void_A,
6738 Object_CallMethod_Void_V,
6739 Object_CallMethodByName_Boolean,
6740 Object_CallMethodByName_Boolean_A,
6741 Object_CallMethodByName_Boolean_V,
6742 Object_CallMethodByName_Char,
6743 Object_CallMethodByName_Char_A,
6744 Object_CallMethodByName_Char_V,
6745 Object_CallMethodByName_Byte,
6746 Object_CallMethodByName_Byte_A,
6747 Object_CallMethodByName_Byte_V,
6748 Object_CallMethodByName_Short,
6749 Object_CallMethodByName_Short_A,
6750 Object_CallMethodByName_Short_V,
6751 Object_CallMethodByName_Int,
6752 Object_CallMethodByName_Int_A,
6753 Object_CallMethodByName_Int_V,
6754 Object_CallMethodByName_Long,
6755 Object_CallMethodByName_Long_A,
6756 Object_CallMethodByName_Long_V,
6757 Object_CallMethodByName_Float,
6758 Object_CallMethodByName_Float_A,
6759 Object_CallMethodByName_Float_V,
6760 Object_CallMethodByName_Double,
6761 Object_CallMethodByName_Double_A,
6762 Object_CallMethodByName_Double_V,
6763 Object_CallMethodByName_Ref,
6764 Object_CallMethodByName_Ref_A,
6765 Object_CallMethodByName_Ref_V,
6766 Object_CallMethodByName_Void,
6767 Object_CallMethodByName_Void_A,
6768 Object_CallMethodByName_Void_V,
6769 TupleValue_GetNumberOfItems,
6770 TupleValue_GetItem_Boolean,
6771 TupleValue_GetItem_Char,
6772 TupleValue_GetItem_Byte,
6773 TupleValue_GetItem_Short,
6774 TupleValue_GetItem_Int,
6775 TupleValue_GetItem_Long,
6776 TupleValue_GetItem_Float,
6777 TupleValue_GetItem_Double,
6778 TupleValue_GetItem_Ref,
6779 TupleValue_SetItem_Boolean,
6780 TupleValue_SetItem_Char,
6781 TupleValue_SetItem_Byte,
6782 TupleValue_SetItem_Short,
6783 TupleValue_SetItem_Int,
6784 TupleValue_SetItem_Long,
6785 TupleValue_SetItem_Float,
6786 TupleValue_SetItem_Double,
6787 TupleValue_SetItem_Ref,
6788 GlobalReference_Create,
6789 GlobalReference_Delete,
6790 WeakReference_Create,
6791 WeakReference_Delete,
6792 WeakReference_GetReference,
6793 CreateArrayBuffer,
6794 NotImplementedAdapter<445>,
6795 ArrayBuffer_GetInfo,
6796 Promise_New,
6797 PromiseResolver_Resolve,
6798 PromiseResolver_Reject,
6799 FixedArray_New_Boolean,
6800 FixedArray_New_Char,
6801 FixedArray_New_Byte,
6802 FixedArray_New_Short,
6803 FixedArray_New_Int,
6804 FixedArray_New_Long,
6805 FixedArray_New_Float,
6806 FixedArray_New_Double,
6807 FixedArray_New_Ref
6808 };
6809 // clang-format on
6810
GetInteractionAPI()6811 const __ani_interaction_api *GetInteractionAPI()
6812 {
6813 return &INTERACTION_API;
6814 }
6815
IsVersionSupported(uint32_t version)6816 bool IsVersionSupported(uint32_t version)
6817 {
6818 return version == ANI_VERSION_1;
6819 }
6820
6821 } // namespace ark::ets::ani
6822