aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorGravatar Jarred Sumner <jarred@jarredsumner.com> 2023-08-19 18:17:16 -0700
committerGravatar GitHub <noreply@github.com> 2023-08-19 18:17:16 -0700
commit507761b4637a83d10e2f8b64ff870881bba7c14b (patch)
treecb3a2920ed18832df3c7075bd8e21b15b1184a3d /src
parent196620183fd20ca42b363c5f947af1dc979f888f (diff)
downloadbun-507761b4637a83d10e2f8b64ff870881bba7c14b.tar.gz
bun-507761b4637a83d10e2f8b64ff870881bba7c14b.tar.zst
bun-507761b4637a83d10e2f8b64ff870881bba7c14b.zip
Fix crash impacting sharp & resvg (#4221)
Co-authored-by: Jarred Sumner <709451+Jarred-Sumner@users.noreply.github.com>
Diffstat (limited to 'src')
-rw-r--r--src/bun.js/base.zig38
-rw-r--r--src/bun.js/bindings/JSBuffer.cpp2
-rw-r--r--src/bun.js/bindings/napi.cpp49
-rw-r--r--src/napi/napi.zig26
4 files changed, 53 insertions, 62 deletions
diff --git a/src/bun.js/base.zig b/src/bun.js/base.zig
index dbb208284..b08b82c40 100644
--- a/src/bun.js/base.zig
+++ b/src/bun.js/base.zig
@@ -771,44 +771,6 @@ comptime {
std.testing.refAllDecls(RefString);
}
-// TODO: remove this abstraction and make it work directly with
-pub const ExternalBuffer = struct {
- global: *JSC.JSGlobalObject,
- ctx: ?*anyopaque = null,
- function: JSC.napi.napi_finalize = null,
- allocator: std.mem.Allocator,
- buf: []u8 = &[_]u8{},
-
- pub fn create(ctx: ?*anyopaque, buf: []u8, global: *JSC.JSGlobalObject, function: JSC.napi.napi_finalize, allocator: std.mem.Allocator) !*ExternalBuffer {
- var container = try allocator.create(ExternalBuffer);
- container.* = .{
- .ctx = ctx,
- .global = global,
- .allocator = allocator,
- .function = function,
- .buf = buf,
- };
- return container;
- }
-
- pub fn toJS(this: *ExternalBuffer, ctx: *JSC.JSGlobalObject) JSC.JSValue {
- return JSC.JSValue.createBufferWithCtx(ctx, this.buf, this, ExternalBuffer_deallocator);
- }
-
- pub fn toArrayBuffer(this: *ExternalBuffer, ctx: *JSC.JSGlobalObject) JSC.JSValue {
- return JSValue.c(JSC.C.JSObjectMakeArrayBufferWithBytesNoCopy(ctx.ref(), this.buf.ptr, this.buf.len, ExternalBuffer_deallocator, this, null));
- }
-};
-pub export fn ExternalBuffer_deallocator(bytes_: *anyopaque, ctx: *anyopaque) callconv(.C) void {
- var external: *ExternalBuffer = bun.cast(*ExternalBuffer, ctx);
- if (external.function) |function| {
- function(external.global, external.ctx, bytes_);
- }
-
- const allocator = external.allocator;
- allocator.destroy(external);
-}
-
pub export fn MarkedArrayBuffer_deallocator(bytes_: *anyopaque, _: *anyopaque) void {
const mimalloc = @import("../allocators/mimalloc.zig");
// zig's memory allocator interface won't work here
diff --git a/src/bun.js/bindings/JSBuffer.cpp b/src/bun.js/bindings/JSBuffer.cpp
index 16c0e64b6..934fc9b6c 100644
--- a/src/bun.js/bindings/JSBuffer.cpp
+++ b/src/bun.js/bindings/JSBuffer.cpp
@@ -202,7 +202,7 @@ JSC::EncodedJSValue JSBuffer__bufferFromPointerAndLengthAndDeinit(JSC::JSGlobalO
auto* subclassStructure = globalObject->JSBufferSubclassStructure();
if (LIKELY(length > 0)) {
- auto buffer = ArrayBuffer::createFromBytes(ptr, length, createSharedTask<void(void*)>([=](void* p) {
+ auto buffer = ArrayBuffer::createFromBytes(ptr, length, createSharedTask<void(void*)>([ctx, bytesDeallocator](void* p) {
if (bytesDeallocator)
bytesDeallocator(p, ctx);
}));
diff --git a/src/bun.js/bindings/napi.cpp b/src/bun.js/bindings/napi.cpp
index 237f3d554..393c133e1 100644
--- a/src/bun.js/bindings/napi.cpp
+++ b/src/bun.js/bindings/napi.cpp
@@ -1551,6 +1551,55 @@ extern "C" napi_status napi_get_property_names(napi_env env, napi_value object,
return napi_ok;
}
+extern "C" napi_status napi_create_external_buffer(napi_env env, size_t length,
+ void* data,
+ napi_finalize finalize_cb,
+ void* finalize_hint,
+ napi_value* result)
+{
+ if (UNLIKELY(result == nullptr)) {
+ return napi_invalid_arg;
+ }
+
+ Zig::GlobalObject* globalObject = toJS(env);
+ JSC::VM& vm = globalObject->vm();
+
+ auto arrayBuffer = ArrayBuffer::createFromBytes(data, length, createSharedTask<void(void*)>([globalObject, finalize_hint, finalize_cb](void* p) {
+ if (finalize_cb != nullptr) {
+ finalize_cb(toNapi(globalObject), p, finalize_hint);
+ }
+ }));
+ auto* subclassStructure = globalObject->JSBufferSubclassStructure();
+
+ auto* buffer = JSC::JSUint8Array::create(globalObject, subclassStructure, WTFMove(arrayBuffer), 0, length);
+
+ *result = toNapi(buffer);
+ return napi_ok;
+}
+
+extern "C" napi_status napi_create_external_arraybuffer(napi_env env, void* external_data, size_t byte_length,
+ napi_finalize finalize_cb, void* finalize_hint, napi_value* result)
+{
+ if (UNLIKELY(result == nullptr)) {
+ return napi_invalid_arg;
+ }
+
+ Zig::GlobalObject* globalObject = toJS(env);
+ JSC::VM& vm = globalObject->vm();
+
+ auto arrayBuffer = ArrayBuffer::createFromBytes(external_data, byte_length, createSharedTask<void(void*)>([globalObject, finalize_hint, finalize_cb](void* p) {
+ if (finalize_cb != nullptr) {
+ finalize_cb(toNapi(globalObject), p, finalize_hint);
+ }
+ }));
+
+ auto* buffer = JSC::JSArrayBuffer::create(vm, globalObject->arrayBufferStructure(ArrayBufferSharingMode::Shared), WTFMove(arrayBuffer));
+
+ *result = toNapi(buffer);
+
+ return napi_ok;
+}
+
extern "C" napi_status napi_get_value_string_utf8(napi_env env,
napi_value napiValue, char* buf,
size_t bufsize,
diff --git a/src/napi/napi.zig b/src/napi/napi.zig
index 9d361a14e..ac428028b 100644
--- a/src/napi/napi.zig
+++ b/src/napi/napi.zig
@@ -707,20 +707,8 @@ pub export fn napi_create_arraybuffer(env: napi_env, byte_length: usize, data: [
return .ok;
}
-pub export fn napi_create_external_arraybuffer(env: napi_env, external_data: ?*anyopaque, byte_length: usize, finalize_cb: napi_finalize, finalize_hint: ?*anyopaque, result: *napi_value) napi_status {
- log("napi_create_external_arraybuffer", .{});
- var external = JSC.ExternalBuffer.create(
- finalize_hint,
- @as([*]u8, @ptrCast(external_data.?))[0..byte_length],
- env,
- finalize_cb,
- env.bunVM().allocator,
- ) catch {
- return genericFailure();
- };
- result.* = external.toArrayBuffer(env);
- return .ok;
-}
+pub extern fn napi_create_external_arraybuffer(env: napi_env, external_data: ?*anyopaque, byte_length: usize, finalize_cb: napi_finalize, finalize_hint: ?*anyopaque, result: *napi_value) napi_status;
+
pub export fn napi_get_arraybuffer_info(env: napi_env, arraybuffer: napi_value, data: ?*[*]u8, byte_length: ?*usize) napi_status {
log("napi_get_arraybuffer_info", .{});
const array_buffer = arraybuffer.asArrayBuffer(env) orelse return .arraybuffer_expected;
@@ -1072,15 +1060,7 @@ pub export fn napi_create_buffer(env: napi_env, length: usize, data: ?**anyopaqu
result.* = buffer;
return .ok;
}
-pub export fn napi_create_external_buffer(env: napi_env, length: usize, data: ?*anyopaque, finalize_cb: napi_finalize, finalize_hint: ?*anyopaque, result: *napi_value) napi_status {
- log("napi_create_external_buffer: {d}", .{length});
- var buf = JSC.ExternalBuffer.create(finalize_hint, @as([*]u8, @ptrCast(data.?))[0..length], env, finalize_cb, bun.default_allocator) catch {
- return genericFailure();
- };
-
- result.* = buf.toJS(env);
- return .ok;
-}
+pub extern fn napi_create_external_buffer(env: napi_env, length: usize, data: ?*anyopaque, finalize_cb: napi_finalize, finalize_hint: ?*anyopaque, result: *napi_value) napi_status;
pub export fn napi_create_buffer_copy(env: napi_env, length: usize, data: [*]u8, result_data: ?*?*anyopaque, result: *napi_value) napi_status {
log("napi_create_buffer_copy: {d}", .{length});
var buffer = JSC.JSValue.createBufferFromLength(env, length);