diff --git a/IntegrationTests/TestSuites/Sources/PrimaryTests/main.swift b/IntegrationTests/TestSuites/Sources/PrimaryTests/main.swift index b58b037e7..140cc0bd3 100644 --- a/IntegrationTests/TestSuites/Sources/PrimaryTests/main.swift +++ b/IntegrationTests/TestSuites/Sources/PrimaryTests/main.swift @@ -228,6 +228,8 @@ New_Object_Construction: do { let cat1 = objectConstructor.new("Tama", 3, true) try expectEqual(getJSValue(this: cat1, name: "name"), .string("Tama")) try expectEqual(getJSValue(this: cat1, name: "age"), .number(3)) + try expectEqual(cat1.instanceof(objectConstructor), true) + try expectEqual(cat1.instanceof(try expectFunction(getJSValue(this: .global, name: "Array"))), false) let cat1Bark = try expectFunction(getJSValue(this: cat1, name: "bark")) try expectEqual(cat1Bark(), .string("nyan")) diff --git a/Runtime/src/index.ts b/Runtime/src/index.ts index b126b3e4f..94e436aed 100644 --- a/Runtime/src/index.ts +++ b/Runtime/src/index.ts @@ -59,7 +59,7 @@ class SwiftRuntimeHeap { allocHeap(value: any) { const isObject = typeof value == "object"; - const entry = this._heapEntryByValue.get(value); + const entry = this._heapEntryByValue.get(value); if (isObject && entry) { entry.rc++ return entry.id @@ -362,6 +362,14 @@ export class SwiftRuntime { throw Error(`Invalid result type of object constructor of "${obj}": "${result}"`) writeUint32(result_obj, this.heap.allocHeap(result)); }, + swjs_instanceof: ( + obj_ref: ref, constructor_ref: ref, + result_ptr: pointer + ) => { + const obj = this.heap.referenceHeap(obj_ref) + const constructor = this.heap.referenceHeap(constructor_ref) + return obj instanceof constructor + }, swjs_destroy_ref: (ref: ref) => { this.heap.freeHeap(ref) } diff --git a/Sources/JavaScriptKit/JSObject.swift b/Sources/JavaScriptKit/JSObject.swift index 2253d9775..47ae2b4a6 100644 --- a/Sources/JavaScriptKit/JSObject.swift +++ b/Sources/JavaScriptKit/JSObject.swift @@ -32,6 +32,10 @@ public class JSObjectRef: Equatable { getJSValue(this: self, index: Int32(index)) } + public func instanceof(_ constructor: JSFunctionRef) -> Bool { + _instanceof(self.id, constructor.id) + } + public subscript(_ index: Int) -> JSValue { get { get(index) } set { set(index, newValue) } diff --git a/Sources/JavaScriptKit/XcodeSupport.swift b/Sources/JavaScriptKit/XcodeSupport.swift index b75972444..180072ebf 100644 --- a/Sources/JavaScriptKit/XcodeSupport.swift +++ b/Sources/JavaScriptKit/XcodeSupport.swift @@ -64,6 +64,10 @@ import _CJavaScriptKit _: UnsafePointer!, _: Int32, _: UnsafeMutablePointer! ) { fatalError() } + func _instanceof( + _: JavaScriptObjectRef, + _: JavaScriptObjectRef + ) -> Bool { fatalError() } func _create_function( _: JavaScriptHostFuncRef, _: UnsafePointer! diff --git a/Sources/_CJavaScriptKit/include/_CJavaScriptKit.h b/Sources/_CJavaScriptKit/include/_CJavaScriptKit.h index bc54ba345..61789e16c 100644 --- a/Sources/_CJavaScriptKit/include/_CJavaScriptKit.h +++ b/Sources/_CJavaScriptKit/include/_CJavaScriptKit.h @@ -2,6 +2,7 @@ #define _CJavaScriptKit_h #include +#include typedef unsigned int JavaScriptObjectRef; typedef unsigned int JavaScriptHostFuncRef; @@ -82,6 +83,11 @@ __attribute__((__import_module__("javascript_kit"), _call_new(const JavaScriptObjectRef ref, const RawJSValue *argv, const int argc, JavaScriptObjectRef *result_obj); +__attribute__((__import_module__("javascript_kit"), + __import_name__("swjs_instanceof"))) extern bool +_instanceof(const JavaScriptObjectRef obj, + const JavaScriptObjectRef constructor); + __attribute__((__import_module__("javascript_kit"), __import_name__("swjs_create_function"))) extern void _create_function(const JavaScriptHostFuncRef host_func_id,