diff --git a/examples/spec/async_iterators.js b/examples/spec/async_iterators.js index 10be8dc..035c7f0 100644 --- a/examples/spec/async_iterators.js +++ b/examples/spec/async_iterators.js @@ -44,6 +44,11 @@ const dynamicAsyncIter = dynamicAsyncGen(); test('AsyncGeneratorFunction constructs async generator function', Object.getPrototypeOf(dynamicAsyncGen), AsyncGeneratorFunction.prototype); test('AsyncGeneratorFunction instance uses function prototype', Object.getPrototypeOf(dynamicAsyncIter), dynamicAsyncGen.prototype); test('AsyncGeneratorFunction yielded value', (await dynamicAsyncIter.next()).value, 4); +test( + 'strict async generator function expression has own prototype', + Function('"use strict"; return (async function* () {}).hasOwnProperty("prototype");')(), + true +); class CustomAsyncIterator extends AsyncIterator { constructor(values) { diff --git a/include/object.h b/include/object.h index a5b9303..067b4f0 100644 --- a/include/object.h +++ b/include/object.h @@ -71,11 +71,19 @@ typedef struct { uint32_t cap; } ant_private_table_t; +typedef struct { + void *ptr; + uint32_t tag; +} ant_native_entry_t; + typedef struct { ant_extra_slot_t *extra_slots; + ant_native_entry_t *native_entries; ant_private_table_t private_table; ant_proxy_state_t *proxy_state; + uint8_t native_count; + uint8_t native_cap; uint8_t extra_count; uint8_t flags; } ant_object_sidecar_t; @@ -101,11 +109,7 @@ typedef struct ant_object { void (*finalizer)(ant_t *, struct ant_object *); ant_value_t inobj[ANT_INOBJ_MAX_SLOTS]; - - struct { - void *ptr; - uint32_t tag; - } native; + ant_native_entry_t native; union { struct { ant_value_t *data; uint32_t len; uint32_t cap; } array; diff --git a/include/ptr.h b/include/ptr.h index efd51fb..4fbf2ca 100644 --- a/include/ptr.h +++ b/include/ptr.h @@ -4,42 +4,90 @@ #include "types.h" #include "internal.h" // IWYU pragma: keep -static inline void js_set_native_ptr(ant_value_t obj, void *ptr) { +static inline void *js_get_native(ant_value_t obj, uint32_t tag) { ant_object_t *o = js_obj_ptr(obj); - if (!o) return; - o->native.ptr = ptr; -} + + if (!o || !tag) return NULL; + if (o->native.tag == tag) return o->native.ptr; -static inline void *js_get_native_ptr(ant_value_t obj) { - ant_object_t *o = js_obj_ptr(obj); - return o ? o->native.ptr : NULL; + ant_object_sidecar_t *sidecar = ant_object_sidecar(o); + if (!sidecar) return NULL; + + for (uint8_t i = 0; i < sidecar->native_count; i++) + if (sidecar->native_entries[i].tag == tag) return sidecar->native_entries[i].ptr; + + return NULL; } -static inline void js_set_native_tag(ant_value_t obj, uint32_t tag) { +static inline void js_clear_native(ant_value_t obj, uint32_t tag) { ant_object_t *o = js_obj_ptr(obj); - if (!o) return; - o->native.tag = tag; + if (!o || !tag) return; + + ant_object_sidecar_t *sidecar = ant_object_sidecar(o); + if (o->native.tag == tag) { + if (sidecar && sidecar->native_count > 0) { + sidecar->native_count--; + o->native = sidecar->native_entries[sidecar->native_count]; + } else { + o->native.ptr = NULL; + o->native.tag = 0; + } + return; + } + + if (!sidecar) return; + for (uint8_t i = 0; i < sidecar->native_count; i++) { + if (sidecar->native_entries[i].tag != tag) continue; + sidecar->native_count--; + sidecar->native_entries[i] = sidecar->native_entries[sidecar->native_count]; + return; + } } static inline void js_set_native(ant_value_t obj, void *ptr, uint32_t tag) { ant_object_t *o = js_obj_ptr(obj); - if (!o) return; - o->native.ptr = ptr; - o->native.tag = tag; -} + if (!o || !tag) return; + + if (o->native.tag == 0 || o->native.tag == tag) { + o->native.ptr = ptr; + o->native.tag = tag; + return; + } -static inline void js_clear_native(ant_value_t obj) { - js_set_native(obj, NULL, 0); + ant_object_sidecar_t *sidecar = ant_object_ensure_sidecar(o); + if (!sidecar) return; + + for (uint8_t i = 0; i < sidecar->native_count; i++) { + if (sidecar->native_entries[i].tag != tag) continue; + sidecar->native_entries[i].ptr = ptr; + return; + } + + if (sidecar->native_count >= sidecar->native_cap) { + uint8_t next_cap = sidecar->native_cap ? (uint8_t)(sidecar->native_cap * 2) : 2; + ant_native_entry_t *next = realloc(sidecar->native_entries, next_cap * sizeof(*next)); + + if (!next) return; + sidecar->native_entries = next; + sidecar->native_cap = next_cap; + } + + sidecar->native_entries[sidecar->native_count++] = (ant_native_entry_t){ ptr, tag }; } -static inline uint32_t js_get_native_tag(ant_value_t obj) { +static inline bool js_check_native_tag(ant_value_t obj, uint32_t tag) { ant_object_t *o = js_obj_ptr(obj); - return o ? o->native.tag : 0; -} + + if (!o || !tag) return false; + if (o->native.tag == tag) return true; + ant_object_sidecar_t *sidecar = ant_object_sidecar(o); + if (!sidecar) return false; + + for (uint8_t i = 0; i < sidecar->native_count; i++) + if (sidecar->native_entries[i].tag == tag) return true; -static inline bool js_check_native_tag(ant_value_t obj, uint32_t tag) { - return js_get_native_tag(obj) == tag; + return false; } #endif diff --git a/src/ant.c b/src/ant.c index fb9030c..2e384e4 100644 --- a/src/ant.c +++ b/src/ant.c @@ -2745,7 +2745,7 @@ typedef struct { static inline ant_arguments_state_t *js_arguments_state(ant_value_t obj) { if (!js_check_native_tag(obj, ANT_ARGUMENTS_NATIVE_TAG)) return NULL; - return (ant_arguments_state_t *)js_get_native_ptr(obj); + return (ant_arguments_state_t *)js_get_native(obj, ANT_ARGUMENTS_NATIVE_TAG); } static ant_value_t js_arguments_getter(ant_t *js, ant_value_t obj, const char *key, size_t key_len) { @@ -2801,10 +2801,9 @@ static bool js_arguments_deleter(ant_t *js, ant_value_t obj, const char *key, si } static void js_arguments_finalizer(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != ANT_ARGUMENTS_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, ANT_ARGUMENTS_NATIVE_TAG)); + js_clear_native(value, ANT_ARGUMENTS_NATIVE_TAG); } ant_value_t js_create_arguments_object( @@ -2849,8 +2848,7 @@ ant_value_t js_create_arguments_object( state->frame_index = (int)(frame - js->vm->frames); state->mapped_count = (uint32_t)mapped_count; - js_set_native_ptr(arr, state); - js_set_native_tag(arr, ANT_ARGUMENTS_NATIVE_TAG); + js_set_native(arr, state, ANT_ARGUMENTS_NATIVE_TAG); js_set_finalizer(arr, js_arguments_finalizer); js_set_getter(arr, js_arguments_getter); js_set_setter(arr, js_arguments_setter); diff --git a/src/gc/objects.c b/src/gc/objects.c index 3801ee0..5200295 100644 --- a/src/gc/objects.c +++ b/src/gc/objects.c @@ -1,15 +1,18 @@ +#include "ptr.h" +#include "sugar.h" +#include "shapes.h" +#include "runtime.h" #include "internal.h" + +#include "silver/engine.h" +#include "modules/regex.h" +#include "modules/generator.h" +#include "modules/collections.h" + #include "gc.h" #include "gc/objects.h" #include "gc/roots.h" #include "gc/modules.h" -#include "sugar.h" -#include "silver/engine.h" -#include "shapes.h" -#include "runtime.h" -#include "modules/collections.h" -#include "modules/generator.h" -#include "modules/regex.h" #include #include @@ -245,8 +248,8 @@ static void gc_scan_obj(ant_t *js, ant_object_t *obj) { } if (obj->type_tag == T_MAP) { - map_entry_t **head = obj->native.tag == MAP_NATIVE_TAG - ? (map_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + map_entry_t **head = (map_entry_t **)js_get_native(value, MAP_NATIVE_TAG); if (head) { map_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { @@ -256,8 +259,8 @@ static void gc_scan_obj(ant_t *js, ant_object_t *obj) { } else if (obj->type_tag == T_WEAKMAP) { - weakmap_entry_t **head = obj->native.tag == WEAKMAP_NATIVE_TAG - ? (weakmap_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + weakmap_entry_t **head = (weakmap_entry_t **)js_get_native(value, WEAKMAP_NATIVE_TAG); if (head) { weakmap_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { @@ -267,8 +270,8 @@ static void gc_scan_obj(ant_t *js, ant_object_t *obj) { } else if (obj->type_tag == T_SET) { - set_entry_t **head = obj->native.tag == SET_NATIVE_TAG - ? (set_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + set_entry_t **head = (set_entry_t **)js_get_native(value, SET_NATIVE_TAG); if (head) { set_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { gc_mark_value(js, e->value); } @@ -568,20 +571,6 @@ void gc_object_free(ant_t *js, ant_object_t *obj) { obj->shape = NULL; } - if (ant_object_has_sidecar(obj)) { - ant_object_sidecar_t *sidecar = ant_object_sidecar(obj); - free(sidecar->extra_slots); - free(sidecar->proxy_state); - free(sidecar->private_table.entries); - free(sidecar); - obj->extra_slots = NULL; - } - - else if (obj->extra_slots) { - free(obj->extra_slots); - obj->extra_slots = NULL; - } - if (obj->promise_state && obj->promise_state->gc_pending_rooted) gc_unroot_pending_promise(obj); @@ -599,44 +588,67 @@ void gc_object_free(ant_t *js, ant_object_t *obj) { switch (obj->type_tag) { case T_MAP: { - map_entry_t **head = obj->native.tag == MAP_NATIVE_TAG ? (map_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + map_entry_t **head = (map_entry_t **)js_get_native(value, MAP_NATIVE_TAG); if (head) { map_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { HASH_DEL(*head, e); free(e->key); free(e); } free(head); + js_clear_native(value, MAP_NATIVE_TAG); } break; } case T_SET: { - set_entry_t **head = obj->native.tag == SET_NATIVE_TAG ? (set_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + set_entry_t **head = (set_entry_t **)js_get_native(value, SET_NATIVE_TAG); if (head) { set_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { HASH_DEL(*head, e); free(e->key); free(e); } free(head); + js_clear_native(value, SET_NATIVE_TAG); } break; } case T_WEAKMAP: { - weakmap_entry_t **head = obj->native.tag == WEAKMAP_NATIVE_TAG ? (weakmap_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + weakmap_entry_t **head = (weakmap_entry_t **)js_get_native(value, WEAKMAP_NATIVE_TAG); if (head) { weakmap_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { HASH_DEL(*head, e); free(e); } free(head); + js_clear_native(value, WEAKMAP_NATIVE_TAG); } break; } case T_WEAKSET: { - weakset_entry_t **head = obj->native.tag == WEAKSET_NATIVE_TAG ? (weakset_entry_t **)obj->native.ptr : NULL; + ant_value_t value = js_obj_from_ptr(obj); + weakset_entry_t **head = (weakset_entry_t **)js_get_native(value, WEAKSET_NATIVE_TAG); if (head) { weakset_entry_t *e, *tmp; HASH_ITER(hh, *head, e, tmp) { HASH_DEL(*head, e); free(e); } free(head); + js_clear_native(value, WEAKSET_NATIVE_TAG); } break; } default: break; } + if (ant_object_has_sidecar(obj)) { + ant_object_sidecar_t *sidecar = ant_object_sidecar(obj); + free(sidecar->extra_slots); + free(sidecar->native_entries); + free(sidecar->proxy_state); + free(sidecar->private_table.entries); + free(sidecar); + obj->extra_slots = NULL; + } + + else if (obj->extra_slots) { + free(obj->extra_slots); + obj->extra_slots = NULL; + } + free(obj->overflow_prop); obj->overflow_prop = NULL; free((void *)obj->exotic_ops); diff --git a/src/modules/abort.c b/src/modules/abort.c index 7fedcee..8795fd6 100644 --- a/src/modules/abort.c +++ b/src/modules/abort.c @@ -53,7 +53,7 @@ static inline unsigned int abort_array_len(UT_array *arr) { static abort_signal_data_t *get_signal_data(ant_value_t obj) { if (!js_check_native_tag(obj, ABORT_SIGNAL_NATIVE_TAG)) return NULL; - return (abort_signal_data_t *)js_get_native_ptr(obj); + return (abort_signal_data_t *)js_get_native(obj, ABORT_SIGNAL_NATIVE_TAG); } static abort_signal_data_t *get_signal_data_if_signal_object(ant_value_t obj) { diff --git a/src/modules/blob.c b/src/modules/blob.c index 7cccb58..d914a57 100644 --- a/src/modules/blob.c +++ b/src/modules/blob.c @@ -30,7 +30,7 @@ bool blob_is_blob(ant_t *js, ant_value_t obj) { blob_data_t *blob_get_data(ant_value_t obj) { if (!js_check_native_tag(obj, BLOB_NATIVE_TAG)) return NULL; - return (blob_data_t *)js_get_native_ptr(obj); + return (blob_data_t *)js_get_native(obj, BLOB_NATIVE_TAG); } static blob_data_t *blob_data_new(const uint8_t *data, size_t size, const char *type) { @@ -152,11 +152,10 @@ static ant_value_t process_blob_parts(ant_t *js, byte_buf_t *buf, ant_value_t pa } static void blob_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != BLOB_NATIVE_TAG) return; - blob_data_t *bd = (blob_data_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + blob_data_t *bd = (blob_data_t *)js_get_native(value, BLOB_NATIVE_TAG); if (bd) { free(bd->data); free(bd->type); free(bd->name); free(bd); } - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, BLOB_NATIVE_TAG); } ant_value_t blob_create(ant_t *js, const uint8_t *data, size_t size, const char *type) { diff --git a/src/modules/buffer.c b/src/modules/buffer.c index 1a42e7e..3967105 100644 --- a/src/modules/buffer.c +++ b/src/modules/buffer.c @@ -57,7 +57,7 @@ static void ta_meta_free(void *ptr, size_t size) { ArrayBufferData *buffer_get_arraybuffer_data(ant_value_t value) { if (!is_object_type(value) || buffer_is_dataview(value)) return NULL; if (js_check_native_tag(value, BUFFER_ARRAYBUFFER_NATIVE_TAG)) - return (ArrayBufferData *)js_get_native_ptr(value); + return (ArrayBufferData *)js_get_native(value, BUFFER_ARRAYBUFFER_NATIVE_TAG); return NULL; } @@ -66,32 +66,30 @@ TypedArrayData *buffer_get_typedarray_data(ant_value_t value) { return (TypedArrayData *)js_gettypedarray(value); if (!is_object_type(value)) return NULL; if (js_check_native_tag(value, BUFFER_TYPEDARRAY_NATIVE_TAG)) - return (TypedArrayData *)js_get_native_ptr(value); + return (TypedArrayData *)js_get_native(value, BUFFER_TYPEDARRAY_NATIVE_TAG); return NULL; } DataViewData *buffer_get_dataview_data(ant_value_t value) { if (!is_object_type(value)) return NULL; if (js_check_native_tag(value, BUFFER_DATAVIEW_NATIVE_TAG)) - return (DataViewData *)js_get_native_ptr(value); + return (DataViewData *)js_get_native(value, BUFFER_DATAVIEW_NATIVE_TAG); return NULL; } static void arraybuffer_finalize(ant_t *js, ant_object_t *obj) { ant_value_t value = js_obj_from_ptr(obj); if (!js_check_native_tag(value, BUFFER_ARRAYBUFFER_NATIVE_TAG)) return; - ArrayBufferData *data = (ArrayBufferData *)js_get_native_ptr(value); - js_set_native_ptr(value, NULL); - js_set_native_tag(value, 0); + ArrayBufferData *data = (ArrayBufferData *)js_get_native(value, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_clear_native(value, BUFFER_ARRAYBUFFER_NATIVE_TAG); if (data) free_array_buffer_data(data); } static void typedarray_finalize(ant_t *js, ant_object_t *obj) { ant_value_t value = js_obj_from_ptr(obj); if (!js_check_native_tag(value, BUFFER_TYPEDARRAY_NATIVE_TAG)) return; - TypedArrayData *ta_data = (TypedArrayData *)js_get_native_ptr(value); - js_set_native_ptr(value, NULL); - js_set_native_tag(value, 0); + TypedArrayData *ta_data = (TypedArrayData *)js_get_native(value, BUFFER_TYPEDARRAY_NATIVE_TAG); + js_clear_native(value, BUFFER_TYPEDARRAY_NATIVE_TAG); if (!ta_data) return; if (ta_data->buffer) free_array_buffer_data(ta_data->buffer); @@ -101,9 +99,8 @@ static void typedarray_finalize(ant_t *js, ant_object_t *obj) { static void dataview_finalize(ant_t *js, ant_object_t *obj) { ant_value_t value = js_obj_from_ptr(obj); if (!js_check_native_tag(value, BUFFER_DATAVIEW_NATIVE_TAG)) return; - DataViewData *dv_data = (DataViewData *)js_get_native_ptr(value); - js_set_native_ptr(value, NULL); - js_set_native_tag(value, 0); + DataViewData *dv_data = (DataViewData *)js_get_native(value, BUFFER_DATAVIEW_NATIVE_TAG); + js_clear_native(value, BUFFER_DATAVIEW_NATIVE_TAG); if (!dv_data) return; if (dv_data->buffer) free_array_buffer_data(dv_data->buffer); @@ -386,8 +383,7 @@ static ant_value_t js_arraybuffer_constructor(ant_t *js, ant_value_t *args, int ant_value_t proto = js_get_ctor_proto(js, "ArrayBuffer", 11); if (is_special_object(proto)) js_set_proto_init(obj, proto); - js_set_native_ptr(obj, data); - js_set_native_tag(obj, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_set_native(obj, data, BUFFER_ARRAYBUFFER_NATIVE_TAG); js_set(js, obj, "byteLength", js_mknum((double)length)); js_set_finalizer(obj, arraybuffer_finalize); @@ -420,8 +416,7 @@ static ant_value_t js_arraybuffer_slice(ant_t *js, ant_value_t *args, int nargs) ant_value_t proto = js_get_ctor_proto(js, "ArrayBuffer", 11); if (is_special_object(proto)) js_set_proto_init(new_obj, proto); - js_set_native_ptr(new_obj, new_data); - js_set_native_tag(new_obj, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_set_native(new_obj, new_data, BUFFER_ARRAYBUFFER_NATIVE_TAG); js_set(js, new_obj, "byteLength", js_mknum((double)new_length)); js_set_finalizer(new_obj, arraybuffer_finalize); @@ -461,8 +456,7 @@ static ant_value_t js_arraybuffer_transfer(ant_t *js, ant_value_t *args, int nar ant_value_t proto = js_get_ctor_proto(js, "ArrayBuffer", 11); if (is_special_object(proto)) js_set_proto_init(new_obj, proto); - js_set_native_ptr(new_obj, new_data); - js_set_native_tag(new_obj, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_set_native(new_obj, new_data, BUFFER_ARRAYBUFFER_NATIVE_TAG); js_set(js, new_obj, "byteLength", js_mknum((double)new_length)); js_set_finalizer(new_obj, arraybuffer_finalize); @@ -663,8 +657,7 @@ ant_value_t create_arraybuffer_obj(ant_t *js, ArrayBufferData *buffer) { ant_value_t ab_proto = js_get_ctor_proto(js, "ArrayBuffer", 11); if (is_special_object(ab_proto)) js_set_proto_init(ab_obj, ab_proto); - js_set_native_ptr(ab_obj, buffer); - js_set_native_tag(ab_obj, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_set_native(ab_obj, buffer, BUFFER_ARRAYBUFFER_NATIVE_TAG); js_set(js, ab_obj, "byteLength", js_mknum((double)buffer->length)); js_set_finalizer(ab_obj, arraybuffer_finalize); buffer->ref_count++; @@ -691,8 +684,7 @@ ant_value_t create_typed_array_with_buffer( ant_value_t proto = js_get_ctor_proto(js, type_name, strlen(type_name)); if (is_special_object(proto)) js_set_proto_init(obj, proto); - js_set_native_ptr(obj, ta_data); - js_set_native_tag(obj, BUFFER_TYPEDARRAY_NATIVE_TAG); + js_set_native(obj, ta_data, BUFFER_TYPEDARRAY_NATIVE_TAG); js_set(js, obj, "length", js_mknum((double)length)); js_set(js, obj, "byteLength", js_mknum((double)(length * element_size))); js_set(js, obj, "byteOffset", js_mknum((double)byte_offset)); @@ -732,8 +724,7 @@ ant_value_t create_dataview_with_buffer( ant_value_t proto = js_get_ctor_proto(js, "DataView", 8); if (is_special_object(proto)) js_set_proto_init(obj, proto); - js_set_native_ptr(obj, dv_data); - js_set_native_tag(obj, BUFFER_DATAVIEW_NATIVE_TAG); + js_set_native(obj, dv_data, BUFFER_DATAVIEW_NATIVE_TAG); js_set_slot(obj, SLOT_BRAND, js_mknum(BRAND_DATAVIEW)); js_mkprop_fast(js, obj, "buffer", 6, arraybuffer_obj); js_set_descriptor(js, obj, "buffer", 6, 0); @@ -1435,8 +1426,7 @@ static ant_value_t js_dataview_constructor(ant_t *js, ant_value_t *args, int nar ant_value_t proto = js_get_ctor_proto(js, "DataView", 8); if (is_special_object(proto)) js_set_proto_init(obj, proto); - js_set_native_ptr(obj, dv_data); - js_set_native_tag(obj, BUFFER_DATAVIEW_NATIVE_TAG); + js_set_native(obj, dv_data, BUFFER_DATAVIEW_NATIVE_TAG); js_set_slot(obj, SLOT_BRAND, js_mknum(BRAND_DATAVIEW)); js_mkprop_fast(js, obj, "buffer", 6, args[0]); js_set_descriptor(js, obj, "buffer", 6, 0); @@ -2880,8 +2870,7 @@ static ant_value_t js_sharedarraybuffer_constructor(ant_t *js, ant_value_t *args ant_value_t proto = js_get_ctor_proto(js, "SharedArrayBuffer", 17); if (is_special_object(proto)) js_set_proto_init(obj, proto); - js_set_native_ptr(obj, data); - js_set_native_tag(obj, BUFFER_ARRAYBUFFER_NATIVE_TAG); + js_set_native(obj, data, BUFFER_ARRAYBUFFER_NATIVE_TAG); js_set(js, obj, "byteLength", js_mknum((double)length)); js_set_finalizer(obj, arraybuffer_finalize); diff --git a/src/modules/child_process.c b/src/modules/child_process.c index 155bdf7..6f17b27 100644 --- a/src/modules/child_process.c +++ b/src/modules/child_process.c @@ -117,12 +117,12 @@ enum { static child_process_t *get_child_process(ant_value_t obj) { if (!js_check_native_tag(obj, CHILD_PROCESS_NATIVE_TAG)) return NULL; - return (child_process_t *)js_get_native_ptr(obj); + return (child_process_t *)js_get_native(obj, CHILD_PROCESS_NATIVE_TAG); } static child_stream_ctx_t *get_child_stream_ctx(ant_value_t obj) { if (!js_check_native_tag(obj, CHILD_STREAM_NATIVE_TAG)) return NULL; - return (child_stream_ctx_t *)js_get_native_ptr(obj); + return (child_stream_ctx_t *)js_get_native(obj, CHILD_STREAM_NATIVE_TAG); } static child_process_t *pending_children_tail = NULL; diff --git a/src/modules/collections.c b/src/modules/collections.c index 37296da..1e1005f 100644 --- a/src/modules/collections.c +++ b/src/modules/collections.c @@ -310,38 +310,38 @@ map_entry_t **get_map_from_obj(ant_value_t obj) { ant_object_t *ptr = js_obj_ptr(obj); if (!ptr || ptr->type_tag != T_MAP) return NULL; if (!js_check_native_tag(obj, MAP_NATIVE_TAG)) return NULL; - return (map_entry_t **)js_get_native_ptr(obj); + return (map_entry_t **)js_get_native(obj, MAP_NATIVE_TAG); } set_entry_t **get_set_from_obj(ant_value_t obj) { ant_object_t *ptr = js_obj_ptr(obj); if (!ptr || ptr->type_tag != T_SET) return NULL; if (!js_check_native_tag(obj, SET_NATIVE_TAG)) return NULL; - return (set_entry_t **)js_get_native_ptr(obj); + return (set_entry_t **)js_get_native(obj, SET_NATIVE_TAG); } static weakmap_entry_t **get_weakmap_from_obj(ant_value_t obj) { ant_object_t *ptr = js_obj_ptr(obj); if (!ptr || ptr->type_tag != T_WEAKMAP) return NULL; if (!js_check_native_tag(obj, WEAKMAP_NATIVE_TAG)) return NULL; - return (weakmap_entry_t **)js_get_native_ptr(obj); + return (weakmap_entry_t **)js_get_native(obj, WEAKMAP_NATIVE_TAG); } static weakset_entry_t **get_weakset_from_obj(ant_value_t obj) { ant_object_t *ptr = js_obj_ptr(obj); if (!ptr || ptr->type_tag != T_WEAKSET) return NULL; if (!js_check_native_tag(obj, WEAKSET_NATIVE_TAG)) return NULL; - return (weakset_entry_t **)js_get_native_ptr(obj); + return (weakset_entry_t **)js_get_native(obj, WEAKSET_NATIVE_TAG); } map_iterator_state_t *get_map_iter_state(ant_value_t obj) { if (!js_check_native_tag(obj, MAP_ITER_NATIVE_TAG)) return NULL; - return (map_iterator_state_t *)js_get_native_ptr(obj); + return (map_iterator_state_t *)js_get_native(obj, MAP_ITER_NATIVE_TAG); } set_iterator_state_t *get_set_iter_state(ant_value_t obj) { if (!js_check_native_tag(obj, SET_ITER_NATIVE_TAG)) return NULL; - return (set_iterator_state_t *)js_get_native_ptr(obj); + return (set_iterator_state_t *)js_get_native(obj, SET_ITER_NATIVE_TAG); } static ant_value_t map_set(ant_t *js, ant_value_t *args, int nargs) { diff --git a/src/modules/crypto.c b/src/modules/crypto.c index 62553ab..b05e0f9 100644 --- a/src/modules/crypto.c +++ b/src/modules/crypto.c @@ -223,7 +223,7 @@ static ant_value_t crypto_get_input_bytes( static ant_hash_state_t *crypto_get_hash_state(ant_value_t value) { if (!js_check_native_tag(value, CRYPTO_HASH_NATIVE_TAG)) return NULL; - ant_hash_state_t *state = (ant_hash_state_t *)js_get_native_ptr(value); + ant_hash_state_t *state = (ant_hash_state_t *)js_get_native(value, CRYPTO_HASH_NATIVE_TAG); return (state && state->ctx) ? state : NULL; } diff --git a/src/modules/events.c b/src/modules/events.c index 9a61bfc..842f8b3 100644 --- a/src/modules/events.c +++ b/src/modules/events.c @@ -42,7 +42,7 @@ enum { static event_data_t *get_event_data(ant_value_t obj) { if (!js_check_native_tag(obj, EVENT_NATIVE_TAG)) return NULL; - return (event_data_t *)js_get_native_ptr(obj); + return (event_data_t *)js_get_native(obj, EVENT_NATIVE_TAG); } static double get_timestamp_ms(void) { @@ -169,7 +169,7 @@ static EventType **get_or_create_emitter_events(ant_t *js, ant_value_t this_obj) js_set_native(this_obj, events, EVENT_EMITTER_NATIVE_TAG); return events; } - return (EventType **)js_get_native_ptr(this_obj); + return (EventType **)js_get_native(this_obj, EVENT_EMITTER_NATIVE_TAG); } static EventType *find_or_create_global_event_type(ant_t *js, ant_value_t js_key) { diff --git a/src/modules/fetch.c b/src/modules/fetch.c index df0c987..b97fea6 100644 --- a/src/modules/fetch.c +++ b/src/modules/fetch.c @@ -658,7 +658,7 @@ static bool fetch_handle_data_url(fetch_request_t *req) { static ant_value_t fetch_upload_on_reject(ant_t *js, ant_value_t *args, int nargs) { fetch_request_t *req = js_check_native_tag(js->current_func, FETCH_REQUEST_NATIVE_TAG) - ? (fetch_request_t *)js_get_native_ptr(js->current_func) + ? (fetch_request_t *)js_get_native(js->current_func, FETCH_REQUEST_NATIVE_TAG) : NULL; ant_value_t reason = (nargs > 0) ? args[0] : js_mkundef(); @@ -678,7 +678,7 @@ static ant_value_t fetch_upload_on_reject(ant_t *js, ant_value_t *args, int narg static void fetch_upload_schedule_next_read(fetch_request_t *req); static ant_value_t fetch_upload_on_read(ant_t *js, ant_value_t *args, int nargs) { fetch_request_t *req = js_check_native_tag(js->current_func, FETCH_REQUEST_NATIVE_TAG) - ? (fetch_request_t *)js_get_native_ptr(js->current_func) + ? (fetch_request_t *)js_get_native(js->current_func, FETCH_REQUEST_NATIVE_TAG) : NULL; ant_value_t result = (nargs > 0) ? args[0] : js_mkundef(); @@ -839,7 +839,7 @@ static void fetch_start_http(fetch_request_t *req) { static ant_value_t fetch_abort_listener(ant_t *js, ant_value_t *args, int nargs) { fetch_request_t *req = js_check_native_tag(js->current_func, FETCH_REQUEST_NATIVE_TAG) - ? (fetch_request_t *)js_get_native_ptr(js->current_func) + ? (fetch_request_t *)js_get_native(js->current_func, FETCH_REQUEST_NATIVE_TAG) : NULL; ant_value_t signal = 0; ant_value_t reason = 0; diff --git a/src/modules/ffi.c b/src/modules/ffi.c index a3e23d0..8d91448 100644 --- a/src/modules/ffi.c +++ b/src/modules/ffi.c @@ -347,22 +347,22 @@ static ffi_marshaled_type_t ffi_infer_variadic_type(ant_value_t value) { static ffi_library_handle_t *ffi_library_data(ant_value_t value) { if (!js_check_native_tag(value, FFI_LIBRARY_NATIVE_TAG)) return NULL; - return (ffi_library_handle_t *)js_get_native_ptr(value); + return (ffi_library_handle_t *)js_get_native(value, FFI_LIBRARY_NATIVE_TAG); } static ffi_function_handle_t *ffi_function_data(ant_value_t value) { if (!js_check_native_tag(value, FFI_FUNCTION_NATIVE_TAG)) return NULL; - return (ffi_function_handle_t *)js_get_native_ptr(value); + return (ffi_function_handle_t *)js_get_native(value, FFI_FUNCTION_NATIVE_TAG); } static ffi_pointer_handle_t *ffi_pointer_data(ant_value_t value) { if (!js_check_native_tag(value, FFI_POINTER_NATIVE_TAG)) return NULL; - return (ffi_pointer_handle_t *)js_get_native_ptr(value); + return (ffi_pointer_handle_t *)js_get_native(value, FFI_POINTER_NATIVE_TAG); } static ffi_callback_handle_t *ffi_callback_data(ant_value_t value) { if (!js_check_native_tag(value, FFI_CALLBACK_NATIVE_TAG)) return NULL; - return (ffi_callback_handle_t *)js_get_native_ptr(value); + return (ffi_callback_handle_t *)js_get_native(value, FFI_CALLBACK_NATIVE_TAG); } static void ffi_library_close_handle(ffi_library_handle_t *library) { @@ -470,8 +470,7 @@ static ant_value_t ffi_make_pointer(ant_t *js, ffi_pointer_region_t *region, siz if (region) region->ref_count++; if (g_ffi_pointer_proto) js_set_proto_init(obj, g_ffi_pointer_proto); - js_set_native_ptr(obj, handle); - js_set_native_tag(obj, FFI_POINTER_NATIVE_TAG); + js_set_native(obj, handle, FFI_POINTER_NATIVE_TAG); js_set_finalizer(obj, ffi_pointer_finalize); return obj; @@ -773,8 +772,7 @@ static ant_value_t ffi_make_function(ant_t *js, ffi_library_handle_t *library, c if (g_ffi_function_proto) js_set_proto_init(obj, g_ffi_function_proto); js_set_slot(obj, SLOT_CFUNC, js_mkfun(ffi_function_call)); - js_set_native_ptr(obj, handle); - js_set_native_tag(obj, FFI_FUNCTION_NATIVE_TAG); + js_set_native(obj, handle, FFI_FUNCTION_NATIVE_TAG); js_set_slot_wb(js, obj, SLOT_ENTRIES, library ? library->obj : js_mkundef()); js_set_finalizer(obj, ffi_function_finalize); @@ -784,56 +782,52 @@ static ant_value_t ffi_make_function(ant_t *js, ffi_library_handle_t *library, c void ffi_library_finalize(ant_t *js, ant_object_t *obj) { ffi_library_handle_t *library; - if (obj->native.tag != FFI_LIBRARY_NATIVE_TAG) return; + ant_value_t value = js_obj_from_ptr(obj); - library = (ffi_library_handle_t *)obj->native.ptr; + library = (ffi_library_handle_t *)js_get_native(value, FFI_LIBRARY_NATIVE_TAG); if (!library) return; ffi_library_close_handle(library); free(library->path); free(library); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, FFI_LIBRARY_NATIVE_TAG); } void ffi_function_finalize(ant_t *js, ant_object_t *obj) { ffi_function_handle_t *handle; - if (obj->native.tag != FFI_FUNCTION_NATIVE_TAG) return; + ant_value_t value = js_obj_from_ptr(obj); - handle = (ffi_function_handle_t *)obj->native.ptr; + handle = (ffi_function_handle_t *)js_get_native(value, FFI_FUNCTION_NATIVE_TAG); if (!handle) return; free(handle->symbol_name); ffi_signature_cleanup(&handle->signature); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, FFI_FUNCTION_NATIVE_TAG); } void ffi_pointer_finalize(ant_t *js, ant_object_t *obj) { ffi_pointer_handle_t *handle; - if (obj->native.tag != FFI_POINTER_NATIVE_TAG) return; + ant_value_t value = js_obj_from_ptr(obj); - handle = (ffi_pointer_handle_t *)obj->native.ptr; + handle = (ffi_pointer_handle_t *)js_get_native(value, FFI_POINTER_NATIVE_TAG); if (!handle) return; ffi_pointer_close_handle(handle, false); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, FFI_POINTER_NATIVE_TAG); } void ffi_callback_finalize(ant_t *js, ant_object_t *obj) { ffi_callback_handle_t *handle; - if (obj->native.tag != FFI_CALLBACK_NATIVE_TAG) return; + ant_value_t value = js_obj_from_ptr(obj); - handle = (ffi_callback_handle_t *)obj->native.ptr; + handle = (ffi_callback_handle_t *)js_get_native(value, FFI_CALLBACK_NATIVE_TAG); if (!handle) return; ffi_callback_close_handle(handle); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, FFI_CALLBACK_NATIVE_TAG); } static bool ffi_callback_result_to_c( @@ -1003,8 +997,7 @@ static ant_value_t ffi_dlopen(ant_t *js, ant_value_t *args, int nargs) { obj = js_mkobj(js); if (g_ffi_library_proto) js_set_proto_init(obj, g_ffi_library_proto); library->obj = obj; - js_set_native_ptr(obj, library); - js_set_native_tag(obj, FFI_LIBRARY_NATIVE_TAG); + js_set_native(obj, library, FFI_LIBRARY_NATIVE_TAG); js_set_finalizer(obj, ffi_library_finalize); return obj; } @@ -1402,8 +1395,7 @@ static ant_value_t ffi_create_callback(ant_t *js, ant_value_t *args, int nargs) callback->owner_obj = obj; callback->owner_thread = pthread_self(); callback->closed = false; - js_set_native_ptr(obj, callback); - js_set_native_tag(obj, FFI_CALLBACK_NATIVE_TAG); + js_set_native(obj, callback, FFI_CALLBACK_NATIVE_TAG); js_set_slot_wb(js, obj, SLOT_DATA, fn); js_set_finalizer(obj, ffi_callback_finalize); return obj; diff --git a/src/modules/formdata.c b/src/modules/formdata.c index 1048192..45eb575 100644 --- a/src/modules/formdata.c +++ b/src/modules/formdata.c @@ -71,7 +71,7 @@ static void fd_data_free(fd_data_t *d) { static fd_data_t *get_fd_data(ant_value_t obj) { if (!js_check_native_tag(obj, FORMDATA_NATIVE_TAG)) return NULL; - return (fd_data_t *)js_get_native_ptr(obj); + return (fd_data_t *)js_get_native(obj, FORMDATA_NATIVE_TAG); } // TODO: compact @@ -84,11 +84,10 @@ static ant_value_t get_fd_values(ant_value_t obj) { } static void formdata_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != FORMDATA_NATIVE_TAG) return; - fd_data_t *d = (fd_data_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + fd_data_t *d = (fd_data_t *)js_get_native(value, FORMDATA_NATIVE_TAG); fd_data_free(d); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, FORMDATA_NATIVE_TAG); } static bool fd_append_str(fd_data_t *d, const char *name, const char *value) { @@ -383,7 +382,7 @@ static ant_value_t formdata_iter_next(ant_t *js, ant_value_t *args, int nargs) { if (!js_check_native_tag(js->this_val, FORMDATA_ITER_NATIVE_TAG)) return js_iter_result(js, false, js_mkundef()); - fd_iter_t *st = (fd_iter_t *)js_get_native_ptr(js->this_val); + fd_iter_t *st = (fd_iter_t *)js_get_native(js->this_val, FORMDATA_ITER_NATIVE_TAG); ant_value_t fd_obj = js_get_slot(js->this_val, SLOT_DATA); fd_data_t *d = get_fd_data(fd_obj); if (!d) return js_iter_result(js, false, js_mkundef()); @@ -418,10 +417,9 @@ static ant_value_t formdata_iter_next(ant_t *js, ant_value_t *args, int nargs) { } static void formdata_iter_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != FORMDATA_ITER_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, FORMDATA_ITER_NATIVE_TAG)); + js_clear_native(value, FORMDATA_ITER_NATIVE_TAG); } static ant_value_t make_formdata_iter(ant_t *js, ant_value_t fd_obj, int kind) { diff --git a/src/modules/fs.c b/src/modules/fs.c index 8b2c758..6e7a661 100644 --- a/src/modules/fs.c +++ b/src/modules/fs.c @@ -158,7 +158,7 @@ enum { static fs_watcher_t *fs_watcher_data(ant_value_t value) { if (!js_check_native_tag(value, FS_WATCHER_NATIVE_TAG)) return NULL; - return (fs_watcher_t *)js_get_native_ptr(value); + return (fs_watcher_t *)js_get_native(value, FS_WATCHER_NATIVE_TAG); } static void fs_add_active_watcher(fs_watcher_t *watcher) { @@ -922,10 +922,10 @@ static ant_value_t js_fswatcher_ctor(ant_t *js, ant_value_t *args, int nargs) { static void fs_watcher_finalize(ant_t *js, ant_object_t *obj) { fs_watcher_t *watcher = NULL; - if (!obj) return; + ant_value_t value = js_obj_from_ptr(obj); - watcher = (fs_watcher_t *)obj->native.ptr; - obj->native.ptr = NULL; + watcher = (fs_watcher_t *)js_get_native(value, FS_WATCHER_NATIVE_TAG); + js_clear_native(value, FS_WATCHER_NATIVE_TAG); if (!watcher) return; watcher->finalized = true; @@ -1083,8 +1083,7 @@ static ant_value_t fs_watcher_make_object(ant_t *js, fs_watcher_t *watcher) { obj = js_mkobj(js); js_set_proto_init(obj, g_fswatcher_proto); - js_set_native_ptr(obj, watcher); - js_set_native_tag(obj, FS_WATCHER_NATIVE_TAG); + js_set_native(obj, watcher, FS_WATCHER_NATIVE_TAG); js_set_finalizer(obj, fs_watcher_finalize); watcher->obj = obj; @@ -1587,7 +1586,7 @@ static ant_value_t builtin_fs_filehandle_writeFile(ant_t *js, ant_value_t *args, static void fs_init_filehandle_proto(ant_t *js) { if (is_object_type(g_filehandle_proto)) return; g_filehandle_proto = js_mkobj(js); - js_set_native_tag(g_filehandle_proto, FS_FILEHANDLE_NATIVE_TAG); + js_set_native(g_filehandle_proto, NULL, FS_FILEHANDLE_NATIVE_TAG); js_set(js, g_filehandle_proto, "close", js_mkfun(builtin_fs_filehandle_close)); js_set(js, g_filehandle_proto, "stat", js_mkfun(builtin_fs_filehandle_stat)); js_set(js, g_filehandle_proto, "sync", js_mkfun(builtin_fs_filehandle_sync)); @@ -1601,7 +1600,7 @@ static ant_value_t fs_make_filehandle(ant_t *js, int fd) { fs_init_filehandle_proto(js); ant_value_t handle = js_mkobj(js); - js_set_native_tag(handle, FS_FILEHANDLE_NATIVE_TAG); + js_set_native(handle, NULL, FS_FILEHANDLE_NATIVE_TAG); js_set_proto_init(handle, g_filehandle_proto); js_set_slot(handle, SLOT_DATA, js_mknum((double)fd)); js_set(js, handle, "fd", js_mknum((double)fd)); @@ -4335,7 +4334,7 @@ static ant_value_t builtin_fs_watch(ant_t *js, ant_value_t *args, int nargs) { rc = fs_watcher_start_event(watcher, path, opts.persistent, opts.recursive); if (rc != 0) { - js_set_native_ptr(watcher_obj, NULL); + js_clear_native(watcher_obj, FS_WATCHER_NATIVE_TAG); fs_watcher_free(watcher); return fs_watch_error(js, rc, path); } diff --git a/src/modules/generator.c b/src/modules/generator.c index baaee42..c583092 100644 --- a/src/modules/generator.c +++ b/src/modules/generator.c @@ -52,7 +52,7 @@ static ant_value_t generator_result(ant_t *js, bool done, ant_value_t value) { static generator_data_t *generator_data(ant_value_t gen) { if (!js_check_native_tag(gen, GENERATOR_NATIVE_TAG)) return NULL; - return (generator_data_t *)js_get_native_ptr(gen); + return (generator_data_t *)js_get_native(gen, GENERATOR_NATIVE_TAG); } static generator_state_t generator_state(ant_value_t gen) { @@ -285,13 +285,12 @@ bool generator_resume_pending_request(ant_t *js, coroutine_t *coro, ant_value_t static void generator_finalize(ant_t *js, ant_object_t *obj) { ant_value_t gen = js_obj_from_ptr(obj); - generator_data_t *data = (generator_data_t *)js_get_native_ptr(gen); + generator_data_t *data = (generator_data_t *)js_get_native(gen, GENERATOR_NATIVE_TAG); if (!data) return; if (data->coro) generator_clear_coro(gen, data->coro); - js_set_native_ptr(gen, NULL); - js_set_native_tag(gen, 0); + js_set_native(gen, NULL, 0); generator_free_queue(data); free(data); @@ -600,8 +599,7 @@ ant_value_t sv_call_generator_closure_dispatch( coroutine_hold(coro, CORO_HOLD_GENERATOR); coroutine_release(coro); - js_set_native_ptr(gen, data); - js_set_native_tag(gen, GENERATOR_NATIVE_TAG); + js_set_native(gen, data, GENERATOR_NATIVE_TAG); js_set_finalizer(gen, generator_finalize); ant_value_t instance_proto = js_get(js, callee_func, "prototype"); diff --git a/src/modules/headers.c b/src/modules/headers.c index 70a5223..853b40a 100644 --- a/src/modules/headers.c +++ b/src/modules/headers.c @@ -71,7 +71,7 @@ static void list_free(hdr_list_t *l) { static hdr_list_t *get_list(ant_value_t obj) { if (!js_check_native_tag(obj, HEADERS_NATIVE_TAG)) return NULL; - return (hdr_list_t *)js_get_native_ptr(obj); + return (hdr_list_t *)js_get_native(obj, HEADERS_NATIVE_TAG); } static headers_guard_t get_guard(ant_value_t obj) { @@ -480,7 +480,7 @@ static ant_value_t init_from_record(ant_t *js, hdr_list_t *l, ant_value_t obj) { bool advance_headers(ant_t *js, js_iter_t *it, ant_value_t *out) { if (!js_check_native_tag(it->iterator, HEADERS_ITER_NATIVE_TAG)) return false; - hdr_iter_t *st = (hdr_iter_t *)js_get_native_ptr(it->iterator); + hdr_iter_t *st = (hdr_iter_t *)js_get_native(it->iterator, HEADERS_ITER_NATIVE_TAG); size_t count = 0; sorted_pair_t *view = build_sorted_view(st->list, &count); diff --git a/src/modules/iterator.c b/src/modules/iterator.c index 8d06d61..92c493c 100644 --- a/src/modules/iterator.c +++ b/src/modules/iterator.c @@ -884,13 +884,14 @@ static ant_value_t async_terminal_finish_callback(ant_t *js, ant_value_t state, static void async_terminal_close_and_reject(ant_t *js, ant_value_t state, ant_value_t reason); static void async_terminal_state_finalize(ant_t *js, ant_object_t *obj) { - free(obj->native.ptr); - obj->native.ptr = NULL; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, ASYNC_TERMINAL_STATE_TAG)); + js_clear_native(value, ASYNC_TERMINAL_STATE_TAG); } static inline async_terminal_state_t *async_terminal_state(ant_value_t state) { if (!js_check_native_tag(state, ASYNC_TERMINAL_STATE_TAG)) return NULL; - return (async_terminal_state_t *)js_get_native_ptr(state); + return (async_terminal_state_t *)js_get_native(state, ASYNC_TERMINAL_STATE_TAG); } static inline int async_terminal_mode(ant_value_t state) { @@ -1194,8 +1195,7 @@ static ant_value_t async_iter_terminal(ant_t *js, ant_value_t *args, int nargs, st->index = 0; st->has_acc = (mode == ASYNC_TERM_REDUCE && nargs > 1); - js_set_native_tag(state, ASYNC_TERMINAL_STATE_TAG); - js_set_native_ptr(state, st); + js_set_native(state, st, ASYNC_TERMINAL_STATE_TAG); js_set_finalizer(state, async_terminal_state_finalize); js_set_slot_wb(js, state, SLOT_DATA, iter); diff --git a/src/modules/napi.c b/src/modules/napi.c index 88d7e5a..b5a038e 100644 --- a/src/modules/napi.c +++ b/src/modules/napi.c @@ -483,7 +483,7 @@ static ant_value_t napi_callback_trampoline(ant_t *js, ant_value_t *args, int na ant_value_t current = js_getcurrentfunc(js); if (!js_check_native_tag(current, NAPI_CALLBACK_NATIVE_TAG)) return js_mkundef(); - napi_callback_binding_t *binding = (napi_callback_binding_t *)js_get_native_ptr(current); + napi_callback_binding_t *binding = (napi_callback_binding_t *)js_get_native(current, NAPI_CALLBACK_NATIVE_TAG); if (!binding || !binding->cb) return js_mkundef(); ant_napi_env_t *nenv = binding->env ? binding->env : napi_get_or_create_env(js); diff --git a/src/modules/net.c b/src/modules/net.c index 624396e..3186841 100644 --- a/src/modules/net.c +++ b/src/modules/net.c @@ -102,12 +102,12 @@ static ant_value_t net_not_implemented(ant_t *js, const char *what); static net_server_t *net_server_data(ant_value_t value) { if (!js_check_native_tag(value, NET_SERVER_NATIVE_TAG)) return NULL; - return (net_server_t *)js_get_native_ptr(value); + return (net_server_t *)js_get_native(value, NET_SERVER_NATIVE_TAG); } static net_socket_t *net_socket_data(ant_value_t value) { if (!js_check_native_tag(value, NET_SOCKET_NATIVE_TAG)) return NULL; - return (net_socket_t *)js_get_native_ptr(value); + return (net_socket_t *)js_get_native(value, NET_SOCKET_NATIVE_TAG); } static void net_add_active_server(net_server_t *server) { @@ -357,8 +357,7 @@ static void net_socket_detach(net_socket_t *socket) { net_remove_active_socket(socket); if (is_object_type(socket->obj)) { - js_set_native_ptr(socket->obj, NULL); - js_set_native_tag(socket->obj, 0); + js_set_native(socket->obj, NULL, 0); } net_server_maybe_finish_close(socket->server); free(socket); @@ -383,8 +382,7 @@ static net_socket_t *net_socket_create(ant_t *js, bool allow_half_open) { socket->encoding = js_mkundef(); socket->allow_half_open = allow_half_open; - js_set_native_ptr(obj, socket); - js_set_native_tag(obj, NET_SOCKET_NATIVE_TAG); + js_set_native(obj, socket, NET_SOCKET_NATIVE_TAG); js_set(js, obj, "remoteAddress", js_mkundef()); js_set(js, obj, "remotePort", js_mkundef()); js_set(js, obj, "remoteFamily", js_mkundef()); @@ -431,8 +429,7 @@ static net_server_t *net_server_create(ant_t *js) { return NULL; } - js_set_native_ptr(obj, server); - js_set_native_tag(obj, NET_SERVER_NATIVE_TAG); + js_set_native(obj, server, NET_SERVER_NATIVE_TAG); net_server_sync_state(server); return server; } diff --git a/src/modules/request.c b/src/modules/request.c index 4db02a5..b58d666 100644 --- a/src/modules/request.c +++ b/src/modules/request.c @@ -32,7 +32,7 @@ enum { REQUEST_NATIVE_TAG = 0x52455153u }; // REQS static request_data_t *get_data(ant_value_t obj) { if (!js_check_native_tag(obj, REQUEST_NATIVE_TAG)) return NULL; - return (request_data_t *)js_get_native_ptr(obj); + return (request_data_t *)js_get_native(obj, REQUEST_NATIVE_TAG); } request_data_t *request_get_data(ant_value_t obj) { diff --git a/src/modules/response.c b/src/modules/response.c index ec1dcbe..bd90651 100644 --- a/src/modules/response.c +++ b/src/modules/response.c @@ -32,7 +32,7 @@ enum { RESPONSE_NATIVE_TAG = 0x52455350u }; // RESP static response_data_t *get_data(ant_value_t obj) { if (!js_check_native_tag(obj, RESPONSE_NATIVE_TAG)) return NULL; - return (response_data_t *)js_get_native_ptr(obj); + return (response_data_t *)js_get_native(obj, RESPONSE_NATIVE_TAG); } response_data_t *response_get_data(ant_value_t obj) { diff --git a/src/modules/server.c b/src/modules/server.c index 14a4245..cf1d3e0 100644 --- a/src/modules/server.c +++ b/src/modules/server.c @@ -37,6 +37,11 @@ typedef struct server_conn_state_s server_conn_state_t; static server_runtime_t *g_server = NULL; +enum { + SERVER_REQUEST_NATIVE_TAG = 0x53524551u, // SREQ + SERVER_RUNTIME_NATIVE_TAG = 0x5352544du // SRTM +}; + typedef struct stop_waiter_s { ant_value_t promise; struct stop_waiter_s *next; @@ -119,11 +124,11 @@ static inline void server_request_retain(server_request_t *req) { } static inline server_request_t *server_current_request(ant_t *js) { - return (server_request_t *)js_get_native_ptr(js->current_func); + return (server_request_t *)js_get_native(js->current_func, SERVER_REQUEST_NATIVE_TAG); } static inline server_runtime_t *server_current_runtime(ant_t *js) { - return (server_runtime_t *)js_get_native_ptr(js->current_func); + return (server_runtime_t *)js_get_native(js->current_func, SERVER_RUNTIME_NATIVE_TAG); } static ant_value_t server_mkreqfun( @@ -132,7 +137,7 @@ static ant_value_t server_mkreqfun( server_request_t *req ) { ant_value_t func = js_heavy_mkfun(js, fn, js_mkundef()); - js_set_native_ptr(func, req); + js_set_native(func, req, SERVER_REQUEST_NATIVE_TAG); return func; } @@ -142,7 +147,7 @@ static ant_value_t server_mkruntimefun( server_runtime_t *server ) { ant_value_t func = js_heavy_mkfun(js, fn, js_mkundef()); - js_set_native_ptr(func, server); + js_set_native(func, server, SERVER_RUNTIME_NATIVE_TAG); return func; } diff --git a/src/modules/stream.c b/src/modules/stream.c index 6459a5d..a8a1a6c 100644 --- a/src/modules/stream.c +++ b/src/modules/stream.c @@ -52,7 +52,7 @@ static inline void stream_set_end_callback(ant_t *js, ant_value_t stream_obj, an static stream_private_state_t *stream_private_state(ant_value_t stream_obj) { if (!stream_is_instance(stream_obj)) return NULL; - return (stream_private_state_t *)js_get_native_ptr(stream_obj); + return (stream_private_state_t *)js_get_native(stream_obj, STREAM_NATIVE_TAG); } static ant_value_t stream_require_this(ant_t *js, ant_value_t value, const char *label) { @@ -118,7 +118,7 @@ static void stream_finalize(ant_t *js, ant_object_t *obj) { ant_value_t stream_obj = js_obj_from_ptr(obj); stream_private_state_t *priv = stream_private_state(stream_obj); if (!priv) return; - js_set_native_ptr(stream_obj, NULL); + js_clear_native(stream_obj, STREAM_NATIVE_TAG); if (priv->attached_state && priv->attached_state_finalize) priv->attached_state_finalize(js, stream_obj, priv->attached_state); free(priv); @@ -347,9 +347,7 @@ static ant_value_t stream_make_base_object(ant_t *js, ant_value_t proto) { stream_private_state_t *priv = calloc(1, sizeof(*priv)); if (is_object_type(proto)) js_set_proto_init(obj, proto); - js_set_native_tag(obj, STREAM_NATIVE_TAG); - - if (priv) js_set_native_ptr(obj, priv); + js_set_native(obj, priv, STREAM_NATIVE_TAG); js_set_slot(obj, SLOT_AUX, js_mkundef()); js_set_finalizer(obj, stream_finalize); @@ -1801,21 +1799,21 @@ ant_value_t stream_construct_writable(ant_t *js, ant_value_t base_proto, ant_val void stream_init_readable_object(ant_t *js, ant_value_t obj, ant_value_t options) { stream_init_constructors(js); if (!is_object_type(obj)) return; - js_set_native_tag(obj, STREAM_NATIVE_TAG); + js_set_native(obj, NULL, STREAM_NATIVE_TAG); stream_init_readable(js, obj, options); } void stream_init_writable_object(ant_t *js, ant_value_t obj, ant_value_t options) { stream_init_constructors(js); if (!is_object_type(obj)) return; - js_set_native_tag(obj, STREAM_NATIVE_TAG); + js_set_native(obj, NULL, STREAM_NATIVE_TAG); stream_init_writable(js, obj, options); } void stream_init_duplex_object(ant_t *js, ant_value_t obj, ant_value_t options) { stream_init_constructors(js); if (!is_object_type(obj)) return; - js_set_native_tag(obj, STREAM_NATIVE_TAG); + js_set_native(obj, NULL, STREAM_NATIVE_TAG); stream_init_readable(js, obj, options); stream_init_writable(js, obj, options); } diff --git a/src/modules/string_decoder.c b/src/modules/string_decoder.c index 861ee79..3d1fa70 100644 --- a/src/modules/string_decoder.c +++ b/src/modules/string_decoder.c @@ -35,15 +35,14 @@ enum { STRING_DECODER_NATIVE_TAG = 0x53444543u }; // SDEC static sd_state_t *sd_get_state(ant_value_t obj) { if (!js_check_native_tag(obj, STRING_DECODER_NATIVE_TAG)) return NULL; - return (sd_state_t *)js_get_native_ptr(obj); + return (sd_state_t *)js_get_native(obj, STRING_DECODER_NATIVE_TAG); } static void sd_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != STRING_DECODER_NATIVE_TAG) return; - sd_state_t *st = (sd_state_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + sd_state_t *st = (sd_state_t *)js_get_native(value, STRING_DECODER_NATIVE_TAG); if (st) { free(st->td); free(st); } - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, STRING_DECODER_NATIVE_TAG); } static int sd_parse_encoding(const char *s, size_t len) { diff --git a/src/modules/textcodec.c b/src/modules/textcodec.c index 026f29c..89229b5 100644 --- a/src/modules/textcodec.c +++ b/src/modules/textcodec.c @@ -30,14 +30,13 @@ td_state_t *td_state_new(td_encoding_t enc, bool fatal, bool ignore_bom) { static td_state_t *td_get_state(ant_value_t obj) { if (!js_check_native_tag(obj, TEXT_DECODER_NATIVE_TAG)) return NULL; - return (td_state_t *)js_get_native_ptr(obj); + return (td_state_t *)js_get_native(obj, TEXT_DECODER_NATIVE_TAG); } static void td_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != TEXT_DECODER_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, TEXT_DECODER_NATIVE_TAG)); + js_clear_native(value, TEXT_DECODER_NATIVE_TAG); } static int resolve_encoding(const char *s, size_t len) { diff --git a/src/modules/tls.c b/src/modules/tls.c index d63aca4..9330923 100644 --- a/src/modules/tls.c +++ b/src/modules/tls.c @@ -41,7 +41,7 @@ static void tls_context_free(ant_tls_context_wrap_t *wrap) { static ant_tls_context_wrap_t *tls_context_data(ant_value_t value) { if (!js_check_native_tag(value, TLS_CONTEXT_NATIVE_TAG)) return NULL; - return (ant_tls_context_wrap_t *)js_get_native_ptr(value); + return (ant_tls_context_wrap_t *)js_get_native(value, TLS_CONTEXT_NATIVE_TAG); } static bool tls_value_bytes( @@ -95,8 +95,7 @@ static ant_value_t js_tls_context_close(ant_t *js, ant_value_t *args, int nargs) if (!wrap) return js_getthis(js); tls_context_free(wrap); - js_set_native_ptr(wrap->obj, NULL); - js_set_native_tag(wrap->obj, 0); + js_set_native(wrap->obj, NULL, 0); return js_getthis(js); } @@ -214,8 +213,7 @@ static ant_value_t js_tls_create_context(ant_t *js, ant_value_t *args, int nargs js_set_proto_init(obj, g_tls_context_proto); wrap->obj = obj; - js_set_native_ptr(obj, wrap); - js_set_native_tag(obj, TLS_CONTEXT_NATIVE_TAG); + js_set_native(obj, wrap, TLS_CONTEXT_NATIVE_TAG); return obj; } diff --git a/src/modules/url.c b/src/modules/url.c index e179ae7..30eed97 100644 --- a/src/modules/url.c +++ b/src/modules/url.c @@ -31,7 +31,7 @@ enum { url_state_t *url_get_state(ant_value_t obj) { if (!js_check_native_tag(obj, URL_NATIVE_TAG)) return NULL; - return (url_state_t *)js_get_native_ptr(obj); + return (url_state_t *)js_get_native(obj, URL_NATIVE_TAG); } bool usp_is_urlsearchparams(ant_t *js, ant_value_t obj) { @@ -51,10 +51,9 @@ void url_free_state(url_state_t *s) { } static void url_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != URL_NATIVE_TAG) return; - url_free_state((url_state_t *)obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + url_free_state((url_state_t *)js_get_native(value, URL_NATIVE_TAG)); + js_clear_native(value, URL_NATIVE_TAG); } static int default_port_for(const char *proto) { diff --git a/src/modules/wasi.c b/src/modules/wasi.c index ac3ff2e..ed5443b 100644 --- a/src/modules/wasi.c +++ b/src/modules/wasi.c @@ -224,7 +224,7 @@ static ant_value_t wasi_handle_proc_exit(wasm_module_inst_t inst) { static ant_value_t wasi_exported_func_call(ant_t *js, ant_value_t *args, int nargs) { if (!js_check_native_tag(js->current_func, WASI_FUNC_TAG)) return js_mkerr(js, "Invalid WASI function"); - wasi_func_env_t *env = (wasi_func_env_t *)js_get_native_ptr(js->current_func); + wasi_func_env_t *env = (wasi_func_env_t *)js_get_native(js->current_func, WASI_FUNC_TAG); uint32_t param_count = wasm_func_get_param_count(env->func, env->inst); uint32_t result_count = wasm_func_get_result_count(env->func, env->inst); @@ -248,20 +248,19 @@ static ant_value_t wasi_exported_func_call(ant_t *js, ant_value_t *args, int nar } static void wasi_func_finalize(ant_t *js, ant_object_t *obj) { - if (obj->native.tag != WASI_FUNC_TAG) return; - - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, WASI_FUNC_TAG)); + js_clear_native(value, WASI_FUNC_TAG); } static void wasi_instance_finalize(ant_t *js, ant_object_t *obj) { - if (obj->native.tag != WASI_INSTANCE_TAG) return; - wasi_instance_handle_t *handle = (wasi_instance_handle_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + wasi_instance_handle_t *handle = (wasi_instance_handle_t *)js_get_native(value, WASI_INSTANCE_TAG); if (!handle) return; if (handle->exec_env) wasm_runtime_destroy_exec_env(handle->exec_env); if (handle->inst) wasm_runtime_deinstantiate(handle->inst); + js_clear_native(value, WASI_INSTANCE_TAG); if (handle->module) wasm_runtime_unload(handle->module); free(handle->binary); @@ -340,8 +339,7 @@ static void wasi_bind_func_export( GC_ROOT_PIN(js, obj); js_set_slot(obj, SLOT_CFUNC, js_mkfun(wasi_exported_func_call)); - js_set_native_ptr(obj, fenv); - js_set_native_tag(obj, WASI_FUNC_TAG); + js_set_native(obj, fenv, WASI_FUNC_TAG); js_set_slot_wb(js, obj, SLOT_ENTRIES, instance_obj); js_set_finalizer(obj, wasi_func_finalize); js_set(js, exports_obj, name, js_obj_to_func(obj)); @@ -441,8 +439,7 @@ ant_value_t wasi_instantiate( ant_value_t instance_obj = js_mkobj(js); ant_value_t exports_obj = js_mkobj(js); - js_set_native_ptr(instance_obj, handle); - js_set_native_tag(instance_obj, WASI_INSTANCE_TAG); + js_set_native(instance_obj, handle, WASI_INSTANCE_TAG); js_set_slot_wb(js, instance_obj, SLOT_CTOR, module_obj); js_set_finalizer(instance_obj, wasi_instance_finalize); diff --git a/src/modules/wasm.c b/src/modules/wasm.c index 2cbe360..8a41288 100644 --- a/src/modules/wasm.c +++ b/src/modules/wasm.c @@ -179,13 +179,13 @@ static wasm_valkind_t wasm_valkind_from_string(const char *name, size_t len, boo static wasm_module_handle_t *wasm_module_handle(ant_value_t value) { if (!js_check_brand(value, BRAND_WASM_MODULE)) return NULL; if (!js_check_native_tag(value, WASM_MODULE_NATIVE_TAG)) return NULL; - return (wasm_module_handle_t *)js_get_native_ptr(value); + return (wasm_module_handle_t *)js_get_native(value, WASM_MODULE_NATIVE_TAG); } static wasm_instance_handle_t *wasm_instance_handle(ant_value_t value) { if (!js_check_brand(value, BRAND_WASM_INSTANCE)) return NULL; if (!js_check_native_tag(value, WASM_INSTANCE_NATIVE_TAG)) return NULL; - return (wasm_instance_handle_t *)js_get_native_ptr(value); + return (wasm_instance_handle_t *)js_get_native(value, WASM_INSTANCE_NATIVE_TAG); } static wasm_extern_handle_t *wasm_extern_handle(ant_value_t value, wasm_extern_wrap_kind_t kind) { @@ -196,7 +196,7 @@ static wasm_extern_handle_t *wasm_extern_handle(ant_value_t value, wasm_extern_w } if (!js_check_native_tag(value, WASM_EXTERN_NATIVE_TAG)) return NULL; - wasm_extern_handle_t *handle = (wasm_extern_handle_t *)js_get_native_ptr(value); + wasm_extern_handle_t *handle = (wasm_extern_handle_t *)js_get_native(value, WASM_EXTERN_NATIVE_TAG); return handle && handle->kind == kind ? handle : NULL; } @@ -325,7 +325,7 @@ static bool js_value_to_wasm(ant_t *js, ant_value_t value, wasm_valkind_t kind, state = js_get_slot(value, SLOT_DATA); if (!is_object_type(state) || !js_check_native_tag(state, WASM_FUNC_STATE_TAG)) return false; - handle = (wasm_func_handle_t *)js_get_native_ptr(state); + handle = (wasm_func_handle_t *)js_get_native(state, WASM_FUNC_STATE_TAG); if (!handle || !handle->func) return false; out->of.ref = wasm_func_as_ref(handle->func); return out->of.ref != NULL; @@ -375,15 +375,14 @@ static ant_value_t wasm_wrap_module(ant_t *js, wasm_store_t *store, wasm_module_ } static void wasm_module_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WASM_MODULE_NATIVE_TAG) return; - wasm_module_handle_t *handle = (wasm_module_handle_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + wasm_module_handle_t *handle = (wasm_module_handle_t *)js_get_native(value, WASM_MODULE_NATIVE_TAG); if (!handle) return; if (handle->module) wasm_module_delete(handle->module); if (handle->store) wasm_store_delete(handle->store); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WASM_MODULE_NATIVE_TAG); } static ant_value_t wasm_wrap_instance(ant_t *js, wasm_instance_handle_t *handle, ant_value_t module_ref) { @@ -396,8 +395,8 @@ static ant_value_t wasm_wrap_instance(ant_t *js, wasm_instance_handle_t *handle, } static void wasm_instance_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WASM_INSTANCE_NATIVE_TAG) return; - wasm_instance_handle_t *handle = (wasm_instance_handle_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + wasm_instance_handle_t *handle = (wasm_instance_handle_t *)js_get_native(value, WASM_INSTANCE_NATIVE_TAG); if (!handle) return; for (size_t j = 0; j < handle->host_func_count; j++) if (handle->host_funcs[j]) wasm_func_delete(handle->host_funcs[j]); @@ -405,8 +404,7 @@ static void wasm_instance_finalize(ant_t *js, ant_object_t *obj) { free(handle->host_funcs); wasm_extern_vec_delete(&handle->exports); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WASM_INSTANCE_NATIVE_TAG); } static ant_value_t wasm_wrap_extern_object(ant_t *js, wasm_extern_wrap_kind_t kind, ant_value_t proto, int brand, wasm_store_t *store, bool own_handle, void *ptr, ant_value_t owner) { @@ -433,8 +431,8 @@ static ant_value_t wasm_wrap_extern_object(ant_t *js, wasm_extern_wrap_kind_t ki } static void wasm_extern_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WASM_EXTERN_NATIVE_TAG) return; - wasm_extern_handle_t *handle = (wasm_extern_handle_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + wasm_extern_handle_t *handle = (wasm_extern_handle_t *)js_get_native(value, WASM_EXTERN_NATIVE_TAG); if (!handle) return; if (handle->own_handle) { @@ -453,8 +451,7 @@ static void wasm_extern_finalize(ant_t *js, ant_object_t *obj) { } free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WASM_EXTERN_NATIVE_TAG); } static ant_value_t js_wasm_exported_func_call(ant_t *js, ant_value_t *args, int nargs) { @@ -465,7 +462,7 @@ static ant_value_t js_wasm_exported_func_call(ant_t *js, ant_value_t *args, int if (!is_object_type(state) || !js_check_native_tag(state, WASM_FUNC_STATE_TAG)) return js_mkerr(js, "Invalid WebAssembly function"); - handle = (wasm_func_handle_t *)js_get_native_ptr(state); + handle = (wasm_func_handle_t *)js_get_native(state, WASM_FUNC_STATE_TAG); func = handle ? handle->func : NULL; if (!func) return js_mkerr(js, "Invalid WebAssembly function"); @@ -531,15 +528,13 @@ static ant_value_t js_wasm_exported_func_call(ant_t *js, ant_value_t *args, int } static void wasm_func_state_finalize(ant_t *js, ant_object_t *obj) { - if (obj->native.tag != WASM_FUNC_STATE_TAG) return; - - wasm_func_handle_t *handle = (wasm_func_handle_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + wasm_func_handle_t *handle = (wasm_func_handle_t *)js_get_native(value, WASM_FUNC_STATE_TAG); if (!handle) return; if (handle->own_func && handle->func) wasm_func_delete(handle->func); free(handle); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WASM_FUNC_STATE_TAG); } static ant_value_t wasm_wrap_func(ant_t *js, wasm_func_t *func, ant_value_t owner, bool own_func) { @@ -558,8 +553,7 @@ static ant_value_t wasm_wrap_func(ant_t *js, wasm_func_t *func, ant_value_t owne handle->own_func = own_func; state = js_mkobj(js); - js_set_native_ptr(state, handle); - js_set_native_tag(state, WASM_FUNC_STATE_TAG); + js_set_native(state, handle, WASM_FUNC_STATE_TAG); if (is_object_type(owner)) js_set_slot_wb(js, state, SLOT_ENTRIES, owner); js_set_finalizer(state, wasm_func_state_finalize); @@ -1221,7 +1215,7 @@ static ant_value_t js_wasm_table_set(ant_t *js, ant_value_t *args, int nargs) { if (!is_object_type(state) || !js_check_native_tag(state, WASM_FUNC_STATE_TAG)) return js_mkerr_typed(js, JS_ERR_TYPE, "WebAssembly.Table.set expects a WebAssembly function or null"); - func_handle = (wasm_func_handle_t *)js_get_native_ptr(state); + func_handle = (wasm_func_handle_t *)js_get_native(state, WASM_FUNC_STATE_TAG); if (!func_handle || !func_handle->func) return js_mkerr_typed(js, JS_ERR_TYPE, "WebAssembly.Table.set expects a WebAssembly function or null"); diff --git a/src/modules/worker_threads.c b/src/modules/worker_threads.c index 58ce686..b15c037 100644 --- a/src/modules/worker_threads.c +++ b/src/modules/worker_threads.c @@ -94,7 +94,7 @@ static void wt_init_env_store(ant_t *js, bool is_worker) { static ant_worker_thread_t *wt_get_worker(ant_t *js, ant_value_t this_obj) { if (!is_object_type(this_obj)) return NULL; if (!js_check_native_tag(this_obj, WORKER_NATIVE_TAG)) return NULL; - return (ant_worker_thread_t *)js_get_native_ptr(this_obj); + return (ant_worker_thread_t *)js_get_native(this_obj, WORKER_NATIVE_TAG); } static bool wt_is_message_port(ant_t *js, ant_value_t obj) { diff --git a/src/modules/zlib.c b/src/modules/zlib.c index 0fdbb4d..6d738f8 100644 --- a/src/modules/zlib.c +++ b/src/modules/zlib.c @@ -76,7 +76,7 @@ static ant_value_t pick_callback(ant_value_t *args, int nargs) { static zlib_stream_t *zlib_stream_ptr(ant_value_t obj) { if (!js_check_native_tag(obj, ZLIB_STREAM_TAG)) return NULL; - return (zlib_stream_t *)js_get_native_ptr(obj); + return (zlib_stream_t *)js_get_native(obj, ZLIB_STREAM_TAG); } static void zlib_add_active(zlib_stream_t *st) { @@ -424,8 +424,7 @@ static ant_value_t zlib_create_stream(ant_t *js, zlib_kind_t kind) { ant_value_t obj = js_mkobj(js); if (is_object_type(g_transform_proto)) js_set_proto_init(obj, g_transform_proto); - js_set_native_ptr(obj, st); - js_set_native_tag(obj, ZLIB_STREAM_TAG); + js_set_native(obj, st, ZLIB_STREAM_TAG); js_set(js, obj, "readable", js_true); js_set(js, obj, "writable", js_true); diff --git a/src/silver/ops/upvalues.h b/src/silver/ops/upvalues.h index 9418e98..a1173c6 100644 --- a/src/silver/ops/upvalues.h +++ b/src/silver/ops/upvalues.h @@ -11,7 +11,6 @@ static inline ant_value_t sv_setup_function_prototype_with_parent( ) { ant_value_t proto_obj = mkobj(js, 0); if (is_err(proto_obj)) return proto_obj; - if (is_object_type(parent_proto)) js_set_proto_init(proto_obj, parent_proto); ant_value_t ctor_key = js_mkstr(js, "constructor", 11); if (is_err(ctor_key)) return ctor_key; @@ -20,6 +19,8 @@ static inline ant_value_t sv_setup_function_prototype_with_parent( if (is_err(set_ctor)) return set_ctor; js_set_descriptor(js, proto_obj, "constructor", 11, JS_DESC_W | JS_DESC_C); + if (is_object_type(parent_proto)) js_set_proto_init(proto_obj, parent_proto); + ant_value_t proto_key = js_mkstr(js, "prototype", 9); if (is_err(proto_key)) return proto_key; diff --git a/src/streams/codec.c b/src/streams/codec.c index 754bd8c..3e083dc 100644 --- a/src/streams/codec.c +++ b/src/streams/codec.c @@ -64,17 +64,15 @@ ant_value_t tds_stream_writable(ant_value_t obj) { } static void tes_state_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != TES_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, TES_NATIVE_TAG)); + js_clear_native(value, TES_NATIVE_TAG); } static void tds_state_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != TDS_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, TDS_NATIVE_TAG)); + js_clear_native(value, TDS_NATIVE_TAG); } static ant_value_t codec_transform_controller(ant_value_t *args, int nargs) { @@ -87,7 +85,7 @@ static ant_value_t codec_flush_controller(ant_value_t *args, int nargs) { static ant_value_t tes_transform(ant_t *js, ant_value_t *args, int nargs) { tes_state_t *st = js_check_native_tag(js->current_func, TES_NATIVE_TAG) - ? (tes_state_t *)js_get_native_ptr(js->current_func) + ? (tes_state_t *)js_get_native(js->current_func, TES_NATIVE_TAG) : NULL; if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid TextEncoderStream"); @@ -174,7 +172,7 @@ static ant_value_t tes_transform(ant_t *js, ant_value_t *args, int nargs) { static ant_value_t tes_flush(ant_t *js, ant_value_t *args, int nargs) { tes_state_t *st = js_check_native_tag(js->current_func, TES_NATIVE_TAG) - ? (tes_state_t *)js_get_native_ptr(js->current_func) + ? (tes_state_t *)js_get_native(js->current_func, TES_NATIVE_TAG) : NULL; if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid TextEncoderStream"); @@ -242,13 +240,15 @@ static ant_value_t js_tes_ctor(ant_t *js, ant_value_t *args, int nargs) { if (is_err(ts_obj)) { free(st); return ts_obj; } js_set_slot(obj, SLOT_ENTRIES, ts_obj); + js_set_slot_wb(js, transform_fn, SLOT_ENTRIES, obj); + js_set_slot_wb(js, flush_fn, SLOT_ENTRIES, obj); return obj; } static ant_value_t tds_transform(ant_t *js, ant_value_t *args, int nargs) { td_state_t *st = js_check_native_tag(js->current_func, TDS_NATIVE_TAG) - ? (td_state_t *)js_get_native_ptr(js->current_func) + ? (td_state_t *)js_get_native(js->current_func, TDS_NATIVE_TAG) : NULL; if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid TextDecoderStream"); @@ -277,7 +277,7 @@ static ant_value_t tds_transform(ant_t *js, ant_value_t *args, int nargs) { static ant_value_t tds_flush(ant_t *js, ant_value_t *args, int nargs) { td_state_t *st = js_check_native_tag(js->current_func, TDS_NATIVE_TAG) - ? (td_state_t *)js_get_native_ptr(js->current_func) + ? (td_state_t *)js_get_native(js->current_func, TDS_NATIVE_TAG) : NULL; if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid TextDecoderStream"); @@ -298,7 +298,7 @@ static ant_value_t tds_flush(ant_t *js, ant_value_t *args, int nargs) { } static ant_value_t js_tds_get_encoding(ant_t *js, ant_value_t *args, int nargs) { - td_state_t *st = (td_state_t *)js_get_native_ptr(js->this_val); + td_state_t *st = (td_state_t *)js_get_native(js->this_val, TDS_NATIVE_TAG); if (!st) return js_mkstr(js, "utf-8", 5); switch (st->encoding) { case TD_ENC_UTF16LE: return js_mkstr(js, "utf-16le", 8); @@ -310,12 +310,12 @@ static ant_value_t js_tds_get_encoding(ant_t *js, ant_value_t *args, int nargs) } static ant_value_t js_tds_get_fatal(ant_t *js, ant_value_t *args, int nargs) { - td_state_t *st = (td_state_t *)js_get_native_ptr(js->this_val); + td_state_t *st = (td_state_t *)js_get_native(js->this_val, TDS_NATIVE_TAG); return (st && st->fatal) ? js_true : js_false; } static ant_value_t js_tds_get_ignore_bom(ant_t *js, ant_value_t *args, int nargs) { - td_state_t *st = (td_state_t *)js_get_native_ptr(js->this_val); + td_state_t *st = (td_state_t *)js_get_native(js->this_val, TDS_NATIVE_TAG); return (st && st->ignore_bom) ? js_true : js_false; } @@ -421,6 +421,8 @@ static ant_value_t js_tds_ctor(ant_t *js, ant_value_t *args, int nargs) { if (is_err(ts_obj)) { free(st); return ts_obj; } js_set_slot(obj, SLOT_ENTRIES, ts_obj); + js_set_slot_wb(js, transform_fn, SLOT_ENTRIES, obj); + js_set_slot_wb(js, flush_fn, SLOT_ENTRIES, obj); return obj; } diff --git a/src/streams/compression.c b/src/streams/compression.c index b00f074..5445903 100644 --- a/src/streams/compression.c +++ b/src/streams/compression.c @@ -87,31 +87,31 @@ ant_value_t ds_stream_writable(ant_value_t obj) { } static void zstate_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != CS_Z_NATIVE_TAG) return; - zstate_t *st = (zstate_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + zstate_t *st = (zstate_t *)js_get_native(value, CS_Z_NATIVE_TAG); if (!st) return; if (st->initialized) deflateEnd(&st->strm); free(st); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, CS_Z_NATIVE_TAG); } static void zstate_inflate_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != DS_Z_NATIVE_TAG) return; - zstate_t *st = (zstate_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + zstate_t *st = (zstate_t *)js_get_native(value, DS_Z_NATIVE_TAG); if (!st) return; if (st->initialized) inflateEnd(&st->strm); free(st); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, DS_Z_NATIVE_TAG); } static void brotli_state_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || (obj->native.tag != CS_BROTLI_NATIVE_TAG && obj->native.tag != DS_BROTLI_NATIVE_TAG)) return; - brotli_stream_state_t *st = (brotli_stream_state_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + uint32_t tag = js_check_native_tag(value, CS_BROTLI_NATIVE_TAG) + ? CS_BROTLI_NATIVE_TAG + : DS_BROTLI_NATIVE_TAG; + brotli_stream_state_t *st = (brotli_stream_state_t *)js_get_native(value, tag); brotli_stream_state_destroy(st); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, tag); } static ant_value_t enqueue_buffer(ant_t *js, ant_value_t ctrl_obj, const uint8_t *data, size_t len) { @@ -127,9 +127,6 @@ static ant_value_t enqueue_buffer(ant_t *js, ant_value_t ctrl_obj, const uint8_t #define ZCHUNK_SIZE 16384 static ant_value_t cs_transform(ant_t *js, ant_value_t *args, int nargs) { - uint32_t tag = js_get_native_tag(js->current_func); - zstate_t *st = (zstate_t *)js_get_native_ptr(js->current_func); - ant_value_t ctrl_obj = (nargs > 1) ? args[1] : js_mkundef(); ant_value_t chunk = (nargs > 0) ? args[0] : js_mkundef(); @@ -141,12 +138,12 @@ static ant_value_t cs_transform(ant_t *js, ant_value_t *args, int nargs) { if (!input || input_len == 0) return js_mkundef(); - if (tag == CS_BROTLI_NATIVE_TAG) { - brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native_ptr(js->current_func); + brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native(js->current_func, CS_BROTLI_NATIVE_TAG); + if (brotli_st) return brotli_stream_transform(js, brotli_st, ctrl_obj, input, input_len); - } - if (tag != CS_Z_NATIVE_TAG || !st) + zstate_t *st = (zstate_t *)js_get_native(js->current_func, CS_Z_NATIVE_TAG); + if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid CompressionStream"); st->strm.next_in = (Bytef *)input; @@ -170,16 +167,14 @@ static ant_value_t cs_transform(ant_t *js, ant_value_t *args, int nargs) { } static ant_value_t cs_flush(ant_t *js, ant_value_t *args, int nargs) { - uint32_t tag = js_get_native_tag(js->current_func); ant_value_t ctrl_obj = (nargs > 0) ? args[0] : js_mkundef(); - if (tag == CS_BROTLI_NATIVE_TAG) { - brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native_ptr(js->current_func); + brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native(js->current_func, CS_BROTLI_NATIVE_TAG); + if (brotli_st) return brotli_stream_flush(js, brotli_st, ctrl_obj); - } - zstate_t *st = (zstate_t *)js_get_native_ptr(js->current_func); - if (tag != CS_Z_NATIVE_TAG || !st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid CompressionStream"); + zstate_t *st = (zstate_t *)js_get_native(js->current_func, CS_Z_NATIVE_TAG); + if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid CompressionStream"); st->strm.next_in = NULL; st->strm.avail_in = 0; @@ -274,13 +269,13 @@ static ant_value_t js_cs_ctor(ant_t *js, ant_value_t *args, int nargs) { return ts_obj; } js_set_slot(obj, SLOT_ENTRIES, ts_obj); + js_set_slot_wb(js, transform_fn, SLOT_ENTRIES, obj); + js_set_slot_wb(js, flush_fn, SLOT_ENTRIES, obj); return obj; } static ant_value_t ds_transform(ant_t *js, ant_value_t *args, int nargs) { - uint32_t tag = js_get_native_tag(js->current_func); - zstate_t *st = (zstate_t *)js_get_native_ptr(js->current_func); ant_value_t ctrl_obj = (nargs > 1) ? args[1] : js_mkundef(); ant_value_t chunk = (nargs > 0) ? args[0] : js_mkundef(); @@ -291,12 +286,12 @@ static ant_value_t ds_transform(ant_t *js, ant_value_t *args, int nargs) { return js_mkerr_typed(js, JS_ERR_TYPE, "The provided value is not of type '(ArrayBuffer or ArrayBufferView)'"); if (!input || input_len == 0) return js_mkundef(); - if (tag == DS_BROTLI_NATIVE_TAG) { - brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native_ptr(js->current_func); + brotli_stream_state_t *brotli_st = (brotli_stream_state_t *)js_get_native(js->current_func, DS_BROTLI_NATIVE_TAG); + if (brotli_st) return brotli_stream_transform(js, brotli_st, ctrl_obj, input, input_len); - } - if (tag != DS_Z_NATIVE_TAG || !st) + zstate_t *st = (zstate_t *)js_get_native(js->current_func, DS_Z_NATIVE_TAG); + if (!st) return js_mkerr_typed(js, JS_ERR_TYPE, "Invalid DecompressionStream"); st->strm.next_in = (Bytef *)input; @@ -321,12 +316,10 @@ static ant_value_t ds_transform(ant_t *js, ant_value_t *args, int nargs) { } static ant_value_t ds_flush(ant_t *js, ant_value_t *args, int nargs) { - uint32_t tag = js_get_native_tag(js->current_func); ant_value_t ctrl_obj = (nargs > 0) ? args[0] : js_mkundef(); - if (tag == DS_BROTLI_NATIVE_TAG) { - brotli_stream_state_t *st = (brotli_stream_state_t *)js_get_native_ptr(js->current_func); + brotli_stream_state_t *st = (brotli_stream_state_t *)js_get_native(js->current_func, DS_BROTLI_NATIVE_TAG); + if (st) return brotli_stream_flush(js, st, ctrl_obj); - } return js_mkundef(); } @@ -404,6 +397,8 @@ static ant_value_t js_ds_ctor(ant_t *js, ant_value_t *args, int nargs) { } js_set_slot(obj, SLOT_ENTRIES, ts_obj); + js_set_slot_wb(js, transform_fn, SLOT_ENTRIES, obj); + js_set_slot_wb(js, flush_fn, SLOT_ENTRIES, obj); return obj; } diff --git a/src/streams/pipes.c b/src/streams/pipes.c index 71f4094..6512282 100644 --- a/src/streams/pipes.c +++ b/src/streams/pipes.c @@ -52,15 +52,14 @@ static void pipes_chain_promise( } static void pipe_state_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != PIPE_STATE_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, PIPE_STATE_NATIVE_TAG)); + js_clear_native(value, PIPE_STATE_NATIVE_TAG); } static pipe_state_t *pipe_get_state(ant_value_t state) { if (!js_check_native_tag(state, PIPE_STATE_NATIVE_TAG)) return NULL; - return (pipe_state_t *)js_get_native_ptr(state); + return (pipe_state_t *)js_get_native(state, PIPE_STATE_NATIVE_TAG); } static ant_value_t pipe_state_source(ant_value_t state) { @@ -489,15 +488,14 @@ typedef struct { } tee_state_t; static void tee_state_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != TEE_STATE_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, TEE_STATE_NATIVE_TAG)); + js_clear_native(value, TEE_STATE_NATIVE_TAG); } static tee_state_t *tee_get_state(ant_value_t state) { if (!js_check_native_tag(state, TEE_STATE_NATIVE_TAG)) return NULL; - return (tee_state_t *)js_get_native_ptr(state); + return (tee_state_t *)js_get_native(state, TEE_STATE_NATIVE_TAG); } static ant_value_t tee_state_reader(ant_value_t state) { diff --git a/src/streams/readable.c b/src/streams/readable.c index 15a5852..f9cb48a 100644 --- a/src/streams/readable.c +++ b/src/streams/readable.c @@ -51,29 +51,27 @@ bool rs_stream_unusable(ant_value_t stream_obj) { rs_stream_t *rs_get_stream(ant_value_t obj) { if (!js_check_native_tag(obj, RS_STREAM_NATIVE_TAG)) return NULL; - return (rs_stream_t *)js_get_native_ptr(obj); + return (rs_stream_t *)js_get_native(obj, RS_STREAM_NATIVE_TAG); } rs_controller_t *rs_get_controller(ant_value_t obj) { if (!js_check_native_tag(obj, RS_CONTROLLER_NATIVE_TAG)) return NULL; - return (rs_controller_t *)js_get_native_ptr(obj); + return (rs_controller_t *)js_get_native(obj, RS_CONTROLLER_NATIVE_TAG); } static void rs_stream_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != RS_STREAM_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, RS_STREAM_NATIVE_TAG)); + js_clear_native(value, RS_STREAM_NATIVE_TAG); } static void rs_controller_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != RS_CONTROLLER_NATIVE_TAG) return; - rs_controller_t *ctrl = (rs_controller_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + rs_controller_t *ctrl = (rs_controller_t *)js_get_native(value, RS_CONTROLLER_NATIVE_TAG); if (!ctrl) return; free(ctrl->queue_sizes); free(ctrl); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, RS_CONTROLLER_NATIVE_TAG); } ant_value_t rs_stream_controller(ant_t *js, ant_value_t stream_obj) { diff --git a/src/streams/transform.c b/src/streams/transform.c index 7384179..9ada7eb 100644 --- a/src/streams/transform.c +++ b/src/streams/transform.c @@ -55,37 +55,33 @@ ant_value_t ts_stream_writable(ant_value_t ts_obj) { } static void ts_ws_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WS_STREAM_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, WS_STREAM_NATIVE_TAG)); + js_clear_native(value, WS_STREAM_NATIVE_TAG); } static void ts_ws_ctrl_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WS_CONTROLLER_NATIVE_TAG) return; - ws_controller_t *ctrl = (ws_controller_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + ws_controller_t *ctrl = (ws_controller_t *)js_get_native(value, WS_CONTROLLER_NATIVE_TAG); if (!ctrl) return; free(ctrl->queue_sizes); free(ctrl); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WS_CONTROLLER_NATIVE_TAG); } static void ts_rs_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != RS_STREAM_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, RS_STREAM_NATIVE_TAG)); + js_clear_native(value, RS_STREAM_NATIVE_TAG); } static void ts_rs_ctrl_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != RS_CONTROLLER_NATIVE_TAG) return; - rs_controller_t *ctrl = (rs_controller_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + rs_controller_t *ctrl = (rs_controller_t *)js_get_native(value, RS_CONTROLLER_NATIVE_TAG); if (!ctrl) return; free(ctrl->queue_sizes); free(ctrl); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, RS_CONTROLLER_NATIVE_TAG); } static inline bool ts_get_backpressure(ant_value_t ts_obj) { diff --git a/src/streams/writable.c b/src/streams/writable.c index 2d069cc..4996d34 100644 --- a/src/streams/writable.c +++ b/src/streams/writable.c @@ -39,29 +39,27 @@ bool ws_is_controller(ant_value_t obj) { ws_stream_t *ws_get_stream(ant_value_t obj) { if (!js_check_native_tag(obj, WS_STREAM_NATIVE_TAG)) return NULL; - return (ws_stream_t *)js_get_native_ptr(obj); + return (ws_stream_t *)js_get_native(obj, WS_STREAM_NATIVE_TAG); } ws_controller_t *ws_get_controller(ant_value_t obj) { if (!js_check_native_tag(obj, WS_CONTROLLER_NATIVE_TAG)) return NULL; - return (ws_controller_t *)js_get_native_ptr(obj); + return (ws_controller_t *)js_get_native(obj, WS_CONTROLLER_NATIVE_TAG); } static void ws_stream_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WS_STREAM_NATIVE_TAG) return; - free(obj->native.ptr); - obj->native.ptr = NULL; - obj->native.tag = 0; + ant_value_t value = js_obj_from_ptr(obj); + free(js_get_native(value, WS_STREAM_NATIVE_TAG)); + js_clear_native(value, WS_STREAM_NATIVE_TAG); } static void ws_controller_finalize(ant_t *js, ant_object_t *obj) { - if (!obj || obj->native.tag != WS_CONTROLLER_NATIVE_TAG) return; - ws_controller_t *ctrl = (ws_controller_t *)obj->native.ptr; + ant_value_t value = js_obj_from_ptr(obj); + ws_controller_t *ctrl = (ws_controller_t *)js_get_native(value, WS_CONTROLLER_NATIVE_TAG); if (!ctrl) return; free(ctrl->queue_sizes); free(ctrl); - obj->native.ptr = NULL; - obj->native.tag = 0; + js_clear_native(value, WS_CONTROLLER_NATIVE_TAG); } ant_value_t ws_stream_controller(ant_value_t stream_obj) {