wasm_native.c 53 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536
  1. /*
  2. * Copyright (C) 2019 Intel Corporation. All rights reserved.
  3. * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  4. */
  5. #include "wasm_native.h"
  6. #include "wasm_runtime_common.h"
  7. #include "bh_log.h"
  8. #if WASM_ENABLE_INTERP != 0
  9. #include "../interpreter/wasm_runtime.h"
  10. #endif
  11. #if WASM_ENABLE_AOT != 0
  12. #include "../aot/aot_runtime.h"
  13. #endif
  14. #if WASM_ENABLE_THREAD_MGR != 0
  15. #include "../libraries/thread-mgr/thread_manager.h"
  16. #endif
  17. #if WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0
  18. #include "wasi_nn_host.h"
  19. #endif
  20. static NativeSymbolsList g_native_symbols_list = NULL;
  21. #if WASM_ENABLE_LIBC_WASI != 0
  22. static void *g_wasi_context_key;
  23. #endif /* WASM_ENABLE_LIBC_WASI */
  24. uint32
  25. get_libc_builtin_export_apis(NativeSymbol **p_libc_builtin_apis);
  26. #if WASM_ENABLE_SPEC_TEST != 0
  27. uint32
  28. get_spectest_export_apis(NativeSymbol **p_libc_builtin_apis);
  29. #endif
  30. #if WASM_ENABLE_SHARED_HEAP != 0
  31. uint32
  32. get_lib_shared_heap_export_apis(NativeSymbol **p_shared_heap_apis);
  33. #endif
  34. uint32
  35. get_libc_wasi_export_apis(NativeSymbol **p_libc_wasi_apis);
  36. uint32
  37. get_base_lib_export_apis(NativeSymbol **p_base_lib_apis);
  38. uint32
  39. get_ext_lib_export_apis(NativeSymbol **p_ext_lib_apis);
  40. #if WASM_ENABLE_LIB_PTHREAD != 0
  41. bool
  42. lib_pthread_init();
  43. void
  44. lib_pthread_destroy();
  45. uint32
  46. get_lib_pthread_export_apis(NativeSymbol **p_lib_pthread_apis);
  47. #endif
  48. #if WASM_ENABLE_LIB_WASI_THREADS != 0
  49. bool
  50. lib_wasi_threads_init(void);
  51. void
  52. lib_wasi_threads_destroy(void);
  53. uint32
  54. get_lib_wasi_threads_export_apis(NativeSymbol **p_lib_wasi_threads_apis);
  55. #endif
  56. uint32
  57. get_libc_emcc_export_apis(NativeSymbol **p_libc_emcc_apis);
  58. uint32
  59. get_lib_rats_export_apis(NativeSymbol **p_lib_rats_apis);
  60. static bool
  61. compare_type_with_signature(uint8 type, const char signature)
  62. {
  63. const char num_sig_map[] = { 'F', 'f', 'I', 'i' };
  64. if (VALUE_TYPE_F64 <= type && type <= VALUE_TYPE_I32
  65. && signature == num_sig_map[type - VALUE_TYPE_F64]) {
  66. return true;
  67. }
  68. #if WASM_ENABLE_REF_TYPES != 0
  69. if ('r' == signature
  70. #if WASM_ENABLE_GC != 0
  71. #if WASM_ENABLE_STRINGREF != 0
  72. && (type >= REF_TYPE_STRINGVIEWITER && type <= REF_TYPE_NULLFUNCREF)
  73. #else
  74. && (type >= REF_TYPE_HT_NULLABLE && type <= REF_TYPE_NULLFUNCREF)
  75. #endif
  76. #else
  77. && type == VALUE_TYPE_EXTERNREF
  78. #endif
  79. )
  80. return true;
  81. #endif
  82. /* TODO: a v128 parameter */
  83. return false;
  84. }
  85. static bool
  86. check_symbol_signature(const WASMFuncType *type, const char *signature)
  87. {
  88. const char *p = signature, *p_end;
  89. char sig;
  90. uint32 i = 0;
  91. if (!p || strlen(p) < 2)
  92. return false;
  93. p_end = p + strlen(signature);
  94. if (*p++ != '(')
  95. return false;
  96. if ((uint32)(p_end - p) < (uint32)(type->param_count + 1))
  97. /* signatures of parameters, and ')' */
  98. return false;
  99. for (i = 0; i < type->param_count; i++) {
  100. sig = *p++;
  101. /* a f64/f32/i64/i32/externref parameter */
  102. if (compare_type_with_signature(type->types[i], sig))
  103. continue;
  104. /* a pointer/string parameter */
  105. if (type->types[i] != VALUE_TYPE_I32)
  106. /* pointer and string must be i32 type */
  107. return false;
  108. if (sig == '*') {
  109. /* it is a pointer */
  110. if (i + 1 < type->param_count
  111. && type->types[i + 1] == VALUE_TYPE_I32 && *p == '~') {
  112. /* pointer length followed */
  113. i++;
  114. p++;
  115. }
  116. }
  117. else if (sig == '$') {
  118. /* it is a string */
  119. }
  120. else {
  121. /* invalid signature */
  122. return false;
  123. }
  124. }
  125. if (*p++ != ')')
  126. return false;
  127. if (type->result_count) {
  128. if (p >= p_end)
  129. return false;
  130. /* result types includes: f64,f32,i64,i32,externref */
  131. if (!compare_type_with_signature(type->types[i], *p))
  132. return false;
  133. p++;
  134. }
  135. if (*p != '\0')
  136. return false;
  137. return true;
  138. }
  139. static int
  140. native_symbol_cmp(const void *native_symbol1, const void *native_symbol2)
  141. {
  142. return strcmp(((const NativeSymbol *)native_symbol1)->symbol,
  143. ((const NativeSymbol *)native_symbol2)->symbol);
  144. }
  145. static void *
  146. lookup_symbol(NativeSymbol *native_symbols, uint32 n_native_symbols,
  147. const char *symbol, const char **p_signature, void **p_attachment)
  148. {
  149. NativeSymbol *native_symbol, key = { 0 };
  150. key.symbol = symbol;
  151. if ((native_symbol = bsearch(&key, native_symbols, n_native_symbols,
  152. sizeof(NativeSymbol), native_symbol_cmp))) {
  153. *p_signature = native_symbol->signature;
  154. *p_attachment = native_symbol->attachment;
  155. return native_symbol->func_ptr;
  156. }
  157. return NULL;
  158. }
  159. /**
  160. * allow func_type and all outputs, like p_signature, p_attachment and
  161. * p_call_conv_raw to be NULL
  162. */
  163. void *
  164. wasm_native_resolve_symbol(const char *module_name, const char *field_name,
  165. const WASMFuncType *func_type,
  166. const char **p_signature, void **p_attachment,
  167. bool *p_call_conv_raw)
  168. {
  169. NativeSymbolsNode *node, *node_next;
  170. const char *signature = NULL;
  171. void *func_ptr = NULL, *attachment = NULL;
  172. node = g_native_symbols_list;
  173. while (node) {
  174. node_next = node->next;
  175. if (!strcmp(node->module_name, module_name)) {
  176. if ((func_ptr =
  177. lookup_symbol(node->native_symbols, node->n_native_symbols,
  178. field_name, &signature, &attachment))
  179. || (field_name[0] == '_'
  180. && (func_ptr = lookup_symbol(
  181. node->native_symbols, node->n_native_symbols,
  182. field_name + 1, &signature, &attachment))))
  183. break;
  184. }
  185. node = node_next;
  186. }
  187. if (!p_signature || !p_attachment || !p_call_conv_raw)
  188. return func_ptr;
  189. if (func_ptr) {
  190. if (signature && signature[0] != '\0') {
  191. /* signature is not empty, check its format */
  192. if (!func_type || !check_symbol_signature(func_type, signature)) {
  193. #if WASM_ENABLE_WAMR_COMPILER == 0
  194. /* Output warning except running aot compiler */
  195. LOG_WARNING("failed to check signature '%s' and resolve "
  196. "pointer params for import function (%s, %s)\n",
  197. signature, module_name, field_name);
  198. #endif
  199. return NULL;
  200. }
  201. else
  202. /* Save signature for runtime to do pointer check and
  203. address conversion */
  204. *p_signature = signature;
  205. }
  206. else
  207. /* signature is empty */
  208. *p_signature = NULL;
  209. *p_attachment = attachment;
  210. *p_call_conv_raw = node->call_conv_raw;
  211. }
  212. return func_ptr;
  213. }
  214. static bool
  215. register_natives(const char *module_name, NativeSymbol *native_symbols,
  216. uint32 n_native_symbols, bool call_conv_raw)
  217. {
  218. NativeSymbolsNode *node;
  219. if (!(node = wasm_runtime_malloc(sizeof(NativeSymbolsNode))))
  220. return false;
  221. #if WASM_ENABLE_MEMORY_TRACING != 0
  222. os_printf("Register native, size: %u\n", sizeof(NativeSymbolsNode));
  223. #endif
  224. node->module_name = module_name;
  225. node->native_symbols = native_symbols;
  226. node->n_native_symbols = n_native_symbols;
  227. node->call_conv_raw = call_conv_raw;
  228. /* Add to list head */
  229. node->next = g_native_symbols_list;
  230. g_native_symbols_list = node;
  231. qsort(native_symbols, n_native_symbols, sizeof(NativeSymbol),
  232. native_symbol_cmp);
  233. return true;
  234. }
  235. bool
  236. wasm_native_register_natives(const char *module_name,
  237. NativeSymbol *native_symbols,
  238. uint32 n_native_symbols)
  239. {
  240. return register_natives(module_name, native_symbols, n_native_symbols,
  241. false);
  242. }
  243. bool
  244. wasm_native_register_natives_raw(const char *module_name,
  245. NativeSymbol *native_symbols,
  246. uint32 n_native_symbols)
  247. {
  248. return register_natives(module_name, native_symbols, n_native_symbols,
  249. true);
  250. }
  251. bool
  252. wasm_native_unregister_natives(const char *module_name,
  253. NativeSymbol *native_symbols)
  254. {
  255. NativeSymbolsNode **prevp;
  256. NativeSymbolsNode *node;
  257. prevp = &g_native_symbols_list;
  258. while ((node = *prevp) != NULL) {
  259. if (node->native_symbols == native_symbols
  260. && !strcmp(node->module_name, module_name)) {
  261. *prevp = node->next;
  262. wasm_runtime_free(node);
  263. return true;
  264. }
  265. prevp = &node->next;
  266. }
  267. return false;
  268. }
  269. #if WASM_ENABLE_MODULE_INST_CONTEXT != 0
  270. static uint32
  271. context_key_to_idx(void *key)
  272. {
  273. bh_assert(key != NULL);
  274. uint32 idx = (uint32)(uintptr_t)key;
  275. bh_assert(idx > 0);
  276. bh_assert(idx <= WASM_MAX_INSTANCE_CONTEXTS);
  277. return idx - 1;
  278. }
  279. static void *
  280. context_idx_to_key(uint32 idx)
  281. {
  282. bh_assert(idx < WASM_MAX_INSTANCE_CONTEXTS);
  283. return (void *)(uintptr_t)(idx + 1);
  284. }
  285. typedef void (*dtor_t)(WASMModuleInstanceCommon *, void *);
  286. static dtor_t g_context_dtors[WASM_MAX_INSTANCE_CONTEXTS];
  287. static void
  288. dtor_noop(WASMModuleInstanceCommon *inst, void *ctx)
  289. {
  290. }
  291. void *
  292. wasm_native_create_context_key(void (*dtor)(WASMModuleInstanceCommon *inst,
  293. void *ctx))
  294. {
  295. uint32 i;
  296. for (i = 0; i < WASM_MAX_INSTANCE_CONTEXTS; i++) {
  297. if (g_context_dtors[i] == NULL) {
  298. if (dtor == NULL) {
  299. dtor = dtor_noop;
  300. }
  301. g_context_dtors[i] = dtor;
  302. return context_idx_to_key(i);
  303. }
  304. }
  305. LOG_ERROR("failed to allocate instance context key");
  306. return NULL;
  307. }
  308. void
  309. wasm_native_destroy_context_key(void *key)
  310. {
  311. uint32 idx = context_key_to_idx(key);
  312. bh_assert(g_context_dtors[idx] != NULL);
  313. g_context_dtors[idx] = NULL;
  314. }
  315. static WASMModuleInstanceExtraCommon *
  316. wasm_module_inst_extra_common(WASMModuleInstanceCommon *inst)
  317. {
  318. #if WASM_ENABLE_INTERP != 0
  319. if (inst->module_type == Wasm_Module_Bytecode) {
  320. return &((WASMModuleInstance *)inst)->e->common;
  321. }
  322. #endif
  323. #if WASM_ENABLE_AOT != 0
  324. if (inst->module_type == Wasm_Module_AoT) {
  325. return &((AOTModuleInstanceExtra *)((AOTModuleInstance *)inst)->e)
  326. ->common;
  327. }
  328. #endif
  329. bh_assert(false);
  330. return NULL;
  331. }
  332. void
  333. wasm_native_set_context(WASMModuleInstanceCommon *inst, void *key, void *ctx)
  334. {
  335. uint32 idx = context_key_to_idx(key);
  336. WASMModuleInstanceExtraCommon *common = wasm_module_inst_extra_common(inst);
  337. common->contexts[idx] = ctx;
  338. }
  339. void
  340. wasm_native_set_context_spread(WASMModuleInstanceCommon *inst, void *key,
  341. void *ctx)
  342. {
  343. #if WASM_ENABLE_THREAD_MGR != 0
  344. wasm_cluster_set_context(inst, key, ctx);
  345. #else
  346. wasm_native_set_context(inst, key, ctx);
  347. #endif
  348. }
  349. void *
  350. wasm_native_get_context(WASMModuleInstanceCommon *inst, void *key)
  351. {
  352. uint32 idx = context_key_to_idx(key);
  353. WASMModuleInstanceExtraCommon *common = wasm_module_inst_extra_common(inst);
  354. return common->contexts[idx];
  355. }
  356. void
  357. wasm_native_call_context_dtors(WASMModuleInstanceCommon *inst)
  358. {
  359. WASMModuleInstanceExtraCommon *common = wasm_module_inst_extra_common(inst);
  360. uint32 i;
  361. for (i = 0; i < WASM_MAX_INSTANCE_CONTEXTS; i++) {
  362. dtor_t dtor = g_context_dtors[i];
  363. if (dtor != NULL) {
  364. dtor(inst, common->contexts[i]);
  365. }
  366. }
  367. }
  368. void
  369. wasm_native_inherit_contexts(WASMModuleInstanceCommon *child,
  370. WASMModuleInstanceCommon *parent)
  371. {
  372. WASMModuleInstanceExtraCommon *parent_common =
  373. wasm_module_inst_extra_common(parent);
  374. WASMModuleInstanceExtraCommon *child_common =
  375. wasm_module_inst_extra_common(child);
  376. bh_memcpy_s(child_common->contexts,
  377. sizeof(*child_common->contexts) * WASM_MAX_INSTANCE_CONTEXTS,
  378. parent_common->contexts,
  379. sizeof(*parent_common->contexts) * WASM_MAX_INSTANCE_CONTEXTS);
  380. }
  381. #endif /* WASM_ENABLE_MODULE_INST_CONTEXT != 0 */
  382. #if WASM_ENABLE_LIBC_WASI != 0
  383. WASIContext *
  384. wasm_runtime_get_wasi_ctx(WASMModuleInstanceCommon *module_inst_comm)
  385. {
  386. return wasm_native_get_context(module_inst_comm, g_wasi_context_key);
  387. }
  388. void
  389. wasm_runtime_set_wasi_ctx(WASMModuleInstanceCommon *module_inst_comm,
  390. WASIContext *wasi_ctx)
  391. {
  392. wasm_native_set_context(module_inst_comm, g_wasi_context_key, wasi_ctx);
  393. }
  394. static void
  395. wasi_context_dtor(WASMModuleInstanceCommon *inst, void *ctx)
  396. {
  397. if (ctx == NULL) {
  398. return;
  399. }
  400. wasm_runtime_destroy_wasi(inst);
  401. }
  402. #endif /* end of WASM_ENABLE_LIBC_WASI */
  403. #if WASM_ENABLE_QUICK_AOT_ENTRY != 0
  404. static bool
  405. quick_aot_entry_init(void);
  406. #endif
  407. bool
  408. wasm_native_init()
  409. {
  410. #if WASM_ENABLE_SPEC_TEST != 0 || WASM_ENABLE_LIBC_BUILTIN != 0 \
  411. || WASM_ENABLE_BASE_LIB != 0 || WASM_ENABLE_LIBC_EMCC != 0 \
  412. || WASM_ENABLE_LIB_RATS != 0 || WASM_ENABLE_WASI_NN != 0 \
  413. || WASM_ENABLE_APP_FRAMEWORK != 0 || WASM_ENABLE_LIBC_WASI != 0 \
  414. || WASM_ENABLE_LIB_PTHREAD != 0 || WASM_ENABLE_LIB_WASI_THREADS != 0 \
  415. || WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0 \
  416. || WASM_ENABLE_SHARED_HEAP != 0
  417. NativeSymbol *native_symbols;
  418. uint32 n_native_symbols;
  419. #endif
  420. #if WASM_ENABLE_LIBC_BUILTIN != 0
  421. n_native_symbols = get_libc_builtin_export_apis(&native_symbols);
  422. if (!wasm_native_register_natives("env", native_symbols, n_native_symbols))
  423. goto fail;
  424. #endif /* WASM_ENABLE_LIBC_BUILTIN */
  425. #if WASM_ENABLE_SPEC_TEST
  426. n_native_symbols = get_spectest_export_apis(&native_symbols);
  427. if (!wasm_native_register_natives("spectest", native_symbols,
  428. n_native_symbols))
  429. goto fail;
  430. #endif /* WASM_ENABLE_SPEC_TEST */
  431. #if WASM_ENABLE_LIBC_WASI != 0
  432. g_wasi_context_key = wasm_native_create_context_key(wasi_context_dtor);
  433. if (g_wasi_context_key == NULL) {
  434. goto fail;
  435. }
  436. n_native_symbols = get_libc_wasi_export_apis(&native_symbols);
  437. if (!wasm_native_register_natives("wasi_unstable", native_symbols,
  438. n_native_symbols))
  439. goto fail;
  440. if (!wasm_native_register_natives("wasi_snapshot_preview1", native_symbols,
  441. n_native_symbols))
  442. goto fail;
  443. #endif
  444. #if WASM_ENABLE_SHARED_HEAP != 0
  445. n_native_symbols = get_lib_shared_heap_export_apis(&native_symbols);
  446. if (n_native_symbols > 0
  447. && !wasm_native_register_natives("env", native_symbols,
  448. n_native_symbols))
  449. goto fail;
  450. #endif
  451. #if WASM_ENABLE_BASE_LIB != 0
  452. n_native_symbols = get_base_lib_export_apis(&native_symbols);
  453. if (n_native_symbols > 0
  454. && !wasm_native_register_natives("env", native_symbols,
  455. n_native_symbols))
  456. goto fail;
  457. #endif
  458. #if WASM_ENABLE_APP_FRAMEWORK != 0
  459. n_native_symbols = get_ext_lib_export_apis(&native_symbols);
  460. if (n_native_symbols > 0
  461. && !wasm_native_register_natives("env", native_symbols,
  462. n_native_symbols))
  463. goto fail;
  464. #endif
  465. #if WASM_ENABLE_LIB_PTHREAD != 0
  466. if (!lib_pthread_init())
  467. goto fail;
  468. n_native_symbols = get_lib_pthread_export_apis(&native_symbols);
  469. if (n_native_symbols > 0
  470. && !wasm_native_register_natives("env", native_symbols,
  471. n_native_symbols))
  472. goto fail;
  473. #endif
  474. #if WASM_ENABLE_LIB_WASI_THREADS != 0
  475. if (!lib_wasi_threads_init())
  476. goto fail;
  477. n_native_symbols = get_lib_wasi_threads_export_apis(&native_symbols);
  478. if (n_native_symbols > 0
  479. && !wasm_native_register_natives("wasi", native_symbols,
  480. n_native_symbols))
  481. goto fail;
  482. #endif
  483. #if WASM_ENABLE_LIBC_EMCC != 0
  484. n_native_symbols = get_libc_emcc_export_apis(&native_symbols);
  485. if (n_native_symbols > 0
  486. && !wasm_native_register_natives("env", native_symbols,
  487. n_native_symbols))
  488. goto fail;
  489. #endif /* WASM_ENABLE_LIBC_EMCC */
  490. #if WASM_ENABLE_LIB_RATS != 0
  491. n_native_symbols = get_lib_rats_export_apis(&native_symbols);
  492. if (n_native_symbols > 0
  493. && !wasm_native_register_natives("env", native_symbols,
  494. n_native_symbols))
  495. goto fail;
  496. #endif /* WASM_ENABLE_LIB_RATS */
  497. #if WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0
  498. if (!wasi_nn_initialize())
  499. goto fail;
  500. n_native_symbols = get_wasi_nn_export_apis(&native_symbols);
  501. if (n_native_symbols > 0
  502. && !wasm_native_register_natives(
  503. #if WASM_ENABLE_WASI_EPHEMERAL_NN != 0
  504. "wasi_ephemeral_nn",
  505. #else
  506. "wasi_nn",
  507. #endif /* WASM_ENABLE_WASI_EPHEMERAL_NN != 0 */
  508. native_symbols, n_native_symbols))
  509. goto fail;
  510. #endif /* WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0 */
  511. #if WASM_ENABLE_QUICK_AOT_ENTRY != 0
  512. if (!quick_aot_entry_init()) {
  513. #if WASM_ENABLE_SPEC_TEST != 0 || WASM_ENABLE_LIBC_BUILTIN != 0 \
  514. || WASM_ENABLE_BASE_LIB != 0 || WASM_ENABLE_LIBC_EMCC != 0 \
  515. || WASM_ENABLE_LIB_RATS != 0 || WASM_ENABLE_WASI_NN != 0 \
  516. || WASM_ENABLE_APP_FRAMEWORK != 0 || WASM_ENABLE_LIBC_WASI != 0 \
  517. || WASM_ENABLE_LIB_PTHREAD != 0 || WASM_ENABLE_LIB_WASI_THREADS != 0 \
  518. || WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0 \
  519. || WASM_ENABLE_SHARED_HEAP != 0
  520. goto fail;
  521. #else
  522. return false;
  523. #endif
  524. }
  525. #endif
  526. return true;
  527. #if WASM_ENABLE_SPEC_TEST != 0 || WASM_ENABLE_LIBC_BUILTIN != 0 \
  528. || WASM_ENABLE_BASE_LIB != 0 || WASM_ENABLE_LIBC_EMCC != 0 \
  529. || WASM_ENABLE_LIB_RATS != 0 || WASM_ENABLE_WASI_NN != 0 \
  530. || WASM_ENABLE_APP_FRAMEWORK != 0 || WASM_ENABLE_LIBC_WASI != 0 \
  531. || WASM_ENABLE_LIB_PTHREAD != 0 || WASM_ENABLE_LIB_WASI_THREADS != 0 \
  532. || WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0 \
  533. || WASM_ENABLE_SHARED_HEAP != 0
  534. fail:
  535. wasm_native_destroy();
  536. return false;
  537. #endif
  538. }
  539. void
  540. wasm_native_destroy()
  541. {
  542. NativeSymbolsNode *node, *node_next;
  543. #if WASM_ENABLE_LIBC_WASI != 0
  544. if (g_wasi_context_key != NULL) {
  545. wasm_native_destroy_context_key(g_wasi_context_key);
  546. g_wasi_context_key = NULL;
  547. }
  548. #endif
  549. #if WASM_ENABLE_LIB_PTHREAD != 0
  550. lib_pthread_destroy();
  551. #endif
  552. #if WASM_ENABLE_LIB_WASI_THREADS != 0
  553. lib_wasi_threads_destroy();
  554. #endif
  555. #if WASM_ENABLE_WASI_NN != 0 || WASM_ENABLE_WASI_EPHEMERAL_NN != 0
  556. wasi_nn_destroy();
  557. #endif
  558. node = g_native_symbols_list;
  559. while (node) {
  560. node_next = node->next;
  561. wasm_runtime_free(node);
  562. node = node_next;
  563. }
  564. g_native_symbols_list = NULL;
  565. }
  566. #if WASM_ENABLE_QUICK_AOT_ENTRY != 0
  567. static void
  568. invoke_no_args_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  569. {
  570. void (*native_code)(WASMExecEnv *) = func_ptr;
  571. native_code(exec_env);
  572. }
  573. static void
  574. invoke_no_args_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  575. {
  576. int32 (*native_code)(WASMExecEnv *) = func_ptr;
  577. argv_ret[0] = native_code(exec_env);
  578. }
  579. static void
  580. invoke_no_args_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  581. {
  582. int64 (*native_code)(WASMExecEnv *) = func_ptr;
  583. int64 ret = native_code(exec_env);
  584. PUT_I64_TO_ADDR(argv_ret, ret);
  585. }
  586. static void
  587. invoke_i_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  588. {
  589. void (*native_code)(WASMExecEnv *, int32) = func_ptr;
  590. native_code(exec_env, argv[0]);
  591. }
  592. static void
  593. invoke_i_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  594. {
  595. int32 (*native_code)(WASMExecEnv *, int32) = func_ptr;
  596. argv_ret[0] = native_code(exec_env, argv[0]);
  597. }
  598. static void
  599. invoke_i_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  600. {
  601. int64 (*native_code)(WASMExecEnv *, int32) = func_ptr;
  602. int64 ret = native_code(exec_env, argv[0]);
  603. PUT_I64_TO_ADDR(argv_ret, ret);
  604. }
  605. static void
  606. invoke_I_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  607. {
  608. void (*native_code)(WASMExecEnv *, int64) = func_ptr;
  609. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv));
  610. }
  611. static void
  612. invoke_I_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  613. {
  614. int32 (*native_code)(WASMExecEnv *, int64) = func_ptr;
  615. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv));
  616. }
  617. static void
  618. invoke_I_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  619. {
  620. int64 (*native_code)(WASMExecEnv *, int64) = func_ptr;
  621. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv));
  622. PUT_I64_TO_ADDR(argv_ret, ret);
  623. }
  624. static void
  625. invoke_ii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  626. {
  627. void (*native_code)(WASMExecEnv *, int32, int32) = func_ptr;
  628. native_code(exec_env, argv[0], argv[1]);
  629. }
  630. static void
  631. invoke_ii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  632. {
  633. int32 (*native_code)(WASMExecEnv *, int32, int32) = func_ptr;
  634. argv_ret[0] = native_code(exec_env, argv[0], argv[1]);
  635. }
  636. static void
  637. invoke_ii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  638. {
  639. int64 (*native_code)(WASMExecEnv *, int32, int32) = func_ptr;
  640. int64 ret = native_code(exec_env, argv[0], argv[1]);
  641. PUT_I64_TO_ADDR(argv_ret, ret);
  642. }
  643. static void
  644. invoke_iI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  645. {
  646. void (*native_code)(WASMExecEnv *, int32, int64) = func_ptr;
  647. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1));
  648. }
  649. static void
  650. invoke_iI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  651. {
  652. int32 (*native_code)(WASMExecEnv *, int32, int64) = func_ptr;
  653. argv_ret[0] =
  654. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1));
  655. }
  656. static void
  657. invoke_iI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  658. {
  659. int64 (*native_code)(WASMExecEnv *, int32, int64) = func_ptr;
  660. int64 ret =
  661. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1));
  662. PUT_I64_TO_ADDR(argv_ret, ret);
  663. }
  664. static void
  665. invoke_Ii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  666. {
  667. void (*native_code)(WASMExecEnv *, int64, int32) = func_ptr;
  668. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2]);
  669. }
  670. static void
  671. invoke_Ii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  672. {
  673. int32 (*native_code)(WASMExecEnv *, int64, int32) = func_ptr;
  674. argv_ret[0] =
  675. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2]);
  676. }
  677. static void
  678. invoke_Ii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  679. {
  680. int64 (*native_code)(WASMExecEnv *, int64, int32) = func_ptr;
  681. int64 ret =
  682. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2]);
  683. PUT_I64_TO_ADDR(argv_ret, ret);
  684. }
  685. static void
  686. invoke_II_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  687. {
  688. void (*native_code)(WASMExecEnv *, int64, int64) = func_ptr;
  689. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  690. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  691. }
  692. static void
  693. invoke_II_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  694. {
  695. int32 (*native_code)(WASMExecEnv *, int64, int64) = func_ptr;
  696. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  697. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  698. }
  699. static void
  700. invoke_II_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  701. {
  702. int64 (*native_code)(WASMExecEnv *, int64, int64) = func_ptr;
  703. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  704. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  705. PUT_I64_TO_ADDR(argv_ret, ret);
  706. }
  707. static void
  708. invoke_iii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  709. {
  710. void (*native_code)(WASMExecEnv *, int32, int32, int32) = func_ptr;
  711. native_code(exec_env, argv[0], argv[1], argv[2]);
  712. }
  713. static void
  714. invoke_iii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  715. {
  716. int32 (*native_code)(WASMExecEnv *, int32, int32, int32) = func_ptr;
  717. argv_ret[0] = native_code(exec_env, argv[0], argv[1], argv[2]);
  718. }
  719. static void
  720. invoke_iii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  721. {
  722. int64 (*native_code)(WASMExecEnv *, int32, int32, int32) = func_ptr;
  723. int64 ret = native_code(exec_env, argv[0], argv[1], argv[2]);
  724. PUT_I64_TO_ADDR(argv_ret, ret);
  725. }
  726. static void
  727. invoke_iiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  728. {
  729. void (*native_code)(WASMExecEnv *, int32, int32, int64) = func_ptr;
  730. native_code(exec_env, argv[0], argv[1],
  731. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  732. }
  733. static void
  734. invoke_iiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  735. {
  736. int32 (*native_code)(WASMExecEnv *, int32, int32, int64) = func_ptr;
  737. argv_ret[0] = native_code(exec_env, argv[0], argv[1],
  738. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  739. }
  740. static void
  741. invoke_iiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  742. {
  743. int64 (*native_code)(WASMExecEnv *, int32, int32, int64) = func_ptr;
  744. int64 ret = native_code(exec_env, argv[0], argv[1],
  745. GET_I64_FROM_ADDR((uint32 *)argv + 2));
  746. PUT_I64_TO_ADDR(argv_ret, ret);
  747. }
  748. static void
  749. invoke_iIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  750. {
  751. void (*native_code)(WASMExecEnv *, int32, int64, int32) = func_ptr;
  752. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  753. argv[3]);
  754. }
  755. static void
  756. invoke_iIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  757. {
  758. int32 (*native_code)(WASMExecEnv *, int32, int64, int32) = func_ptr;
  759. argv_ret[0] = native_code(exec_env, argv[0],
  760. GET_I64_FROM_ADDR((uint32 *)argv + 1), argv[3]);
  761. }
  762. static void
  763. invoke_iIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  764. {
  765. int64 (*native_code)(WASMExecEnv *, int32, int64, int32) = func_ptr;
  766. int64 ret = native_code(exec_env, argv[0],
  767. GET_I64_FROM_ADDR((uint32 *)argv + 1), argv[3]);
  768. PUT_I64_TO_ADDR(argv_ret, ret);
  769. }
  770. static void
  771. invoke_iII_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  772. {
  773. void (*native_code)(WASMExecEnv *, int32, int64, int64) = func_ptr;
  774. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  775. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  776. }
  777. static void
  778. invoke_iII_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  779. {
  780. int32 (*native_code)(WASMExecEnv *, int32, int64, int64) = func_ptr;
  781. argv_ret[0] =
  782. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  783. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  784. }
  785. static void
  786. invoke_iII_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  787. {
  788. int64 (*native_code)(WASMExecEnv *, int32, int64, int64) = func_ptr;
  789. int64 ret =
  790. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  791. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  792. PUT_I64_TO_ADDR(argv_ret, ret);
  793. }
  794. static void
  795. invoke_Iii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  796. {
  797. void (*native_code)(WASMExecEnv *, int64, int32, int32) = func_ptr;
  798. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2], argv[3]);
  799. }
  800. static void
  801. invoke_Iii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  802. {
  803. int32 (*native_code)(WASMExecEnv *, int64, int32, int32) = func_ptr;
  804. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  805. argv[2], argv[3]);
  806. }
  807. static void
  808. invoke_Iii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  809. {
  810. int64 (*native_code)(WASMExecEnv *, int64, int32, int32) = func_ptr;
  811. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  812. argv[2], argv[3]);
  813. PUT_I64_TO_ADDR(argv_ret, ret);
  814. }
  815. static void
  816. invoke_IiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  817. {
  818. void (*native_code)(WASMExecEnv *, int64, int32, int64) = func_ptr;
  819. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  820. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  821. }
  822. static void
  823. invoke_IiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  824. {
  825. int32 (*native_code)(WASMExecEnv *, int64, int32, int64) = func_ptr;
  826. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  827. argv[2], GET_I64_FROM_ADDR((uint32 *)argv + 3));
  828. }
  829. static void
  830. invoke_IiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  831. {
  832. int64 (*native_code)(WASMExecEnv *, int64, int32, int64) = func_ptr;
  833. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  834. argv[2], GET_I64_FROM_ADDR((uint32 *)argv + 3));
  835. PUT_I64_TO_ADDR(argv_ret, ret);
  836. }
  837. static void
  838. invoke_IIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  839. {
  840. void (*native_code)(WASMExecEnv *, int64, int64, int32) = func_ptr;
  841. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  842. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  843. }
  844. static void
  845. invoke_IIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  846. {
  847. int32 (*native_code)(WASMExecEnv *, int64, int64, int32) = func_ptr;
  848. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  849. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  850. }
  851. static void
  852. invoke_IIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  853. {
  854. int64 (*native_code)(WASMExecEnv *, int64, int64, int32) = func_ptr;
  855. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  856. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  857. PUT_I64_TO_ADDR(argv_ret, ret);
  858. }
  859. static void
  860. invoke_III_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  861. {
  862. void (*native_code)(WASMExecEnv *, int64, int64, int64) = func_ptr;
  863. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  864. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  865. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  866. }
  867. static void
  868. invoke_III_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  869. {
  870. int32 (*native_code)(WASMExecEnv *, int64, int64, int64) = func_ptr;
  871. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  872. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  873. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  874. }
  875. static void
  876. invoke_III_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  877. {
  878. int64 (*native_code)(WASMExecEnv *, int64, int64, int64) = func_ptr;
  879. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  880. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  881. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  882. PUT_I64_TO_ADDR(argv_ret, ret);
  883. }
  884. static void
  885. invoke_iiii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  886. {
  887. void (*native_code)(WASMExecEnv *, int32, int32, int32, int32) = func_ptr;
  888. native_code(exec_env, argv[0], argv[1], argv[2], argv[3]);
  889. }
  890. static void
  891. invoke_iiii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  892. {
  893. int32 (*native_code)(WASMExecEnv *, int32, int32, int32, int32) = func_ptr;
  894. argv_ret[0] = native_code(exec_env, argv[0], argv[1], argv[2], argv[3]);
  895. }
  896. static void
  897. invoke_iiii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  898. {
  899. int64 (*native_code)(WASMExecEnv *, int32, int32, int32, int32) = func_ptr;
  900. int64 ret = native_code(exec_env, argv[0], argv[1], argv[2], argv[3]);
  901. PUT_I64_TO_ADDR(argv_ret, ret);
  902. }
  903. static void
  904. invoke_iiiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  905. {
  906. void (*native_code)(WASMExecEnv *, int32, int32, int32, int64) = func_ptr;
  907. native_code(exec_env, argv[0], argv[1], argv[2],
  908. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  909. }
  910. static void
  911. invoke_iiiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  912. {
  913. int32 (*native_code)(WASMExecEnv *, int32, int32, int32, int64) = func_ptr;
  914. argv_ret[0] = native_code(exec_env, argv[0], argv[1], argv[2],
  915. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  916. }
  917. static void
  918. invoke_iiiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  919. {
  920. int64 (*native_code)(WASMExecEnv *, int32, int32, int32, int64) = func_ptr;
  921. int64 ret = native_code(exec_env, argv[0], argv[1], argv[2],
  922. GET_I64_FROM_ADDR((uint32 *)argv + 3));
  923. PUT_I64_TO_ADDR(argv_ret, ret);
  924. }
  925. static void
  926. invoke_iiIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  927. {
  928. void (*native_code)(WASMExecEnv *, int32, int32, int64, int32) = func_ptr;
  929. native_code(exec_env, argv[0], argv[1],
  930. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  931. }
  932. static void
  933. invoke_iiIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  934. {
  935. int32 (*native_code)(WASMExecEnv *, int32, int32, int64, int32) = func_ptr;
  936. argv_ret[0] = native_code(exec_env, argv[0], argv[1],
  937. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  938. }
  939. static void
  940. invoke_iiIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  941. {
  942. int64 (*native_code)(WASMExecEnv *, int32, int32, int64, int32) = func_ptr;
  943. int64 ret = native_code(exec_env, argv[0], argv[1],
  944. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4]);
  945. PUT_I64_TO_ADDR(argv_ret, ret);
  946. }
  947. static void
  948. invoke_iiII_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  949. {
  950. void (*native_code)(WASMExecEnv *, int32, int32, int64, int64) = func_ptr;
  951. native_code(exec_env, argv[0], argv[1],
  952. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  953. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  954. }
  955. static void
  956. invoke_iiII_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  957. {
  958. int32 (*native_code)(WASMExecEnv *, int32, int32, int64, int64) = func_ptr;
  959. argv_ret[0] = native_code(exec_env, argv[0], argv[1],
  960. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  961. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  962. }
  963. static void
  964. invoke_iiII_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  965. {
  966. int64 (*native_code)(WASMExecEnv *, int32, int32, int64, int64) = func_ptr;
  967. int64 ret = native_code(exec_env, argv[0], argv[1],
  968. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  969. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  970. PUT_I64_TO_ADDR(argv_ret, ret);
  971. }
  972. static void
  973. invoke_iIii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  974. {
  975. void (*native_code)(WASMExecEnv *, int32, int64, int32, int32) = func_ptr;
  976. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  977. argv[3], argv[4]);
  978. }
  979. static void
  980. invoke_iIii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  981. {
  982. int32 (*native_code)(WASMExecEnv *, int32, int64, int32, int32) = func_ptr;
  983. argv_ret[0] =
  984. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  985. argv[3], argv[4]);
  986. }
  987. static void
  988. invoke_iIii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  989. {
  990. int64 (*native_code)(WASMExecEnv *, int32, int64, int32, int32) = func_ptr;
  991. int64 ret =
  992. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  993. argv[3], argv[4]);
  994. PUT_I64_TO_ADDR(argv_ret, ret);
  995. }
  996. static void
  997. invoke_iIiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  998. {
  999. void (*native_code)(WASMExecEnv *, int32, int64, int32, int64) = func_ptr;
  1000. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1001. argv[3], GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1002. }
  1003. static void
  1004. invoke_iIiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1005. {
  1006. int32 (*native_code)(WASMExecEnv *, int32, int64, int32, int64) = func_ptr;
  1007. argv_ret[0] =
  1008. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1009. argv[3], GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1010. }
  1011. static void
  1012. invoke_iIiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1013. {
  1014. int64 (*native_code)(WASMExecEnv *, int32, int64, int32, int64) = func_ptr;
  1015. int64 ret =
  1016. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1017. argv[3], GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1018. PUT_I64_TO_ADDR(argv_ret, ret);
  1019. }
  1020. static void
  1021. invoke_iIIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1022. {
  1023. void (*native_code)(WASMExecEnv *, int32, int64, int64, int32) = func_ptr;
  1024. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1025. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1026. }
  1027. static void
  1028. invoke_iIIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1029. {
  1030. int32 (*native_code)(WASMExecEnv *, int32, int64, int64, int32) = func_ptr;
  1031. argv_ret[0] =
  1032. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1033. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1034. }
  1035. static void
  1036. invoke_iIIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1037. {
  1038. int64 (*native_code)(WASMExecEnv *, int32, int64, int64, int32) = func_ptr;
  1039. int64 ret =
  1040. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1041. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1042. PUT_I64_TO_ADDR(argv_ret, ret);
  1043. }
  1044. static void
  1045. invoke_iIII_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1046. {
  1047. void (*native_code)(WASMExecEnv *, int32, int64, int64, int64) = func_ptr;
  1048. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1049. GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1050. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1051. }
  1052. static void
  1053. invoke_iIII_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1054. {
  1055. int32 (*native_code)(WASMExecEnv *, int32, int64, int64, int64) = func_ptr;
  1056. argv_ret[0] =
  1057. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1058. GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1059. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1060. }
  1061. static void
  1062. invoke_iIII_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1063. {
  1064. int64 (*native_code)(WASMExecEnv *, int32, int64, int64, int64) = func_ptr;
  1065. int64 ret =
  1066. native_code(exec_env, argv[0], GET_I64_FROM_ADDR((uint32 *)argv + 1),
  1067. GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1068. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1069. PUT_I64_TO_ADDR(argv_ret, ret);
  1070. }
  1071. static void
  1072. invoke_Iiii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1073. {
  1074. void (*native_code)(WASMExecEnv *, int64, int32, int32, int32) = func_ptr;
  1075. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2], argv[3],
  1076. argv[4]);
  1077. }
  1078. static void
  1079. invoke_Iiii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1080. {
  1081. int32 (*native_code)(WASMExecEnv *, int64, int32, int32, int32) = func_ptr;
  1082. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1083. argv[2], argv[3], argv[4]);
  1084. }
  1085. static void
  1086. invoke_Iiii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1087. {
  1088. int64 (*native_code)(WASMExecEnv *, int64, int32, int32, int32) = func_ptr;
  1089. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1090. argv[2], argv[3], argv[4]);
  1091. PUT_I64_TO_ADDR(argv_ret, ret);
  1092. }
  1093. static void
  1094. invoke_IiiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1095. {
  1096. void (*native_code)(WASMExecEnv *, int64, int32, int32, int64) = func_ptr;
  1097. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2], argv[3],
  1098. GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1099. }
  1100. static void
  1101. invoke_IiiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1102. {
  1103. int32 (*native_code)(WASMExecEnv *, int64, int32, int32, int64) = func_ptr;
  1104. argv_ret[0] =
  1105. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1106. argv[3], GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1107. }
  1108. static void
  1109. invoke_IiiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1110. {
  1111. int64 (*native_code)(WASMExecEnv *, int64, int32, int32, int64) = func_ptr;
  1112. int64 ret =
  1113. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1114. argv[3], GET_I64_FROM_ADDR((uint32 *)argv + 4));
  1115. PUT_I64_TO_ADDR(argv_ret, ret);
  1116. }
  1117. static void
  1118. invoke_IiIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1119. {
  1120. void (*native_code)(WASMExecEnv *, int64, int32, int64, int32) = func_ptr;
  1121. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1122. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1123. }
  1124. static void
  1125. invoke_IiIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1126. {
  1127. int32 (*native_code)(WASMExecEnv *, int64, int32, int64, int32) = func_ptr;
  1128. argv_ret[0] =
  1129. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1130. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1131. }
  1132. static void
  1133. invoke_IiIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1134. {
  1135. int64 (*native_code)(WASMExecEnv *, int64, int32, int64, int32) = func_ptr;
  1136. int64 ret =
  1137. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1138. GET_I64_FROM_ADDR((uint32 *)argv + 3), argv[5]);
  1139. PUT_I64_TO_ADDR(argv_ret, ret);
  1140. }
  1141. static void
  1142. invoke_IiII_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1143. {
  1144. void (*native_code)(WASMExecEnv *, int64, int32, int64, int64) = func_ptr;
  1145. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv), argv[2],
  1146. GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1147. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1148. }
  1149. static void
  1150. invoke_IiII_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1151. {
  1152. int32 (*native_code)(WASMExecEnv *, int64, int32, int64, int64) = func_ptr;
  1153. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1154. argv[2], GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1155. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1156. }
  1157. static void
  1158. invoke_IiII_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1159. {
  1160. int64 (*native_code)(WASMExecEnv *, int64, int32, int64, int64) = func_ptr;
  1161. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1162. argv[2], GET_I64_FROM_ADDR((uint32 *)argv + 3),
  1163. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1164. PUT_I64_TO_ADDR(argv_ret, ret);
  1165. }
  1166. static void
  1167. invoke_IIii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1168. {
  1169. void (*native_code)(WASMExecEnv *, int64, int64, int32, int32) = func_ptr;
  1170. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1171. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4], argv[5]);
  1172. }
  1173. static void
  1174. invoke_IIii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1175. {
  1176. int32 (*native_code)(WASMExecEnv *, int64, int64, int32, int32) = func_ptr;
  1177. argv_ret[0] =
  1178. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1179. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4], argv[5]);
  1180. }
  1181. static void
  1182. invoke_IIii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1183. {
  1184. int64 (*native_code)(WASMExecEnv *, int64, int64, int32, int32) = func_ptr;
  1185. int64 ret =
  1186. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1187. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4], argv[5]);
  1188. PUT_I64_TO_ADDR(argv_ret, ret);
  1189. }
  1190. static void
  1191. invoke_IIiI_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1192. {
  1193. void (*native_code)(WASMExecEnv *, int64, int64, int32, int64) = func_ptr;
  1194. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1195. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4],
  1196. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1197. }
  1198. static void
  1199. invoke_IIiI_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1200. {
  1201. int32 (*native_code)(WASMExecEnv *, int64, int64, int32, int64) = func_ptr;
  1202. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1203. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4],
  1204. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1205. }
  1206. static void
  1207. invoke_IIiI_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1208. {
  1209. int64 (*native_code)(WASMExecEnv *, int64, int64, int32, int64) = func_ptr;
  1210. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1211. GET_I64_FROM_ADDR((uint32 *)argv + 2), argv[4],
  1212. GET_I64_FROM_ADDR((uint32 *)argv + 5));
  1213. PUT_I64_TO_ADDR(argv_ret, ret);
  1214. }
  1215. static void
  1216. invoke_IIIi_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1217. {
  1218. void (*native_code)(WASMExecEnv *, int64, int64, int64, int32) = func_ptr;
  1219. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1220. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1221. GET_I64_FROM_ADDR((uint32 *)argv + 4), argv[6]);
  1222. }
  1223. static void
  1224. invoke_IIIi_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1225. {
  1226. int32 (*native_code)(WASMExecEnv *, int64, int64, int64, int32) = func_ptr;
  1227. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1228. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1229. GET_I64_FROM_ADDR((uint32 *)argv + 4), argv[6]);
  1230. }
  1231. static void
  1232. invoke_IIIi_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1233. {
  1234. int64 (*native_code)(WASMExecEnv *, int64, int64, int64, int32) = func_ptr;
  1235. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1236. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1237. GET_I64_FROM_ADDR((uint32 *)argv + 4), argv[6]);
  1238. PUT_I64_TO_ADDR(argv_ret, ret);
  1239. }
  1240. static void
  1241. invoke_IIII_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1242. {
  1243. void (*native_code)(WASMExecEnv *, int64, int64, int64, int64) = func_ptr;
  1244. native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1245. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1246. GET_I64_FROM_ADDR((uint32 *)argv + 4),
  1247. GET_I64_FROM_ADDR((uint32 *)argv + 6));
  1248. }
  1249. static void
  1250. invoke_IIII_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1251. {
  1252. int32 (*native_code)(WASMExecEnv *, int64, int64, int64, int64) = func_ptr;
  1253. argv_ret[0] = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1254. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1255. GET_I64_FROM_ADDR((uint32 *)argv + 4),
  1256. GET_I64_FROM_ADDR((uint32 *)argv + 6));
  1257. }
  1258. static void
  1259. invoke_IIII_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1260. {
  1261. int64 (*native_code)(WASMExecEnv *, int64, int64, int64, int64) = func_ptr;
  1262. int64 ret = native_code(exec_env, GET_I64_FROM_ADDR((uint32 *)argv),
  1263. GET_I64_FROM_ADDR((uint32 *)argv + 2),
  1264. GET_I64_FROM_ADDR((uint32 *)argv + 4),
  1265. GET_I64_FROM_ADDR((uint32 *)argv + 6));
  1266. PUT_I64_TO_ADDR(argv_ret, ret);
  1267. }
  1268. static void
  1269. invoke_iiiii_v(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1270. {
  1271. void (*native_code)(WASMExecEnv *, int32, int32, int32, int32, int32) =
  1272. func_ptr;
  1273. native_code(exec_env, argv[0], argv[1], argv[2], argv[3], argv[4]);
  1274. }
  1275. static void
  1276. invoke_iiiii_i(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1277. {
  1278. int32 (*native_code)(WASMExecEnv *, int32, int32, int32, int32, int32) =
  1279. func_ptr;
  1280. argv_ret[0] =
  1281. native_code(exec_env, argv[0], argv[1], argv[2], argv[3], argv[4]);
  1282. }
  1283. static void
  1284. invoke_iiiii_I(void *func_ptr, void *exec_env, int32 *argv, int32 *argv_ret)
  1285. {
  1286. int64 (*native_code)(WASMExecEnv *, int32, int32, int32, int32, int32) =
  1287. func_ptr;
  1288. int64 ret =
  1289. native_code(exec_env, argv[0], argv[1], argv[2], argv[3], argv[4]);
  1290. PUT_I64_TO_ADDR(argv_ret, ret);
  1291. }
  1292. typedef struct QuickAOTEntry {
  1293. const char *signature;
  1294. void *func_ptr;
  1295. } QuickAOTEntry;
  1296. /* clang-format off */
  1297. static QuickAOTEntry quick_aot_entries[] = {
  1298. { "()v", invoke_no_args_v },
  1299. { "()i", invoke_no_args_i },
  1300. { "()I", invoke_no_args_I },
  1301. { "(i)v", invoke_i_v }, { "(i)i", invoke_i_i }, { "(i)I", invoke_i_I },
  1302. { "(I)v", invoke_I_v }, { "(I)i", invoke_I_i }, { "(I)I", invoke_I_I },
  1303. { "(ii)v", invoke_ii_v }, { "(ii)i", invoke_ii_i }, { "(ii)I", invoke_ii_I },
  1304. { "(iI)v", invoke_iI_v }, { "(iI)i", invoke_iI_i }, { "(iI)I", invoke_iI_I },
  1305. { "(Ii)v", invoke_Ii_v }, { "(Ii)i", invoke_Ii_i }, { "(Ii)I", invoke_Ii_I },
  1306. { "(II)v", invoke_II_v }, { "(II)i", invoke_II_i }, { "(II)I", invoke_II_I },
  1307. { "(iii)v", invoke_iii_v }, { "(iii)i", invoke_iii_i }, { "(iii)I", invoke_iii_I },
  1308. { "(iiI)v", invoke_iiI_v }, { "(iiI)i", invoke_iiI_i }, { "(iiI)I", invoke_iiI_I },
  1309. { "(iIi)v", invoke_iIi_v }, { "(iIi)i", invoke_iIi_i }, { "(iIi)I", invoke_iIi_I },
  1310. { "(iII)v", invoke_iII_v }, { "(iII)i", invoke_iII_i }, { "(iII)I", invoke_iII_I },
  1311. { "(Iii)v", invoke_Iii_v }, { "(Iii)i", invoke_Iii_i }, { "(Iii)I", invoke_Iii_I },
  1312. { "(IiI)v", invoke_IiI_v }, { "(IiI)i", invoke_IiI_i }, { "(IiI)I", invoke_IiI_I },
  1313. { "(IIi)v", invoke_IIi_v }, { "(IIi)i", invoke_IIi_i }, { "(IIi)I", invoke_IIi_I },
  1314. { "(III)v", invoke_III_v }, { "(III)i", invoke_III_i }, { "(III)I", invoke_III_I },
  1315. { "(iiii)v", invoke_iiii_v }, { "(iiii)i", invoke_iiii_i }, { "(iiii)I", invoke_iiii_I },
  1316. { "(iiiI)v", invoke_iiiI_v }, { "(iiiI)i", invoke_iiiI_i }, { "(iiiI)I", invoke_iiiI_I },
  1317. { "(iiIi)v", invoke_iiIi_v }, { "(iiIi)i", invoke_iiIi_i }, { "(iiIi)I", invoke_iiIi_I },
  1318. { "(iiII)v", invoke_iiII_v }, { "(iiII)i", invoke_iiII_i }, { "(iiII)I", invoke_iiII_I },
  1319. { "(iIii)v", invoke_iIii_v }, { "(iIii)i", invoke_iIii_i }, { "(iIii)I", invoke_iIii_I },
  1320. { "(iIiI)v", invoke_iIiI_v }, { "(iIiI)i", invoke_iIiI_i }, { "(iIiI)I", invoke_iIiI_I },
  1321. { "(iIIi)v", invoke_iIIi_v }, { "(iIIi)i", invoke_iIIi_i }, { "(iIIi)I", invoke_iIIi_I },
  1322. { "(iIII)v", invoke_iIII_v }, { "(iIII)i", invoke_iIII_i }, { "(iIII)I", invoke_iIII_I },
  1323. { "(Iiii)v", invoke_Iiii_v }, { "(Iiii)i", invoke_Iiii_i }, { "(Iiii)I", invoke_Iiii_I },
  1324. { "(IiiI)v", invoke_IiiI_v }, { "(IiiI)i", invoke_IiiI_i }, { "(IiiI)I", invoke_IiiI_I },
  1325. { "(IiIi)v", invoke_IiIi_v }, { "(IiIi)i", invoke_IiIi_i }, { "(IiIi)I", invoke_IiIi_I },
  1326. { "(IiII)v", invoke_IiII_v }, { "(IiII)i", invoke_IiII_i }, { "(IiII)I", invoke_IiII_I },
  1327. { "(IIii)v", invoke_IIii_v }, { "(IIii)i", invoke_IIii_i }, { "(IIii)I", invoke_IIii_I },
  1328. { "(IIiI)v", invoke_IIiI_v }, { "(IIiI)i", invoke_IIiI_i }, { "(IIiI)I", invoke_IIiI_I },
  1329. { "(IIIi)v", invoke_IIIi_v }, { "(IIIi)i", invoke_IIIi_i }, { "(IIIi)I", invoke_IIIi_I },
  1330. { "(IIII)v", invoke_IIII_v }, { "(IIII)i", invoke_IIII_i }, { "(IIII)I", invoke_IIII_I },
  1331. { "(iiiii)v", invoke_iiiii_v }, { "(iiiii)i", invoke_iiiii_i }, { "(iiiii)I", invoke_iiiii_I },
  1332. };
  1333. /* clang-format on */
  1334. static int
  1335. quick_aot_entry_cmp(const void *quick_aot_entry1, const void *quick_aot_entry2)
  1336. {
  1337. return strcmp(((const QuickAOTEntry *)quick_aot_entry1)->signature,
  1338. ((const QuickAOTEntry *)quick_aot_entry2)->signature);
  1339. }
  1340. static bool
  1341. quick_aot_entry_init(void)
  1342. {
  1343. qsort(quick_aot_entries, sizeof(quick_aot_entries) / sizeof(QuickAOTEntry),
  1344. sizeof(QuickAOTEntry), quick_aot_entry_cmp);
  1345. return true;
  1346. }
  1347. void *
  1348. wasm_native_lookup_quick_aot_entry(const WASMFuncType *func_type)
  1349. {
  1350. char signature[16] = { 0 };
  1351. uint32 param_count = func_type->param_count;
  1352. uint32 result_count = func_type->result_count, i, j = 0;
  1353. const uint8 *types = func_type->types;
  1354. QuickAOTEntry *quick_aot_entry, key = { 0 };
  1355. if (param_count > 5 || result_count > 1)
  1356. return NULL;
  1357. signature[j++] = '(';
  1358. for (i = 0; i < param_count; i++) {
  1359. if (types[i] == VALUE_TYPE_I32)
  1360. signature[j++] = 'i';
  1361. else if (types[i] == VALUE_TYPE_I64)
  1362. signature[j++] = 'I';
  1363. else
  1364. return NULL;
  1365. }
  1366. signature[j++] = ')';
  1367. if (result_count == 0) {
  1368. signature[j++] = 'v';
  1369. }
  1370. else {
  1371. if (types[i] == VALUE_TYPE_I32)
  1372. signature[j++] = 'i';
  1373. else if (types[i] == VALUE_TYPE_I64)
  1374. signature[j++] = 'I';
  1375. else
  1376. return NULL;
  1377. }
  1378. key.signature = signature;
  1379. if ((quick_aot_entry =
  1380. bsearch(&key, quick_aot_entries,
  1381. sizeof(quick_aot_entries) / sizeof(QuickAOTEntry),
  1382. sizeof(QuickAOTEntry), quick_aot_entry_cmp))) {
  1383. return quick_aot_entry->func_ptr;
  1384. }
  1385. return NULL;
  1386. }
  1387. #endif /* end of WASM_ENABLE_QUICK_AOT_ENTRY != 0 */