[TS] Handle nullable arrays and objects in more cases
[ldk-java] / typescript_strings.py
index 52dd12ce03bf0822023beb18390e429e2f0bd65a..aeb2a4ae8e68b5ac7214eec3a0c5273e844cfb14 100644 (file)
@@ -167,7 +167,8 @@ export function WitnessVersionArrToBytes(inputArray: Array<WitnessVersion>): Uin
 
 
 /* @internal */
-export function encodeUint8Array (inputArray: Uint8Array): number {
+export function encodeUint8Array (inputArray: Uint8Array|null): number {
+       if (inputArray == null) return 0;
        const cArrayPointer = wasm.TS_malloc(inputArray.length + 8);
        const arrayLengthView = new BigUint64Array(wasm.memory.buffer, cArrayPointer, 1);
        arrayLengthView[0] = BigInt(inputArray.length);
@@ -176,7 +177,8 @@ export function encodeUint8Array (inputArray: Uint8Array): number {
        return cArrayPointer;
 }
 /* @internal */
-export function encodeUint32Array (inputArray: Uint32Array|Array<number>): number {
+export function encodeUint32Array (inputArray: Uint32Array|Array<number>|null): number {
+       if (inputArray == null) return 0;
        const cArrayPointer = wasm.TS_malloc((inputArray.length + 2) * 4);
        const arrayLengthView = new BigUint64Array(wasm.memory.buffer, cArrayPointer, 1);
        arrayLengthView[0] = BigInt(inputArray.length);
@@ -185,17 +187,18 @@ export function encodeUint32Array (inputArray: Uint32Array|Array<number>): numbe
        return cArrayPointer;
 }
 /* @internal */
-export function encodeUint64Array (inputArray: BigUint64Array|Array<bigint>): number {
+export function encodeUint64Array (inputArray: BigUint64Array|Array<bigint>|null): number {
+       if (inputArray == null) return 0;
        const cArrayPointer = wasm.TS_malloc((inputArray.length + 1) * 8);
-       const arrayMemoryView = new BigUint64Array(wasm.memory.buffer, cArrayPointer, 1);
-       arrayMemoryView.set(inputArray, 1);
+       const arrayMemoryView = new BigUint64Array(wasm.memory.buffer, cArrayPointer, inputArray.length + 1);
        arrayMemoryView[0] = BigInt(inputArray.length);
+       arrayMemoryView.set(inputArray, 1);
        return cArrayPointer;
 }
 
 /* @internal */
-export function check_arr_len(arr: Uint8Array, len: number): Uint8Array {
-       if (arr.length != len) { throw new Error("Expected array of length " + len + " got " + arr.length); }
+export function check_arr_len(arr: Uint8Array|null, len: number): Uint8Array {
+       if (arr !== null && arr.length != len) { throw new Error("Expected array of length " + len + " got " + arr.length); }
        return arr;
 }
 
@@ -347,8 +350,8 @@ export class CommonBase {
        // In Java, protected means "any subclass can access fields on any other subclass'"
        // In TypeScript, protected means "any subclass can access parent fields on instances of itself"
        // To work around this, we add accessors for other instances' protected fields here.
-       protected static add_ref_from(holder: CommonBase, referent: object) {
-               if (holder !== null) { holder.ptrs_to.push(referent); }
+       protected static add_ref_from(holder: CommonBase|null, referent: object|null) {
+               if (holder !== null && referent !== null) { holder.ptrs_to.push(referent); }
        }
        protected static get_ptr_of(o: CommonBase) {
                return o.ptr;
@@ -871,7 +874,7 @@ export enum {struct_name} {{
                 else:
                     bindings_instantiator += ", " + first_to_lower(var.arg_name)
             else:
-                bindings_instantiator += ", " + first_to_lower(var[1]) + ".bindings_instance"
+                bindings_instantiator += ", " + first_to_lower(var[1]) + ".instance_idx"
                 super_instantiator += first_to_lower(var[1]) + "_impl, "
                 pointer_to_adder += "\t\timpl_holder.held.ptrs_to.push(" + first_to_lower(var[1]) + ");\n"
                 impl_constructor_arguments += f", {first_to_lower(var[1])}_impl: {var[0].replace('LDK', '')}Interface"
@@ -883,7 +886,7 @@ export enum {struct_name} {{
                 trait_constructor_arguments += ", " + var.arg_name
             else:
                 super_constructor_statements += "\t\tconst " + first_to_lower(var[1]) + " = " + var[1] + ".new_impl(" + super_instantiator + ");\n"
-                trait_constructor_arguments += ", " + first_to_lower(var[1]) + ".bindings_instance"
+                trait_constructor_arguments += ", " + first_to_lower(var[1]) + ".instance_idx"
                 for suparg in var[2]:
                     if isinstance(suparg, ConvInfo):
                         trait_constructor_arguments += ", " + suparg.arg_name
@@ -965,6 +968,9 @@ export class {struct_name.replace("LDK","")} extends CommonBase {{
        /* @internal */
        public bindings_instance?: bindings.{struct_name};
 
+       /* @internal */
+       public instance_idx?: number;
+
        /* @internal */
        constructor(_dummy: object, ptr: bigint) {{
                super(ptr, bindings.{struct_name.replace("LDK","")}_free);
@@ -976,9 +982,10 @@ export class {struct_name.replace("LDK","")} extends CommonBase {{
                const impl_holder: {struct_name}Holder = new {struct_name}Holder();
                let structImplementation = {{
 {out_interface_implementation_overrides}               }} as bindings.{struct_name};
-{super_constructor_statements}         const ptr: bigint = bindings.{struct_name}_new(structImplementation{bindings_instantiator});
+{super_constructor_statements}         const ptr_idx: [bigint, number] = bindings.{struct_name}_new(structImplementation{bindings_instantiator});
 
-               impl_holder.held = new {struct_name.replace("LDK", "")}(null, ptr);
+               impl_holder.held = new {struct_name.replace("LDK", "")}(null, ptr_idx[0]);
+               impl_holder.held.instance_idx = ptr_idx[1];
                impl_holder.held.bindings_instance = structImplementation;
 {pointer_to_adder}             return impl_holder.held;
        }}
@@ -1001,14 +1008,18 @@ export class {struct_name.replace("LDK","")} extends CommonBase {{
 
         out_typescript_bindings += "}\n\n"
 
+        c_call_extra_args = ""
         out_typescript_bindings += f"/* @internal */\nexport function {struct_name}_new(impl: {struct_name}"
         for var in flattened_field_var_conversions:
             if isinstance(var, ConvInfo):
                 out_typescript_bindings += f", {var.arg_name}: {var.java_ty}"
+                c_call_extra_args += f", {var.arg_name}"
             else:
-                out_typescript_bindings += f", {var[1]}: {var[0]}"
+                out_typescript_bindings += f", {var[1]}: number"
+                c_call_extra_args += f", {var[1]}"
+
 
-        out_typescript_bindings += f"""): bigint {{
+        out_typescript_bindings += f"""): [bigint, number] {{
        if(!isWasmInitialized) {{
                throw new Error("initializeWasm() must be awaited first!");
        }}
@@ -1017,7 +1028,7 @@ export class {struct_name.replace("LDK","")} extends CommonBase {{
                if (js_objs[i] == null || js_objs[i] == undefined) {{ new_obj_idx = i; break; }}
        }}
        js_objs[i] = new WeakRef(impl);
-       return wasm.TS_{struct_name}_new(i);
+       return [wasm.TS_{struct_name}_new(i{c_call_extra_args}), i];
 }}
 """
 
@@ -1079,7 +1090,7 @@ export class {struct_name.replace("LDK","")} extends CommonBase {{
                     out_c = out_c + "\tjs_invoke_function_" + fn_suffix + "(j_calls->instance_ptr, " + str(self.function_ptr_counter)
                 elif fn_line.ret_ty_info.java_hu_ty == "string":
                     out_c += "\tjstring ret = (jstring)js_invoke_function_" + fn_suffix + "(j_calls->instance_ptr, " + str(self.function_ptr_counter)
-                elif not fn_line.ret_ty_info.passed_as_ptr:
+                elif fn_line.ret_ty_info.arg_conv is None:
                     out_c += "\treturn js_invoke_function_" + fn_suffix + "(j_calls->instance_ptr, " + str(self.function_ptr_counter)
                 else:
                     out_c += "\tuint64_t ret = js_invoke_function_" + fn_suffix + "(j_calls->instance_ptr, " + str(self.function_ptr_counter)