koffi 2.16.1 → 3.0.0-alpha.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (84) hide show
  1. package/CHANGELOG.md +2 -2
  2. package/README.md +8 -8
  3. package/build/koffi/darwin_arm64/koffi.node +0 -0
  4. package/build/koffi/darwin_x64/koffi.node +0 -0
  5. package/build/koffi/freebsd_arm64/koffi.node +0 -0
  6. package/build/koffi/freebsd_ia32/koffi.node +0 -0
  7. package/build/koffi/freebsd_x64/koffi.node +0 -0
  8. package/build/koffi/linux_arm64/koffi.node +0 -0
  9. package/build/koffi/linux_ia32/koffi.node +0 -0
  10. package/build/koffi/linux_x64/koffi.node +0 -0
  11. package/build/koffi/musl_arm64/koffi.node +0 -0
  12. package/build/koffi/musl_x64/koffi.node +0 -0
  13. package/build/koffi/openbsd_ia32/koffi.node +0 -0
  14. package/build/koffi/openbsd_x64/koffi.node +0 -0
  15. package/build/koffi/win32_ia32/koffi.node +0 -0
  16. package/build/koffi/win32_x64/koffi.node +0 -0
  17. package/doc/benchmarks.md +33 -33
  18. package/doc/benchmarks.xlsx +0 -0
  19. package/doc/contribute.md +37 -25
  20. package/doc/index.md +8 -8
  21. package/doc/variables.md +1 -1
  22. package/index.d.ts +11 -9
  23. package/index.js +1 -634
  24. package/indirect.js +1 -533
  25. package/lib/native/base/base.cc +63 -85
  26. package/lib/native/base/base.hh +178 -151
  27. package/package.json +3 -4
  28. package/src/build.js +1178 -0
  29. package/src/koffi/CMakeLists.txt +97 -34
  30. package/src/koffi/index.js +359 -0
  31. package/src/koffi/indirect.js +216 -0
  32. package/src/koffi/src/{abi_arm32.cc → abi/arm32.cc} +279 -275
  33. package/src/koffi/src/{abi_arm32_asm.S → abi/arm32_asm.S} +2 -5
  34. package/src/koffi/src/abi/arm64.cc +1511 -0
  35. package/src/koffi/src/{abi_arm64_asm.S → abi/arm64_asm.S} +44 -23
  36. package/src/koffi/src/{abi_arm64_asm.asm → abi/arm64_asm.asm} +32 -25
  37. package/src/koffi/src/{abi_loong64_asm.S → abi/loong64_asm.S} +1 -5
  38. package/src/koffi/src/{abi_riscv64.cc → abi/riscv64.cc} +279 -273
  39. package/src/koffi/src/{abi_riscv64_asm.S → abi/riscv64_asm.S} +1 -4
  40. package/src/koffi/src/abi/x64sysv.cc +1456 -0
  41. package/src/koffi/src/{abi_x64_sysv_asm.S → abi/x64sysv_asm.S} +30 -33
  42. package/src/koffi/src/abi/x64win.cc +1121 -0
  43. package/src/koffi/src/{abi_x64_win_asm.S → abi/x64win_asm.S} +8 -12
  44. package/src/koffi/src/{abi_x64_win_asm.asm → abi/x64win_asm.asm} +11 -14
  45. package/src/koffi/src/abi/x86.cc +1233 -0
  46. package/src/koffi/src/{abi_x86_asm.S → abi/x86_asm.S} +49 -25
  47. package/src/koffi/src/{abi_x86_asm.asm → abi/x86_asm.asm} +11 -14
  48. package/src/koffi/src/call.cc +458 -598
  49. package/src/koffi/src/call.hh +61 -82
  50. package/src/koffi/src/ffi.cc +595 -309
  51. package/src/koffi/src/ffi.hh +103 -89
  52. package/src/koffi/src/parser.cc +0 -4
  53. package/src/koffi/src/primitives.inc +39 -0
  54. package/src/koffi/{tools/write_trampolines.js → src/trampolines.js} +1 -1
  55. package/src/koffi/src/util.cc +503 -446
  56. package/src/koffi/src/util.hh +269 -57
  57. package/src/koffi/src/uv.cc +2 -2
  58. package/src/koffi/src/uv.def +3 -0
  59. package/src/koffi/src/win32.hh +30 -1
  60. package/vendor/node-addon-api/napi-inl.h +4 -0
  61. package/vendor/node-addon-api/napi.h +1 -0
  62. package/build/koffi/linux_armhf/koffi.node +0 -0
  63. package/build/koffi/linux_loong64/koffi.node +0 -0
  64. package/build/koffi/linux_riscv64d/koffi.node +0 -0
  65. package/build/koffi/win32_arm64/koffi.exp +0 -0
  66. package/build/koffi/win32_arm64/koffi.lib +0 -0
  67. package/build/koffi/win32_arm64/koffi.node +0 -0
  68. package/doc/platforms.md +0 -36
  69. package/src/cnoke/LICENSE.txt +0 -22
  70. package/src/cnoke/README.md +0 -99
  71. package/src/cnoke/assets/FindCNoke.cmake +0 -127
  72. package/src/cnoke/assets/toolchains.json +0 -126
  73. package/src/cnoke/assets/win_delay_hook.c +0 -36
  74. package/src/cnoke/cnoke.js +0 -170
  75. package/src/cnoke/package.json +0 -24
  76. package/src/cnoke/src/builder.js +0 -511
  77. package/src/cnoke/src/index.js +0 -10
  78. package/src/cnoke/src/tools.js +0 -407
  79. package/src/koffi/src/abi_arm64.cc +0 -1295
  80. package/src/koffi/src/abi_x64_sysv.cc +0 -939
  81. package/src/koffi/src/abi_x64_win.cc +0 -715
  82. package/src/koffi/src/abi_x86.cc +0 -860
  83. package/src/koffi/src/init.js +0 -105
  84. /package/src/koffi/src/{abi_loong64.cc → abi/loong64.cc} +0 -0
@@ -39,135 +39,114 @@ struct alignas(8) CallData {
39
39
 
40
40
  Napi::Env env;
41
41
  InstanceData *instance;
42
-
43
42
  InstanceMemory *mem;
44
- Span<uint8_t> old_stack_mem;
45
- Span<uint8_t> old_heap_mem;
46
-
47
- uint8_t *new_sp;
48
- uint8_t *old_sp;
49
-
50
- union {
51
- int8_t i8;
52
- uint8_t u8;
53
- int16_t i16;
54
- uint16_t u16;
55
- int32_t i32;
56
- uint32_t u32;
57
- int64_t i64;
58
- uint64_t u64;
59
- float f;
60
- double d;
61
- void *ptr;
62
- uint8_t buf[32];
63
- } result;
64
- uint8_t *return_ptr = nullptr;
43
+ void *native;
65
44
 
66
- LocalArray<int16_t, 16> used_trampolines;
67
- HeapArray<OutArgument> out_arguments;
45
+ uint8_t *prev_stack;
46
+ uint8_t *prev_heap;
47
+ uint8_t *saved_sp;
48
+ bool release_alloc = false;
68
49
 
69
- BlockAllocator alloc;
50
+ uint8_t *async_base;
51
+ const AbiInstruction *async_ip;
70
52
 
71
- public:
72
- CallData(Napi::Env env, InstanceData *instance, InstanceMemory *mem);
73
- ~CallData();
53
+ LocalArray<int16_t, 16> used_trampolines;
54
+ LocalArray<OutArgument, MaxParameters> out_arguments;
74
55
 
75
- void Dispose();
56
+ #if defined(K_DEBUG)
57
+ bool finalized = false;
58
+ #endif
76
59
 
77
- #if defined(UNITY_BUILD)
78
- #if defined(_MSC_VER)
79
- #define INLINE_IF_UNITY __forceinline
80
- #else
81
- #define INLINE_IF_UNITY __attribute__((always_inline)) inline
82
- #endif
83
- #else
84
- #define INLINE_IF_UNITY
60
+ CallData(napi_env env, InstanceData *instance, InstanceMemory *mem, void *native)
61
+ : env(env), instance(instance), mem(mem), native(native),
62
+ prev_stack(mem->stack.end), prev_heap(mem->heap.ptr) {}
63
+ #if defined(K_DEBUG)
64
+ ~CallData();
85
65
  #endif
86
66
 
87
- INLINE_IF_UNITY bool Prepare(const FunctionInfo *func, const Napi::CallbackInfo &info);
88
- INLINE_IF_UNITY void Execute(const FunctionInfo *func, void *native);
89
- INLINE_IF_UNITY Napi::Value Complete(const FunctionInfo *func);
67
+ INLINE_UNITY napi_value Run(const FunctionInfo *func, napi_value *args);
68
+
69
+ bool PrepareAsync(const FunctionInfo *func, napi_value *args);
70
+ void ExecuteAsync();
71
+ napi_value EndAsync();
90
72
 
91
- #undef INLINE_IF_UNITY
73
+ INLINE_UNITY void Finalize();
74
+ INLINE_UNITY void FinalizeFast();
92
75
 
93
76
  void Relay(Size idx, uint8_t *sp);
94
77
  void RelayAsync(Size idx, uint8_t *sp);
95
78
 
96
- void DumpForward(const FunctionInfo *func) const;
97
-
98
- bool PushString(Napi::Value value, int directions, const char **out_str);
99
- bool PushString16(Napi::Value value, int directions, const char16_t **out_str16);
100
- bool PushString32(Napi::Value value, int directions, const char32_t **out_str32);
101
- Size PushStringValue(Napi::Value value, const char **out_str);
102
- Size PushString16Value(Napi::Value value, const char16_t **out_str16);
103
- Size PushString32Value(Napi::Value value, const char32_t **out_str32);
104
- bool PushObject(Napi::Object obj, const TypeInfo *type, uint8_t *origin);
79
+ INLINE_UNITY bool PushString(napi_value value, int directions, const char **out_str);
80
+ INLINE_UNITY bool PushString16(napi_value value, int directions, const char16_t **out_str16);
81
+ INLINE_UNITY bool PushString32(napi_value value, int directions, const char32_t **out_str32);
82
+ INLINE_UNITY Size PushStringValue(napi_value value, const char **out_str);
83
+ INLINE_UNITY Size PushString16Value(napi_value value, const char16_t **out_str16);
84
+ INLINE_UNITY Size PushString32Value(napi_value value, const char32_t **out_str32);
85
+ bool PushObject(napi_value value, const TypeInfo *type, uint8_t *origin);
105
86
  bool PushNormalArray(Napi::Array array, const TypeInfo *type, Size size, uint8_t *origin);
106
- void PushBuffer(Span<const uint8_t> buffer, const TypeInfo *type, uint8_t *origin);
107
- bool PushStringArray(Napi::Value value, const TypeInfo *type, uint8_t *origin);
108
- bool PushPointer(Napi::Value value, const TypeInfo *type, int directions, void **out_ptr);
109
- bool PushCallback(Napi::Value value, const TypeInfo *type, void **out_ptr);
110
- Size PushIndirectString(Napi::Array array, const TypeInfo *ref, uint8_t **out_ptr);
87
+ INLINE_UNITY void PushBuffer(Span<const uint8_t> buffer, const TypeInfo *type, uint8_t *origin);
88
+ bool PushStringArray(napi_value value, const TypeInfo *type, uint8_t *origin);
89
+ INLINE_UNITY bool PushPointer(napi_value value, const TypeInfo *type, int directions, void **out_ptr);
90
+ bool PushPointerSlow(napi_value value, const TypeInfo *type, int directions, void **out_ptr);
91
+ INLINE_UNITY bool PushCallback(napi_value value, const TypeInfo *type, void **out_ptr);
92
+ Size PushIndirectString(Napi::Array array, const TypeInfo *ref, void **out_ptr);
111
93
 
112
94
  void *ReserveTrampoline(const FunctionInfo *proto, Napi::Function func);
113
95
 
114
96
  template <typename T>
115
- bool AllocStack(Size size, Size align, T **out_ptr);
97
+ T *AllocStack(Size size);
116
98
  template <typename T = uint8_t>
117
- T *AllocHeap(Size size, Size align);
118
-
119
- bool CheckDynamicLength(Napi::Object obj, Size element, const char *countedby, Napi::Value value);
99
+ T *AllocHeap(Size size);
120
100
 
121
- void PopOutArguments();
101
+ bool CheckDynamicLength(napi_value obj, Size element, const char *countedby, napi_value value);
122
102
  };
123
103
 
124
104
  template <typename T>
125
- inline bool CallData::AllocStack(Size size, Size align, T **out_ptr)
105
+ inline T *CallData::AllocStack(Size size)
126
106
  {
127
- uint8_t *ptr = AlignDown(mem->stack.end() - size, align);
128
- Size delta = mem->stack.end() - ptr;
107
+ uint8_t *ptr = AlignDown(mem->stack.end, 16) - size;
129
108
 
130
109
  // Keep 512 bytes for redzone (required in some ABIs)
131
- if (mem->stack.len - 512 < delta) [[unlikely]] {
110
+ if (ptr < mem->stack.ptr + 512) [[unlikely]] {
132
111
  ThrowError<Napi::Error>(env, "FFI call is taking up too much memory");
133
- return false;
112
+ return nullptr;
134
113
  }
135
114
 
136
115
  #if defined(K_DEBUG)
137
- MemSet(ptr, 0, delta);
116
+ Size len = mem->stack.end - ptr;
117
+ MemSet(ptr, 0, len);
138
118
  #endif
139
119
 
140
- mem->stack.len -= delta;
120
+ mem->stack.end = ptr;
141
121
 
142
- *out_ptr = (T *)ptr;
143
- return true;
122
+ return (T *)ptr;
144
123
  }
145
124
 
146
125
  template <typename T>
147
- inline T *CallData::AllocHeap(Size size, Size align)
126
+ inline T *CallData::AllocHeap(Size size)
148
127
  {
149
- uint8_t *ptr = AlignUp(mem->heap.ptr, align);
150
- Size delta = size + (ptr - mem->heap.ptr);
128
+ K_ASSERT(AlignUp(mem->heap.ptr, 16) == mem->heap.ptr);
151
129
 
152
- if (size < 4096 && delta <= mem->heap.len) [[likely]] {
130
+ uint8_t *ptr = mem->heap.ptr;
131
+ uint8_t *end = AlignUp(ptr + size, 16);
132
+
133
+ if (end <= mem->heap.end) [[likely]] {
153
134
  #if defined(K_DEBUG)
154
- MemSet(mem->heap.ptr, 0, delta);
135
+ MemSet(ptr, 0, size);
155
136
  #endif
156
137
 
157
- mem->heap.ptr += delta;
158
- mem->heap.len -= delta;
138
+ mem->heap.ptr = end;
159
139
 
160
140
  return ptr;
161
141
  } else {
142
+ ptr = (uint8_t *)AllocateRaw(&mem->allocator, size + 16);
143
+ ptr = AlignUp(ptr, 16);
144
+ release_alloc |= (prev_stack == mem->stack.end);
145
+
162
146
  #if defined(K_DEBUG)
163
- int flags = (int)AllocFlag::Zero;
164
- #else
165
- int flags = 0;
147
+ MemSet(ptr, 0, size);
166
148
  #endif
167
149
 
168
- ptr = (uint8_t *)AllocateRaw(&alloc, size + align, flags);
169
- ptr = AlignUp(ptr, align);
170
-
171
150
  return ptr;
172
151
  }
173
152
  }