From 25f36d67bf631de39d5519e096ab83101ada5b21 Mon Sep 17 00:00:00 2001 From: Hossein Yousefi Date: Fri, 29 Nov 2024 21:37:39 +0100 Subject: [PATCH] Generate null-safe Kotlin code (#1758) Now we parse the Kotlin metadata and add a `Nullable` or `NonNull` annotation to each type based on that. Not everything is covered because we simply don't support all Kotlin features. --- pkgs/jnigen/CHANGELOG.md | 2 +- .../kotlin_plugin/example/lib/main.dart | 4 +- .../kotlin_plugin/lib/kotlin_bindings.dart | 12 +- .../apisummarizer/elements/KotlinPackage.java | 3 + .../apisummarizer/elements/KotlinType.java | 4 + .../lib/src/bindings/kotlin_processor.dart | 225 ++- pkgs/jnigen/lib/src/elements/elements.dart | 233 ++- pkgs/jnigen/lib/src/elements/elements.g.dart | 210 ++- .../test/kotlin_test/bindings/kotlin.dart | 1425 +++++++++++++++-- .../github/dart_lang/jnigen/Nullability.kt | 84 + .../kotlin_test/runtime_test_registrant.dart | 217 ++- 11 files changed, 2194 insertions(+), 225 deletions(-) create mode 100644 pkgs/jnigen/test/kotlin_test/kotlin/src/main/kotlin/com/github/dart_lang/jnigen/Nullability.kt diff --git a/pkgs/jnigen/CHANGELOG.md b/pkgs/jnigen/CHANGELOG.md index 7d94206cb..f8408ec7c 100644 --- a/pkgs/jnigen/CHANGELOG.md +++ b/pkgs/jnigen/CHANGELOG.md @@ -1,7 +1,7 @@ ## 0.13.0-wip - **Breaking Change**([#1644](https://github.com/dart-lang/native/issues/1644)): - Generate null-safe Dart bindings. + Generate null-safe Dart bindings for Java and Kotlin. ## 0.12.2 diff --git a/pkgs/jnigen/example/kotlin_plugin/example/lib/main.dart b/pkgs/jnigen/example/kotlin_plugin/example/lib/main.dart index a7e671ef8..84a91337c 100644 --- a/pkgs/jnigen/example/kotlin_plugin/example/lib/main.dart +++ b/pkgs/jnigen/example/kotlin_plugin/example/lib/main.dart @@ -62,8 +62,8 @@ class _MyHomePageState extends State { ElevatedButton( onPressed: () { setState(() { - answer = example.thinkBeforeAnswering().then((value) => - value?.toDartString(releaseOriginal: true) ?? 'null'); + answer = example.thinkBeforeAnswering().then( + (value) => value.toDartString(releaseOriginal: true)); }); }, child: const Text('Think...'), diff --git a/pkgs/jnigen/example/kotlin_plugin/lib/kotlin_bindings.dart b/pkgs/jnigen/example/kotlin_plugin/lib/kotlin_bindings.dart index 60b859b65..fceb46300 100644 --- a/pkgs/jnigen/example/kotlin_plugin/lib/kotlin_bindings.dart +++ b/pkgs/jnigen/example/kotlin_plugin/lib/kotlin_bindings.dart @@ -94,7 +94,7 @@ class Example extends _$jni.JObject { /// from: `public final java.lang.Object thinkBeforeAnswering(kotlin.coroutines.Continuation continuation)` /// The returned object must be released after use, by calling the [release] method. - _$core.Future<_$jni.JString?> thinkBeforeAnswering() async { + _$core.Future<_$jni.JString> thinkBeforeAnswering() async { final $p = _$jni.ReceivePort(); final _$continuation = _$jni.ProtectedJniExtensions.newPortContinuation($p); @@ -102,17 +102,17 @@ class Example extends _$jni.JObject { reference.pointer, _id_thinkBeforeAnswering as _$jni.JMethodIDPtr, _$continuation.pointer) - .object<_$jni.JObject?>(const _$jni.JObjectNullableType()); + .object<_$jni.JObject>(const _$jni.JObjectType()); _$continuation.release(); final $o = _$jni.JGlobalReference(_$jni.JObjectPtr.fromAddress(await $p.first)); - final $k = const _$jni.JStringNullableType().jClass.reference; + final $k = const _$jni.JStringType().jClass.reference; if (!_$jni.Jni.env.IsInstanceOf($o.pointer, $k.pointer)) { $k.release(); throw 'Failed'; } $k.release(); - return const _$jni.JStringNullableType().fromReference($o); + return const _$jni.JStringType().fromReference($o); } } @@ -133,7 +133,7 @@ final class $Example$NullableType extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -168,7 +168,7 @@ final class $Example$Type extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override diff --git a/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinPackage.java b/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinPackage.java index 5252e0071..3610a18aa 100644 --- a/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinPackage.java +++ b/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinPackage.java @@ -6,11 +6,14 @@ public class KotlinPackage { public List functions; + public List properties; public static KotlinPackage fromKmPackage(KmPackage p) { var pkg = new KotlinPackage(); pkg.functions = p.getFunctions().stream().map(KotlinFunction::fromKmFunction).collect(Collectors.toList()); + pkg.properties = + p.getProperties().stream().map(KotlinProperty::fromKmProperty).collect(Collectors.toList()); return pkg; } } diff --git a/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinType.java b/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinType.java index 8e91122ef..69af1b9ee 100644 --- a/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinType.java +++ b/pkgs/jnigen/java/src/main/java/com/github/dart_lang/jnigen/apisummarizer/elements/KotlinType.java @@ -6,6 +6,7 @@ import java.util.List; import java.util.stream.Collectors; +import kotlinx.metadata.Flag; import kotlinx.metadata.KmClassifier; import kotlinx.metadata.KmType; @@ -15,11 +16,14 @@ public class KotlinType { public String name; public int id; public List arguments; + public boolean isNullable; public static KotlinType fromKmType(KmType t) { if (t == null) return null; var type = new KotlinType(); type.flags = t.getFlags(); + // Processing the information needed from the flags. + type.isNullable = Flag.Type.IS_NULLABLE.invoke(type.flags); var classifier = t.getClassifier(); if (classifier instanceof KmClassifier.Class) { type.kind = "class"; diff --git a/pkgs/jnigen/lib/src/bindings/kotlin_processor.dart b/pkgs/jnigen/lib/src/bindings/kotlin_processor.dart index 53de1ed2d..b1539fa94 100644 --- a/pkgs/jnigen/lib/src/bindings/kotlin_processor.dart +++ b/pkgs/jnigen/lib/src/bindings/kotlin_processor.dart @@ -5,6 +5,31 @@ import '../elements/elements.dart'; import 'visitor.dart'; +String _toJavaBinaryName(String kotlinBinaryName) { + final binaryName = + kotlinBinaryName.replaceAll('.', r'$').replaceAll('/', '.'); + return const { + 'kotlin.Any': 'java.lang.Object', + 'kotlin.Byte': 'java.lang.Byte', + 'kotlin.Short': 'java.lang.Short', + 'kotlin.Int': 'java.lang.Integer', + 'kotlin.Long': 'java.lang.Long', + 'kotlin.Char': 'java.lang.Character', + 'kotlin.Float': 'java.lang.Float', + 'kotlin.Double': 'java.lang.Double', + 'kotlin.Boolean': 'java.lang.Boolean', + 'kotlin.Cloneable': 'java.lang.Cloneable', + 'kotlin.Comparable': 'java.lang.Comparable', + 'kotlin.Enum': 'java.lang.Enum', + 'kotlin.Annotation': 'java.lang.annotation.Annotation', + 'kotlin.CharSequence': 'java.lang.CharSequence', + 'kotlin.String': 'java.lang.String', + 'kotlin.Number': 'java.lang.Number', + 'kotlin.Throwable': 'java.lang.Throwable', + }[binaryName] ?? + binaryName; +} + /// A [Visitor] that adds the the information from Kotlin's metadata to the Java /// classes and methods. class KotlinProcessor extends Visitor { @@ -24,6 +49,46 @@ class _KotlinClassProcessor extends Visitor { return; } // This [ClassDecl] is actually a Kotlin class. + if (node.kotlinClass != null) { + for (var i = 0; i < node.kotlinClass!.typeParameters.length; ++i) { + node.typeParams[i].accept( + _KotlinTypeParamProcessor(node.kotlinClass!.typeParameters[i])); + } + if (node.superclass case final superClass?) { + final kotlinSuperTypes = node.kotlinClass!.superTypes.where( + (superType) => + _toJavaBinaryName(superType.name ?? '') == superClass.name, + ); + if (kotlinSuperTypes.isNotEmpty) { + superClass.accept(_KotlinTypeProcessor(kotlinSuperTypes.single)); + } + } + } + + // Matching fields and properties from the metadata. + final properties = {}; + final getters = {}; + final setters = {}; + final kotlinProperties = + (node.kotlinClass?.properties ?? node.kotlinPackage?.properties)!; + for (final property in kotlinProperties) { + if (property.fieldName case final fieldName?) { + properties[fieldName] = property; + } + if (property.getterName case final getterName?) { + final getterSignature = getterName + property.getterDescriptor!; + getters[getterSignature] = property; + } + if (property.setterName case final setterName?) { + final setterSignature = setterName + property.setterDescriptor!; + setters[setterSignature] = property; + } + } + for (final field in node.fields) { + if (properties[field.name] case final property?) { + field.accept(_KotlinPropertyProcessor(property)); + } + } // Matching methods and functions from the metadata. final functions = {}; final kotlinFunctions = @@ -32,15 +97,37 @@ class _KotlinClassProcessor extends Visitor { final signature = function.name + function.descriptor; functions[signature] = function; } + final constructors = {}; + final kotlinConstructors = node.kotlinClass?.constructors ?? []; + for (final constructor in kotlinConstructors) { + final signature = constructor.name + constructor.descriptor; + constructors[signature] = constructor; + } for (final method in node.methods) { final signature = method.name + method.descriptor!; - if (functions.containsKey(signature)) { - method.accept(_KotlinMethodProcessor(functions[signature]!)); + if (functions[signature] case final function?) { + method.accept(_KotlinMethodProcessor(function)); + } else if (constructors[signature] case final constructor?) { + method.accept(_KotlinConstructorProcessor(constructor)); + } else if (getters[signature] case final getter?) { + method.accept(_KotlinGetterProcessor(getter)); + } else if (setters[signature] case final setter?) { + method.accept(_KotlinSetterProcessor(setter)); } } } } +void _processParams( + List params, List kotlinParams) { + if (params.length != kotlinParams.length) { + return; + } + for (var i = 0; i < params.length; ++i) { + params[i].accept(_KotlinParamProcessor(kotlinParams[i])); + } +} + class _KotlinMethodProcessor extends Visitor { final KotlinFunction function; @@ -48,6 +135,11 @@ class _KotlinMethodProcessor extends Visitor { @override void visit(Method node) { + _processParams(node.params, function.valueParameters); + for (var i = 0; i < node.typeParams.length; ++i) { + node.typeParams[i] + .accept(_KotlinTypeParamProcessor(function.typeParameters[i])); + } if (function.isSuspend) { const kotlinContinutationType = 'kotlin.coroutines.Continuation'; assert(node.params.isNotEmpty && @@ -63,6 +155,135 @@ class _KotlinMethodProcessor extends Visitor { node.asyncReturnType = continuationType == null ? TypeUsage.object : continuationType.clone(); + node.asyncReturnType!.accept(_KotlinTypeProcessor(function.returnType)); + + // The continuation object is always non-null. + node.returnType.type.annotations ??= []; + node.returnType.type.annotations!.add(Annotation.nonNull); + } else { + node.returnType.accept(_KotlinTypeProcessor(function.returnType)); + } + } +} + +class _KotlinConstructorProcessor extends Visitor { + final KotlinConstructor constructor; + + _KotlinConstructorProcessor(this.constructor); + + @override + void visit(Method node) { + _processParams(node.params, constructor.valueParameters); + } +} + +class _KotlinGetterProcessor extends Visitor { + final KotlinProperty getter; + + _KotlinGetterProcessor(this.getter); + + @override + void visit(Method node) { + node.returnType.accept(_KotlinTypeProcessor(getter.returnType)); + } +} + +class _KotlinSetterProcessor extends Visitor { + final KotlinProperty setter; + + _KotlinSetterProcessor(this.setter); + + @override + void visit(Method node) { + if (setter.setterParameter case final setterParam?) { + node.params.single.type.accept(_KotlinTypeProcessor(setterParam.type)); } + node.params.single.type.accept(_KotlinTypeProcessor(setter.returnType)); + } +} + +class _KotlinPropertyProcessor extends Visitor { + final KotlinProperty property; + + _KotlinPropertyProcessor(this.property); + + @override + void visit(Field node) { + node.type.accept(_KotlinTypeProcessor(property.returnType)); + } +} + +class _KotlinParamProcessor extends Visitor { + final KotlinValueParameter kotlinParam; + + _KotlinParamProcessor(this.kotlinParam); + + @override + void visit(Param node) { + node.type.accept(_KotlinTypeProcessor(kotlinParam.type)); + } +} + +class _KotlinTypeParamProcessor extends Visitor { + final KotlinTypeParameter kotlinTypeParam; + + _KotlinTypeParamProcessor(this.kotlinTypeParam); + + @override + void visit(TypeParam node) { + final kotlinBounds = kotlinTypeParam.upperBounds; + final bounds = {}; + for (final bound in kotlinBounds) { + if (bound.name case final boundName?) { + bounds[_toJavaBinaryName(boundName)] = bound; + } + } + for (final bound in node.bounds) { + if (bounds[bound.name] case final kotlinBound?) { + bound.accept(_KotlinTypeProcessor(kotlinBound)); + } + } + } +} + +class _KotlinTypeProcessor extends TypeVisitor { + final KotlinType kotlinType; + + _KotlinTypeProcessor(this.kotlinType); + + @override + void visitDeclaredType(DeclaredType node) { + for (var i = 0; i < node.params.length; ++i) { + node.params[i].accept(_KotlinTypeProcessor(kotlinType.arguments[i].type)); + } + super.visitDeclaredType(node); + } + + @override + void visitArrayType(ArrayType node) { + if (kotlinType.arguments.isNotEmpty) { + node.elementType + .accept(_KotlinTypeProcessor(kotlinType.arguments.first.type)); + } + super.visitArrayType(node); + } + + @override + void visitWildcard(Wildcard node) { + node.extendsBound?.accept(_KotlinTypeProcessor(kotlinType)); + node.superBound?.accept(_KotlinTypeProcessor(kotlinType)); + super.visitWildcard(node); + } + + @override + void visitNonPrimitiveType(ReferredType node) { + node.annotations ??= []; + node.annotations! + .add(kotlinType.isNullable ? Annotation.nullable : Annotation.nonNull); + } + + @override + void visitPrimitiveType(PrimitiveType node) { + // Do nothing. } } diff --git a/pkgs/jnigen/lib/src/elements/elements.dart b/pkgs/jnigen/lib/src/elements/elements.dart index 9ab4aa720..cbdbea653 100644 --- a/pkgs/jnigen/lib/src/elements/elements.dart +++ b/pkgs/jnigen/lib/src/elements/elements.dart @@ -21,9 +21,8 @@ abstract class Element> { R accept(Visitor v); } -@JsonEnum() - /// A kind describes the type of a declaration. +@JsonEnum() enum DeclKind { @JsonValue('CLASS') classKind, @@ -915,11 +914,39 @@ class Annotation implements Element { class KotlinClass implements Element { KotlinClass({ required this.name, + required this.moduleName, this.functions = const [], + this.properties = const [], + this.constructors = const [], + this.typeParameters = const [], + this.contextReceiverTypes = const [], + this.superTypes = const [], + this.nestedClasses = const [], + this.enumEntries = const [], + this.sealedClasses = const [], + required this.companionObject, + required this.inlineClassUnderlyingPropertyName, + required this.inlineClassUnderlyingType, + required this.flags, + required this.jvmFlags, }); final String name; + final String moduleName; final List functions; + final List properties; + final List constructors; + final List typeParameters; + final List contextReceiverTypes; + final List superTypes; + final List nestedClasses; + final List enumEntries; + final List sealedClasses; + final String? companionObject; + final String? inlineClassUnderlyingPropertyName; + final KotlinType? inlineClassUnderlyingType; + final int flags; + final int jvmFlags; factory KotlinClass.fromJson(Map json) => _$KotlinClassFromJson(json); @@ -934,9 +961,11 @@ class KotlinClass implements Element { class KotlinPackage implements Element { KotlinPackage({ this.functions = const [], + this.properties = const [], }); final List functions; + final List properties; factory KotlinPackage.fromJson(Map json) => _$KotlinPackageFromJson(json); @@ -948,28 +977,216 @@ class KotlinPackage implements Element { } @JsonSerializable(createToJson: false) -class KotlinFunction implements Element { +class KotlinFunction { KotlinFunction({ required this.name, required this.descriptor, required this.kotlinName, + this.valueParameters = const [], + required this.returnType, + this.receiverParameterType, + this.contextReceiverTypes = const [], + this.typeParameters = const [], + required this.flags, required this.isSuspend, }); + /// Name in the byte code. final String name; - - /// Used to match with [Method]'s descriptor. - /// - /// Creates a unique signature in combination with [name]. final String descriptor; + + /// Name in the Kotlin's metadata. final String kotlinName; + + final List valueParameters; + final KotlinType returnType; + final KotlinType? receiverParameterType; + final List contextReceiverTypes; + final List typeParameters; + final int flags; final bool isSuspend; factory KotlinFunction.fromJson(Map json) => _$KotlinFunctionFromJson(json); +} + +@JsonSerializable(createToJson: false) +class KotlinConstructor implements Element { + KotlinConstructor({ + required this.name, + required this.descriptor, + this.valueParameters = const [], + required this.flags, + }); + + final String name; + final String descriptor; + final List valueParameters; + final int flags; + + factory KotlinConstructor.fromJson(Map json) => + _$KotlinConstructorFromJson(json); + + @override + R accept(Visitor v) { + return v.visit(this); + } +} + +@JsonSerializable(createToJson: false) +class KotlinProperty implements Element { + KotlinProperty({ + this.fieldName, + this.fieldDescriptor, + this.getterName, + this.getterDescriptor, + this.setterName, + this.setterDescriptor, + required this.kotlinName, + required this.returnType, + required this.receiverParameterType, + this.contextReceiverTypes = const [], + required this.jvmFlags, + required this.flags, + required this.setterFlags, + required this.getterFlags, + this.typeParameters = const [], + required this.setterParameter, + }); + + final String? fieldName; + final String? fieldDescriptor; + + /// Getter's name in the byte code. + final String? getterName; + final String? getterDescriptor; + + /// Setter's name in the byte code. + final String? setterName; + final String? setterDescriptor; + + /// Name in the Kotlin's metadata. + final String kotlinName; + + final KotlinType returnType; + final KotlinType? receiverParameterType; + final List contextReceiverTypes; + final int jvmFlags; + final int flags; + final int setterFlags; + final int getterFlags; + final List typeParameters; + final KotlinValueParameter? setterParameter; + + factory KotlinProperty.fromJson(Map json) => + _$KotlinPropertyFromJson(json); + + @override + R accept(Visitor v) { + return v.visit(this); + } +} + +@JsonSerializable(createToJson: false) +class KotlinType implements Element { + KotlinType({ + required this.flags, + required this.kind, + required this.name, + required this.id, + required this.isNullable, + this.arguments = const [], + }); + + final int flags; + final String kind; + final String? name; + final int id; + final List arguments; + final bool isNullable; + + factory KotlinType.fromJson(Map json) => + _$KotlinTypeFromJson(json); + + @override + R accept(Visitor v) { + return v.visit(this); + } +} + +@JsonEnum() +enum KmVariance { + @JsonValue('INVARIANT') + invariant, + @JsonValue('IN') + contravariant, + @JsonValue('OUT') + covariant, +} + +@JsonSerializable(createToJson: false) +class KotlinTypeParameter implements Element { + KotlinTypeParameter({ + required this.name, + required this.id, + required this.flags, + this.upperBounds = const [], + required this.variance, + }); + + final String name; + final int id; + final int flags; + final List upperBounds; + final KmVariance variance; + + factory KotlinTypeParameter.fromJson(Map json) => + _$KotlinTypeParameterFromJson(json); + + @override + R accept(Visitor v) { + return v.visit(this); + } +} + +@JsonSerializable(createToJson: false) +class KotlinValueParameter implements Element { + KotlinValueParameter({ + required this.name, + required this.flags, + required this.type, + required this.varargElementType, + }); + + final String name; + final int flags; + final KotlinType type; + final KotlinType? varargElementType; + + factory KotlinValueParameter.fromJson(Map json) => + _$KotlinValueParameterFromJson(json); + + @override + R accept(Visitor v) { + return v.visit(this); + } +} + +@JsonSerializable(createToJson: false) +class KotlinTypeProjection implements Element { + KotlinTypeProjection({ + required this.type, + required this.variance, + }); + + final KotlinType type; + final KmVariance variance; + + factory KotlinTypeProjection.fromJson(Map json) => + _$KotlinTypeProjectionFromJson(json); @override - R accept(Visitor v) { + R accept(Visitor v) { return v.visit(this); } } diff --git a/pkgs/jnigen/lib/src/elements/elements.g.dart b/pkgs/jnigen/lib/src/elements/elements.g.dart index e981d2054..180741d65 100644 --- a/pkgs/jnigen/lib/src/elements/elements.g.dart +++ b/pkgs/jnigen/lib/src/elements/elements.g.dart @@ -8,9 +8,8 @@ part of 'elements.dart'; ClassDecl _$ClassDeclFromJson(Map json) => ClassDecl( annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), javadoc: json['javadoc'] == null ? null : JavaDocComment.fromJson(json['javadoc'] as Map), @@ -76,9 +75,8 @@ const _$KindEnumMap = { DeclaredType _$DeclaredTypeFromJson(Map json) => DeclaredType( binaryName: json['binaryName'] as String, annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), params: (json['params'] as List?) ?.map((e) => TypeUsage.fromJson(e as Map)) .toList() ?? @@ -88,9 +86,8 @@ DeclaredType _$DeclaredTypeFromJson(Map json) => DeclaredType( TypeVar _$TypeVarFromJson(Map json) => TypeVar( name: json['name'] as String, annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), ); Wildcard _$WildcardFromJson(Map json) => Wildcard( @@ -101,25 +98,22 @@ Wildcard _$WildcardFromJson(Map json) => Wildcard( ? null : TypeUsage.fromJson(json['superBound'] as Map), annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), ); ArrayType _$ArrayTypeFromJson(Map json) => ArrayType( elementType: TypeUsage.fromJson(json['elementType'] as Map), annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), ); Method _$MethodFromJson(Map json) => Method( annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), javadoc: json['javadoc'] == null ? null : JavaDocComment.fromJson(json['javadoc'] as Map), @@ -143,9 +137,8 @@ Method _$MethodFromJson(Map json) => Method( Param _$ParamFromJson(Map json) => Param( annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), javadoc: json['javadoc'] == null ? null : JavaDocComment.fromJson(json['javadoc'] as Map), @@ -155,9 +148,8 @@ Param _$ParamFromJson(Map json) => Param( Field _$FieldFromJson(Map json) => Field( annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), javadoc: json['javadoc'] == null ? null : JavaDocComment.fromJson(json['javadoc'] as Map), @@ -177,9 +169,8 @@ TypeParam _$TypeParamFromJson(Map json) => TypeParam( .toList() ?? const [], annotations: (json['annotations'] as List?) - ?.map((e) => Annotation.fromJson(e as Map)) - .toList() ?? - const [], + ?.map((e) => Annotation.fromJson(e as Map)) + .toList(), ); JavaDocComment _$JavaDocCommentFromJson(Map json) => @@ -200,10 +191,54 @@ Annotation _$AnnotationFromJson(Map json) => Annotation( KotlinClass _$KotlinClassFromJson(Map json) => KotlinClass( name: json['name'] as String, + moduleName: json['moduleName'] as String, functions: (json['functions'] as List?) ?.map((e) => KotlinFunction.fromJson(e as Map)) .toList() ?? const [], + properties: (json['properties'] as List?) + ?.map((e) => KotlinProperty.fromJson(e as Map)) + .toList() ?? + const [], + constructors: (json['constructors'] as List?) + ?.map( + (e) => KotlinConstructor.fromJson(e as Map)) + .toList() ?? + const [], + typeParameters: (json['typeParameters'] as List?) + ?.map((e) => + KotlinTypeParameter.fromJson(e as Map)) + .toList() ?? + const [], + contextReceiverTypes: (json['contextReceiverTypes'] as List?) + ?.map((e) => KotlinType.fromJson(e as Map)) + .toList() ?? + const [], + superTypes: (json['superTypes'] as List?) + ?.map((e) => KotlinType.fromJson(e as Map)) + .toList() ?? + const [], + nestedClasses: (json['nestedClasses'] as List?) + ?.map((e) => e as String) + .toList() ?? + const [], + enumEntries: (json['enumEntries'] as List?) + ?.map((e) => e as String) + .toList() ?? + const [], + sealedClasses: (json['sealedClasses'] as List?) + ?.map((e) => e as String) + .toList() ?? + const [], + companionObject: json['companionObject'] as String?, + inlineClassUnderlyingPropertyName: + json['inlineClassUnderlyingPropertyName'] as String?, + inlineClassUnderlyingType: json['inlineClassUnderlyingType'] == null + ? null + : KotlinType.fromJson( + json['inlineClassUnderlyingType'] as Map), + flags: (json['flags'] as num).toInt(), + jvmFlags: (json['jvmFlags'] as num).toInt(), ); KotlinPackage _$KotlinPackageFromJson(Map json) => @@ -212,6 +247,10 @@ KotlinPackage _$KotlinPackageFromJson(Map json) => ?.map((e) => KotlinFunction.fromJson(e as Map)) .toList() ?? const [], + properties: (json['properties'] as List?) + ?.map((e) => KotlinProperty.fromJson(e as Map)) + .toList() ?? + const [], ); KotlinFunction _$KotlinFunctionFromJson(Map json) => @@ -219,5 +258,122 @@ KotlinFunction _$KotlinFunctionFromJson(Map json) => name: json['name'] as String, descriptor: json['descriptor'] as String, kotlinName: json['kotlinName'] as String, + valueParameters: (json['valueParameters'] as List?) + ?.map((e) => + KotlinValueParameter.fromJson(e as Map)) + .toList() ?? + const [], + returnType: + KotlinType.fromJson(json['returnType'] as Map), + receiverParameterType: json['receiverParameterType'] == null + ? null + : KotlinType.fromJson( + json['receiverParameterType'] as Map), + contextReceiverTypes: (json['contextReceiverTypes'] as List?) + ?.map((e) => KotlinType.fromJson(e as Map)) + .toList() ?? + const [], + typeParameters: (json['typeParameters'] as List?) + ?.map((e) => + KotlinTypeParameter.fromJson(e as Map)) + .toList() ?? + const [], + flags: (json['flags'] as num).toInt(), isSuspend: json['isSuspend'] as bool, ); + +KotlinConstructor _$KotlinConstructorFromJson(Map json) => + KotlinConstructor( + name: json['name'] as String, + descriptor: json['descriptor'] as String, + valueParameters: (json['valueParameters'] as List?) + ?.map((e) => + KotlinValueParameter.fromJson(e as Map)) + .toList() ?? + const [], + flags: (json['flags'] as num).toInt(), + ); + +KotlinProperty _$KotlinPropertyFromJson(Map json) => + KotlinProperty( + fieldName: json['fieldName'] as String?, + fieldDescriptor: json['fieldDescriptor'] as String?, + getterName: json['getterName'] as String?, + getterDescriptor: json['getterDescriptor'] as String?, + setterName: json['setterName'] as String?, + setterDescriptor: json['setterDescriptor'] as String?, + kotlinName: json['kotlinName'] as String, + returnType: + KotlinType.fromJson(json['returnType'] as Map), + receiverParameterType: json['receiverParameterType'] == null + ? null + : KotlinType.fromJson( + json['receiverParameterType'] as Map), + contextReceiverTypes: (json['contextReceiverTypes'] as List?) + ?.map((e) => KotlinType.fromJson(e as Map)) + .toList() ?? + const [], + jvmFlags: (json['jvmFlags'] as num).toInt(), + flags: (json['flags'] as num).toInt(), + setterFlags: (json['setterFlags'] as num).toInt(), + getterFlags: (json['getterFlags'] as num).toInt(), + typeParameters: (json['typeParameters'] as List?) + ?.map((e) => + KotlinTypeParameter.fromJson(e as Map)) + .toList() ?? + const [], + setterParameter: json['setterParameter'] == null + ? null + : KotlinValueParameter.fromJson( + json['setterParameter'] as Map), + ); + +KotlinType _$KotlinTypeFromJson(Map json) => KotlinType( + flags: (json['flags'] as num).toInt(), + kind: json['kind'] as String, + name: json['name'] as String?, + id: (json['id'] as num).toInt(), + isNullable: json['isNullable'] as bool, + arguments: (json['arguments'] as List?) + ?.map((e) => + KotlinTypeProjection.fromJson(e as Map)) + .toList() ?? + const [], + ); + +KotlinTypeParameter _$KotlinTypeParameterFromJson(Map json) => + KotlinTypeParameter( + name: json['name'] as String, + id: (json['id'] as num).toInt(), + flags: (json['flags'] as num).toInt(), + upperBounds: (json['upperBounds'] as List?) + ?.map((e) => KotlinType.fromJson(e as Map)) + .toList() ?? + const [], + variance: $enumDecode(_$KmVarianceEnumMap, json['variance']), + ); + +const _$KmVarianceEnumMap = { + KmVariance.invariant: 'INVARIANT', + KmVariance.contravariant: 'IN', + KmVariance.covariant: 'OUT', +}; + +KotlinValueParameter _$KotlinValueParameterFromJson( + Map json) => + KotlinValueParameter( + name: json['name'] as String, + flags: (json['flags'] as num).toInt(), + type: KotlinType.fromJson(json['type'] as Map), + varargElementType: json['varargElementType'] == null + ? null + : KotlinType.fromJson( + json['varargElementType'] as Map), + ); + +KotlinTypeProjection _$KotlinTypeProjectionFromJson( + Map json) => + KotlinTypeProjection( + type: KotlinType.fromJson(json['type'] as Map), + variance: $enumDecode(_$KmVarianceEnumMap, json['variance']), + ); diff --git a/pkgs/jnigen/test/kotlin_test/bindings/kotlin.dart b/pkgs/jnigen/test/kotlin_test/bindings/kotlin.dart index 42b7ca029..d6769f1aa 100644 --- a/pkgs/jnigen/test/kotlin_test/bindings/kotlin.dart +++ b/pkgs/jnigen/test/kotlin_test/bindings/kotlin.dart @@ -40,7 +40,7 @@ import 'package:jni/_internal.dart' as _$jni; import 'package:jni/jni.dart' as _$jni; /// from: `com.github.dart_lang.jnigen.Measure` -class Measure<$T extends _$jni.JObject?> extends _$jni.JObject { +class Measure<$T extends _$jni.JObject> extends _$jni.JObject { @_$jni.internal @_$core.override final _$jni.JObjType> $type; @@ -59,7 +59,7 @@ class Measure<$T extends _$jni.JObject?> extends _$jni.JObject { _$jni.JClass.forName(r'com/github/dart_lang/jnigen/Measure'); /// The type which includes information such as the signature of this class. - static $Measure$NullableType<$T> nullableType<$T extends _$jni.JObject?>( + static $Measure$NullableType<$T> nullableType<$T extends _$jni.JObject>( _$jni.JObjType<$T> T, ) { return $Measure$NullableType<$T>( @@ -67,7 +67,7 @@ class Measure<$T extends _$jni.JObject?> extends _$jni.JObject { ); } - static $Measure$Type<$T> type<$T extends _$jni.JObject?>( + static $Measure$Type<$T> type<$T extends _$jni.JObject>( _$jni.JObjType<$T> T, ) { return $Measure$Type<$T>( @@ -117,9 +117,9 @@ class Measure<$T extends _$jni.JObject?> extends _$jni.JObject { /// from: `public T getUnit()` /// The returned object must be released after use, by calling the [release] method. - $T? getUnit() { + $T getUnit() { return _getUnit(reference.pointer, _id_getUnit as _$jni.JMethodIDPtr) - .object<$T?>(T.nullableType); + .object<$T>(T); } static final _id_convertValue = _class.instanceMethodId( @@ -140,16 +140,16 @@ class Measure<$T extends _$jni.JObject?> extends _$jni.JObject { /// from: `public final float convertValue(T measureUnit)` double convertValue( - $T? measureUnit, + $T measureUnit, ) { - final _$measureUnit = measureUnit?.reference ?? _$jni.jNullReference; + final _$measureUnit = measureUnit.reference; return _convertValue(reference.pointer, _id_convertValue as _$jni.JMethodIDPtr, _$measureUnit.pointer) .float; } } -final class $Measure$NullableType<$T extends _$jni.JObject?> +final class $Measure$NullableType<$T extends _$jni.JObject> extends _$jni.JObjType?> { @_$jni.internal final _$jni.JObjType<$T> T; @@ -173,7 +173,7 @@ final class $Measure$NullableType<$T extends _$jni.JObject?> ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -194,7 +194,7 @@ final class $Measure$NullableType<$T extends _$jni.JObject?> } } -final class $Measure$Type<$T extends _$jni.JObject?> +final class $Measure$Type<$T extends _$jni.JObject> extends _$jni.JObjType> { @_$jni.internal final _$jni.JObjType<$T> T; @@ -217,7 +217,7 @@ final class $Measure$Type<$T extends _$jni.JObject?> ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -275,224 +275,1299 @@ class MeasureUnit extends _$jni.JObject { /// from: `public abstract java.lang.String getSign()` /// The returned object must be released after use, by calling the [release] method. - _$jni.JString? getSign() { + _$jni.JString getSign() { return _getSign(reference.pointer, _id_getSign as _$jni.JMethodIDPtr) + .object<_$jni.JString>(const _$jni.JStringType()); + } + + static final _id_getCoefficient = _class.instanceMethodId( + r'getCoefficient', + r'()F', + ); + + static final _getCoefficient = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>>('globalEnv_CallFloatMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>(); + + /// from: `public abstract float getCoefficient()` + double getCoefficient() { + return _getCoefficient( + reference.pointer, _id_getCoefficient as _$jni.JMethodIDPtr) + .float; + } + + /// Maps a specific port to the implemented interface. + static final _$core.Map _$impls = {}; + static _$jni.JObjectPtr _$invoke( + int port, + _$jni.JObjectPtr descriptor, + _$jni.JObjectPtr args, + ) { + return _$invokeMethod( + port, + _$jni.MethodInvocation.fromAddresses( + 0, + descriptor.address, + args.address, + ), + ); + } + + static final _$jni.Pointer< + _$jni.NativeFunction< + _$jni.JObjectPtr Function( + _$jni.Int64, _$jni.JObjectPtr, _$jni.JObjectPtr)>> + _$invokePointer = _$jni.Pointer.fromFunction(_$invoke); + + static _$jni.Pointer<_$jni.Void> _$invokeMethod( + int $p, + _$jni.MethodInvocation $i, + ) { + try { + final $d = $i.methodDescriptor.toDartString(releaseOriginal: true); + final $a = $i.args; + if ($d == r'getSign()Ljava/lang/String;') { + final $r = _$impls[$p]!.getSign(); + return ($r as _$jni.JObject?) + ?.as(const _$jni.JObjectType()) + .reference + .toPointer() ?? + _$jni.nullptr; + } + if ($d == r'getCoefficient()F') { + final $r = _$impls[$p]!.getCoefficient(); + return _$jni.JFloat($r).reference.toPointer(); + } + } catch (e) { + return _$jni.ProtectedJniExtensions.newDartException(e); + } + return _$jni.nullptr; + } + + static void implementIn( + _$jni.JImplementer implementer, + $MeasureUnit $impl, + ) { + late final _$jni.RawReceivePort $p; + $p = _$jni.RawReceivePort(($m) { + if ($m == null) { + _$impls.remove($p.sendPort.nativePort); + $p.close(); + return; + } + final $i = _$jni.MethodInvocation.fromMessage($m); + final $r = _$invokeMethod($p.sendPort.nativePort, $i); + _$jni.ProtectedJniExtensions.returnResult($i.result, $r); + }); + implementer.add( + r'com.github.dart_lang.jnigen.MeasureUnit', + $p, + _$invokePointer, + [], + ); + final $a = $p.sendPort.nativePort; + _$impls[$a] = $impl; + } + + factory MeasureUnit.implement( + $MeasureUnit $impl, + ) { + final $i = _$jni.JImplementer(); + implementIn($i, $impl); + return MeasureUnit.fromReference( + $i.implementReference(), + ); + } +} + +abstract base mixin class $MeasureUnit { + factory $MeasureUnit({ + required _$jni.JString Function() getSign, + required double Function() getCoefficient, + }) = _$MeasureUnit; + + _$jni.JString getSign(); + double getCoefficient(); +} + +final class _$MeasureUnit with $MeasureUnit { + _$MeasureUnit({ + required _$jni.JString Function() getSign, + required double Function() getCoefficient, + }) : _getSign = getSign, + _getCoefficient = getCoefficient; + + final _$jni.JString Function() _getSign; + final double Function() _getCoefficient; + + _$jni.JString getSign() { + return _getSign(); + } + + double getCoefficient() { + return _getCoefficient(); + } +} + +final class $MeasureUnit$NullableType extends _$jni.JObjType { + @_$jni.internal + const $MeasureUnit$NullableType(); + + @_$jni.internal + @_$core.override + String get signature => r'Lcom/github/dart_lang/jnigen/MeasureUnit;'; + + @_$jni.internal + @_$core.override + MeasureUnit? fromReference(_$jni.JReference reference) => reference.isNull + ? null + : MeasureUnit.fromReference( + reference, + ); + @_$jni.internal + @_$core.override + _$jni.JObjType get superType => const _$jni.JObjectType(); + + @_$jni.internal + @_$core.override + _$jni.JObjType get nullableType => this; + + @_$jni.internal + @_$core.override + final superCount = 1; + + @_$core.override + int get hashCode => ($MeasureUnit$NullableType).hashCode; + + @_$core.override + bool operator ==(Object other) { + return other.runtimeType == ($MeasureUnit$NullableType) && + other is $MeasureUnit$NullableType; + } +} + +final class $MeasureUnit$Type extends _$jni.JObjType { + @_$jni.internal + const $MeasureUnit$Type(); + + @_$jni.internal + @_$core.override + String get signature => r'Lcom/github/dart_lang/jnigen/MeasureUnit;'; + + @_$jni.internal + @_$core.override + MeasureUnit fromReference(_$jni.JReference reference) => + MeasureUnit.fromReference( + reference, + ); + @_$jni.internal + @_$core.override + _$jni.JObjType get superType => const _$jni.JObjectType(); + + @_$jni.internal + @_$core.override + _$jni.JObjType get nullableType => + const $MeasureUnit$NullableType(); + + @_$jni.internal + @_$core.override + final superCount = 1; + + @_$core.override + int get hashCode => ($MeasureUnit$Type).hashCode; + + @_$core.override + bool operator ==(Object other) { + return other.runtimeType == ($MeasureUnit$Type) && + other is $MeasureUnit$Type; + } +} + +/// from: `com.github.dart_lang.jnigen.Nullability$InnerClass` +class Nullability_InnerClass<$T extends _$jni.JObject?, + $U extends _$jni.JObject, $V extends _$jni.JObject?> extends _$jni.JObject { + @_$jni.internal + @_$core.override + final _$jni.JObjType> $type; + + @_$jni.internal + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + final _$jni.JObjType<$V> V; + + @_$jni.internal + Nullability_InnerClass.fromReference( + this.T, + this.U, + this.V, + _$jni.JReference reference, + ) : $type = type<$T, $U, $V>(T, U, V), + super.fromReference(reference); + + static final _class = _$jni.JClass.forName( + r'com/github/dart_lang/jnigen/Nullability$InnerClass'); + + /// The type which includes information such as the signature of this class. + static $Nullability_InnerClass$NullableType<$T, $U, $V> nullableType< + $T extends _$jni.JObject?, + $U extends _$jni.JObject, + $V extends _$jni.JObject?>( + _$jni.JObjType<$T> T, + _$jni.JObjType<$U> U, + _$jni.JObjType<$V> V, + ) { + return $Nullability_InnerClass$NullableType<$T, $U, $V>( + T, + U, + V, + ); + } + + static $Nullability_InnerClass$Type<$T, $U, $V> type< + $T extends _$jni.JObject?, + $U extends _$jni.JObject, + $V extends _$jni.JObject?>( + _$jni.JObjType<$T> T, + _$jni.JObjType<$U> U, + _$jni.JObjType<$V> V, + ) { + return $Nullability_InnerClass$Type<$T, $U, $V>( + T, + U, + V, + ); + } + + static final _id_new$ = _class.constructorId( + r'(Lcom/github/dart_lang/jnigen/Nullability;)V', + ); + + static final _new$ = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_NewObject') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public void (com.github.dart_lang.jnigen.Nullability $outerClass)` + /// The returned object must be released after use, by calling the [release] method. + factory Nullability_InnerClass( + Nullability<$T?, $U> $outerClass, { + _$jni.JObjType<$T>? T, + _$jni.JObjType<$U>? U, + required _$jni.JObjType<$V> V, + }) { + T ??= _$jni.lowestCommonSuperType([ + ($outerClass.$type as $Nullability$Type<_$core.dynamic, _$core.dynamic>) + .T, + ]) as _$jni.JObjType<$T>; + U ??= _$jni.lowestCommonSuperType([ + ($outerClass.$type as $Nullability$Type<_$core.dynamic, _$core.dynamic>) + .U, + ]) as _$jni.JObjType<$U>; + final _$$outerClass = $outerClass.reference; + return Nullability_InnerClass<$T, $U, $V>.fromReference( + T, + U, + V, + _new$(_class.reference.pointer, _id_new$ as _$jni.JMethodIDPtr, + _$$outerClass.pointer) + .reference); + } + + static final _id_f = _class.instanceMethodId( + r'f', + r'(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V', + ); + + static final _f = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JThrowablePtr Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs< + ( + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void> + )>)>>('globalEnv_CallVoidMethod') + .asFunction< + _$jni.JThrowablePtr Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final void f(T object, U object1, V object2)` + void f( + $T object, + $U object1, + $V object2, + ) { + final _$object = object?.reference ?? _$jni.jNullReference; + final _$object1 = object1.reference; + final _$object2 = object2?.reference ?? _$jni.jNullReference; + _f(reference.pointer, _id_f as _$jni.JMethodIDPtr, _$object.pointer, + _$object1.pointer, _$object2.pointer) + .check(); + } +} + +final class $Nullability_InnerClass$NullableType<$T extends _$jni.JObject?, + $U extends _$jni.JObject, $V extends _$jni.JObject?> + extends _$jni.JObjType?> { + @_$jni.internal + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + final _$jni.JObjType<$V> V; + + @_$jni.internal + const $Nullability_InnerClass$NullableType( + this.T, + this.U, + this.V, + ); + + @_$jni.internal + @_$core.override + String get signature => + r'Lcom/github/dart_lang/jnigen/Nullability$InnerClass;'; + + @_$jni.internal + @_$core.override + Nullability_InnerClass<$T, $U, $V>? fromReference( + _$jni.JReference reference) => + reference.isNull + ? null + : Nullability_InnerClass<$T, $U, $V>.fromReference( + T, + U, + V, + reference, + ); + @_$jni.internal + @_$core.override + _$jni.JObjType get superType => const _$jni.JObjectType(); + + @_$jni.internal + @_$core.override + _$jni.JObjType?> get nullableType => this; + + @_$jni.internal + @_$core.override + final superCount = 1; + + @_$core.override + int get hashCode => + Object.hash($Nullability_InnerClass$NullableType, T, U, V); + + @_$core.override + bool operator ==(Object other) { + return other.runtimeType == + ($Nullability_InnerClass$NullableType<$T, $U, $V>) && + other is $Nullability_InnerClass$NullableType<$T, $U, $V> && + T == other.T && + U == other.U && + V == other.V; + } +} + +final class $Nullability_InnerClass$Type<$T extends _$jni.JObject?, + $U extends _$jni.JObject, $V extends _$jni.JObject?> + extends _$jni.JObjType> { + @_$jni.internal + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + final _$jni.JObjType<$V> V; + + @_$jni.internal + const $Nullability_InnerClass$Type( + this.T, + this.U, + this.V, + ); + + @_$jni.internal + @_$core.override + String get signature => + r'Lcom/github/dart_lang/jnigen/Nullability$InnerClass;'; + + @_$jni.internal + @_$core.override + Nullability_InnerClass<$T, $U, $V> fromReference( + _$jni.JReference reference) => + Nullability_InnerClass<$T, $U, $V>.fromReference( + T, + U, + V, + reference, + ); + @_$jni.internal + @_$core.override + _$jni.JObjType get superType => const _$jni.JObjectType(); + + @_$jni.internal + @_$core.override + _$jni.JObjType?> get nullableType => + $Nullability_InnerClass$NullableType<$T, $U, $V>(T, U, V); + + @_$jni.internal + @_$core.override + final superCount = 1; + + @_$core.override + int get hashCode => Object.hash($Nullability_InnerClass$Type, T, U, V); + + @_$core.override + bool operator ==(Object other) { + return other.runtimeType == ($Nullability_InnerClass$Type<$T, $U, $V>) && + other is $Nullability_InnerClass$Type<$T, $U, $V> && + T == other.T && + U == other.U && + V == other.V; + } +} + +/// from: `com.github.dart_lang.jnigen.Nullability` +class Nullability<$T extends _$jni.JObject?, $U extends _$jni.JObject> + extends _$jni.JObject { + @_$jni.internal + @_$core.override + final _$jni.JObjType> $type; + + @_$jni.internal + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + Nullability.fromReference( + this.T, + this.U, + _$jni.JReference reference, + ) : $type = type<$T, $U>(T, U), + super.fromReference(reference); + + static final _class = + _$jni.JClass.forName(r'com/github/dart_lang/jnigen/Nullability'); + + /// The type which includes information such as the signature of this class. + static $Nullability$NullableType<$T, $U> + nullableType<$T extends _$jni.JObject?, $U extends _$jni.JObject>( + _$jni.JObjType<$T> T, + _$jni.JObjType<$U> U, + ) { + return $Nullability$NullableType<$T, $U>( + T, + U, + ); + } + + static $Nullability$Type<$T, $U> + type<$T extends _$jni.JObject?, $U extends _$jni.JObject>( + _$jni.JObjType<$T> T, + _$jni.JObjType<$U> U, + ) { + return $Nullability$Type<$T, $U>( + T, + U, + ); + } + + static final _id_new$ = _class.constructorId( + r'(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V', + ); + + static final _new$ = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs< + ( + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void> + )>)>>('globalEnv_NewObject') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>, + _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public void (T object, U object1, U object2)` + /// The returned object must be released after use, by calling the [release] method. + factory Nullability( + $T object, + $U object1, + $U? object2, { + required _$jni.JObjType<$T> T, + _$jni.JObjType<$U>? U, + }) { + U ??= _$jni.lowestCommonSuperType([ + object1.$type, + ]) as _$jni.JObjType<$U>; + final _$object = object?.reference ?? _$jni.jNullReference; + final _$object1 = object1.reference; + final _$object2 = object2?.reference ?? _$jni.jNullReference; + return Nullability<$T, $U>.fromReference( + T, + U, + _new$(_class.reference.pointer, _id_new$ as _$jni.JMethodIDPtr, + _$object.pointer, _$object1.pointer, _$object2.pointer) + .reference); + } + + static final _id_getT = _class.instanceMethodId( + r'getT', + r'()Ljava/lang/Object;', + ); + + static final _getT = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>>('globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>(); + + /// from: `public final T getT()` + /// The returned object must be released after use, by calling the [release] method. + $T getT() { + return _getT(reference.pointer, _id_getT as _$jni.JMethodIDPtr) + .object<$T>(T); + } + + static final _id_getU = _class.instanceMethodId( + r'getU', + r'()Ljava/lang/Object;', + ); + + static final _getU = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>>('globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>(); + + /// from: `public final U getU()` + /// The returned object must be released after use, by calling the [release] method. + $U getU() { + return _getU(reference.pointer, _id_getU as _$jni.JMethodIDPtr) + .object<$U>(U); + } + + static final _id_getNullableU = _class.instanceMethodId( + r'getNullableU', + r'()Ljava/lang/Object;', + ); + + static final _getNullableU = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>>('globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>(); + + /// from: `public final U getNullableU()` + /// The returned object must be released after use, by calling the [release] method. + $U? getNullableU() { + return _getNullableU( + reference.pointer, _id_getNullableU as _$jni.JMethodIDPtr) + .object<$U?>(U.nullableType); + } + + static final _id_setNullableU = _class.instanceMethodId( + r'setNullableU', + r'(Ljava/lang/Object;)V', + ); + + static final _setNullableU = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JThrowablePtr Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallVoidMethod') + .asFunction< + _$jni.JThrowablePtr Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final void setNullableU(U object)` + void setNullableU( + $U? object, + ) { + final _$object = object?.reference ?? _$jni.jNullReference; + _setNullableU(reference.pointer, _id_setNullableU as _$jni.JMethodIDPtr, + _$object.pointer) + .check(); + } + + static final _id_hello = _class.instanceMethodId( + r'hello', + r'()Ljava/lang/String;', + ); + + static final _hello = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>>('globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + )>(); + + /// from: `public final java.lang.String hello()` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JString hello() { + return _hello(reference.pointer, _id_hello as _$jni.JMethodIDPtr) + .object<_$jni.JString>(const _$jni.JStringType()); + } + + static final _id_nullableHello = _class.instanceMethodId( + r'nullableHello', + r'(Z)Ljava/lang/String;', + ); + + static final _nullableHello = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Int32,)>)>>('globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, _$jni.JMethodIDPtr, int)>(); + + /// from: `public final java.lang.String nullableHello(boolean z)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JString? nullableHello( + bool z, + ) { + return _nullableHello(reference.pointer, + _id_nullableHello as _$jni.JMethodIDPtr, z ? 1 : 0) + .object<_$jni.JString?>(const _$jni.JStringNullableType()); + } + + static final _id_methodGenericEcho = _class.instanceMethodId( + r'methodGenericEcho', + r'(Ljava/lang/Object;)Ljava/lang/Object;', + ); + + static final _methodGenericEcho = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final V methodGenericEcho(V object)` + /// The returned object must be released after use, by calling the [release] method. + $V methodGenericEcho<$V extends _$jni.JObject>( + $V object, { + _$jni.JObjType<$V>? V, + }) { + V ??= _$jni.lowestCommonSuperType([ + object.$type, + ]) as _$jni.JObjType<$V>; + final _$object = object.reference; + return _methodGenericEcho(reference.pointer, + _id_methodGenericEcho as _$jni.JMethodIDPtr, _$object.pointer) + .object<$V>(V); + } + + static final _id_methodGenericNullableEcho = _class.instanceMethodId( + r'methodGenericNullableEcho', + r'(Ljava/lang/Object;)Ljava/lang/Object;', + ); + + static final _methodGenericNullableEcho = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final V methodGenericNullableEcho(V object)` + /// The returned object must be released after use, by calling the [release] method. + $V methodGenericNullableEcho<$V extends _$jni.JObject?>( + $V object, { + required _$jni.JObjType<$V> V, + }) { + final _$object = object?.reference ?? _$jni.jNullReference; + return _methodGenericNullableEcho( + reference.pointer, + _id_methodGenericNullableEcho as _$jni.JMethodIDPtr, + _$object.pointer) + .object<$V>(V); + } + + static final _id_classGenericEcho = _class.instanceMethodId( + r'classGenericEcho', + r'(Ljava/lang/Object;)Ljava/lang/Object;', + ); + + static final _classGenericEcho = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final U classGenericEcho(U object)` + /// The returned object must be released after use, by calling the [release] method. + $U classGenericEcho( + $U object, + ) { + final _$object = object.reference; + return _classGenericEcho(reference.pointer, + _id_classGenericEcho as _$jni.JMethodIDPtr, _$object.pointer) + .object<$U>(U); + } + + static final _id_classGenericNullableEcho = _class.instanceMethodId( + r'classGenericNullableEcho', + r'(Ljava/lang/Object;)Ljava/lang/Object;', + ); + + static final _classGenericNullableEcho = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final T classGenericNullableEcho(T object)` + /// The returned object must be released after use, by calling the [release] method. + $T classGenericNullableEcho( + $T object, + ) { + final _$object = object?.reference ?? _$jni.jNullReference; + return _classGenericNullableEcho( + reference.pointer, + _id_classGenericNullableEcho as _$jni.JMethodIDPtr, + _$object.pointer) + .object<$T>(T); + } + + static final _id_firstOf = _class.instanceMethodId( + r'firstOf', + r'(Ljava/util/List;)Ljava/lang/String;', + ); + + static final _firstOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.lang.String firstOf(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JString firstOf( + _$jni.JList<_$jni.JString> list, + ) { + final _$list = list.reference; + return _firstOf(reference.pointer, _id_firstOf as _$jni.JMethodIDPtr, + _$list.pointer) + .object<_$jni.JString>(const _$jni.JStringType()); + } + + static final _id_firstOfNullable = _class.instanceMethodId( + r'firstOfNullable', + r'(Ljava/util/List;)Ljava/lang/String;', + ); + + static final _firstOfNullable = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.lang.String firstOfNullable(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JString? firstOfNullable( + _$jni.JList<_$jni.JString?> list, + ) { + final _$list = list.reference; + return _firstOfNullable(reference.pointer, + _id_firstOfNullable as _$jni.JMethodIDPtr, _$list.pointer) .object<_$jni.JString?>(const _$jni.JStringNullableType()); } - static final _id_getCoefficient = _class.instanceMethodId( - r'getCoefficient', - r'()F', + static final _id_classGenericFirstOf = _class.instanceMethodId( + r'classGenericFirstOf', + r'(Ljava/util/List;)Ljava/lang/Object;', ); - static final _getCoefficient = _$jni.ProtectedJniExtensions.lookup< - _$jni.NativeFunction< - _$jni.JniResult Function( - _$jni.Pointer<_$jni.Void>, - _$jni.JMethodIDPtr, - )>>('globalEnv_CallFloatMethod') + static final _classGenericFirstOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') .asFunction< - _$jni.JniResult Function( - _$jni.Pointer<_$jni.Void>, - _$jni.JMethodIDPtr, - )>(); + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); - /// from: `public abstract float getCoefficient()` - double getCoefficient() { - return _getCoefficient( - reference.pointer, _id_getCoefficient as _$jni.JMethodIDPtr) - .float; + /// from: `public final U classGenericFirstOf(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + $U classGenericFirstOf( + _$jni.JList<$U> list, + ) { + final _$list = list.reference; + return _classGenericFirstOf(reference.pointer, + _id_classGenericFirstOf as _$jni.JMethodIDPtr, _$list.pointer) + .object<$U>(U); } - /// Maps a specific port to the implemented interface. - static final _$core.Map _$impls = {}; - static _$jni.JObjectPtr _$invoke( - int port, - _$jni.JObjectPtr descriptor, - _$jni.JObjectPtr args, + static final _id_classGenericFirstOfNullable = _class.instanceMethodId( + r'classGenericFirstOfNullable', + r'(Ljava/util/List;)Ljava/lang/Object;', + ); + + static final _classGenericFirstOfNullable = + _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final T classGenericFirstOfNullable(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + $T classGenericFirstOfNullable( + _$jni.JList<$T> list, ) { - return _$invokeMethod( - port, - _$jni.MethodInvocation.fromAddresses( - 0, - descriptor.address, - args.address, - ), - ); + final _$list = list.reference; + return _classGenericFirstOfNullable( + reference.pointer, + _id_classGenericFirstOfNullable as _$jni.JMethodIDPtr, + _$list.pointer) + .object<$T>(T); } - static final _$jni.Pointer< - _$jni.NativeFunction< - _$jni.JObjectPtr Function( - _$jni.Int64, _$jni.JObjectPtr, _$jni.JObjectPtr)>> - _$invokePointer = _$jni.Pointer.fromFunction(_$invoke); + static final _id_methodGenericFirstOf = _class.instanceMethodId( + r'methodGenericFirstOf', + r'(Ljava/util/List;)Ljava/lang/Object;', + ); - static _$jni.Pointer<_$jni.Void> _$invokeMethod( - int $p, - _$jni.MethodInvocation $i, + static final _methodGenericFirstOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final V methodGenericFirstOf(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + $V methodGenericFirstOf<$V extends _$jni.JObject>( + _$jni.JList<$V> list, { + _$jni.JObjType<$V>? V, + }) { + V ??= _$jni.lowestCommonSuperType([ + (list.$type as _$jni.JListType<_$core.dynamic>).E, + ]) as _$jni.JObjType<$V>; + final _$list = list.reference; + return _methodGenericFirstOf(reference.pointer, + _id_methodGenericFirstOf as _$jni.JMethodIDPtr, _$list.pointer) + .object<$V>(V); + } + + static final _id_methodGenericFirstOfNullable = _class.instanceMethodId( + r'methodGenericFirstOfNullable', + r'(Ljava/util/List;)Ljava/lang/Object;', + ); + + static final _methodGenericFirstOfNullable = + _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final V methodGenericFirstOfNullable(java.util.List list)` + /// The returned object must be released after use, by calling the [release] method. + $V methodGenericFirstOfNullable<$V extends _$jni.JObject?>( + _$jni.JList<$V> list, { + _$jni.JObjType<$V>? V, + }) { + V ??= _$jni.lowestCommonSuperType([ + (list.$type as _$jni.JListType<_$core.dynamic>).E, + ]) as _$jni.JObjType<$V>; + final _$list = list.reference; + return _methodGenericFirstOfNullable( + reference.pointer, + _id_methodGenericFirstOfNullable as _$jni.JMethodIDPtr, + _$list.pointer) + .object<$V>(V); + } + + static final _id_stringListOf = _class.instanceMethodId( + r'stringListOf', + r'(Ljava/lang/String;)Ljava/util/List;', + ); + + static final _stringListOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.util.List stringListOf(java.lang.String string)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<_$jni.JString> stringListOf( + _$jni.JString string, ) { - try { - final $d = $i.methodDescriptor.toDartString(releaseOriginal: true); - final $a = $i.args; - if ($d == r'getSign()Ljava/lang/String;') { - final $r = _$impls[$p]!.getSign(); - return ($r as _$jni.JObject?) - ?.as(const _$jni.JObjectType()) - .reference - .toPointer() ?? - _$jni.nullptr; - } - if ($d == r'getCoefficient()F') { - final $r = _$impls[$p]!.getCoefficient(); - return _$jni.JFloat($r).reference.toPointer(); - } - } catch (e) { - return _$jni.ProtectedJniExtensions.newDartException(e); - } - return _$jni.nullptr; + final _$string = string.reference; + return _stringListOf(reference.pointer, + _id_stringListOf as _$jni.JMethodIDPtr, _$string.pointer) + .object<_$jni.JList<_$jni.JString>>( + const _$jni.JListType<_$jni.JString>(_$jni.JStringType())); } - static void implementIn( - _$jni.JImplementer implementer, - $MeasureUnit $impl, + static final _id_nullableListOf = _class.instanceMethodId( + r'nullableListOf', + r'(Ljava/lang/String;)Ljava/util/List;', + ); + + static final _nullableListOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.util.List nullableListOf(java.lang.String string)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<_$jni.JString?> nullableListOf( + _$jni.JString? string, ) { - late final _$jni.RawReceivePort $p; - $p = _$jni.RawReceivePort(($m) { - if ($m == null) { - _$impls.remove($p.sendPort.nativePort); - $p.close(); - return; - } - final $i = _$jni.MethodInvocation.fromMessage($m); - final $r = _$invokeMethod($p.sendPort.nativePort, $i); - _$jni.ProtectedJniExtensions.returnResult($i.result, $r); - }); - implementer.add( - r'com.github.dart_lang.jnigen.MeasureUnit', - $p, - _$invokePointer, - [], - ); - final $a = $p.sendPort.nativePort; - _$impls[$a] = $impl; + final _$string = string?.reference ?? _$jni.jNullReference; + return _nullableListOf(reference.pointer, + _id_nullableListOf as _$jni.JMethodIDPtr, _$string.pointer) + .object<_$jni.JList<_$jni.JString?>>( + const _$jni.JListType<_$jni.JString?>(_$jni.JStringNullableType())); } - factory MeasureUnit.implement( - $MeasureUnit $impl, + static final _id_classGenericListOf = _class.instanceMethodId( + r'classGenericListOf', + r'(Ljava/lang/Object;)Ljava/util/List;', + ); + + static final _classGenericListOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.util.List classGenericListOf(U object)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<$U> classGenericListOf( + $U object, ) { - final $i = _$jni.JImplementer(); - implementIn($i, $impl); - return MeasureUnit.fromReference( - $i.implementReference(), - ); + final _$object = object.reference; + return _classGenericListOf(reference.pointer, + _id_classGenericListOf as _$jni.JMethodIDPtr, _$object.pointer) + .object<_$jni.JList<$U>>(_$jni.JListType<$U>(U)); } -} -abstract base mixin class $MeasureUnit { - factory $MeasureUnit({ - required _$jni.JString? Function() getSign, - required double Function() getCoefficient, - }) = _$MeasureUnit; + static final _id_classGenericNullableListOf = _class.instanceMethodId( + r'classGenericNullableListOf', + r'(Ljava/lang/Object;)Ljava/util/List;', + ); - _$jni.JString? getSign(); - double getCoefficient(); -} + static final _classGenericNullableListOf = + _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.util.List classGenericNullableListOf(T object)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<$T> classGenericNullableListOf( + $T object, + ) { + final _$object = object?.reference ?? _$jni.jNullReference; + return _classGenericNullableListOf( + reference.pointer, + _id_classGenericNullableListOf as _$jni.JMethodIDPtr, + _$object.pointer) + .object<_$jni.JList<$T>>(_$jni.JListType<$T>(T)); + } -final class _$MeasureUnit with $MeasureUnit { - _$MeasureUnit({ - required _$jni.JString? Function() getSign, - required double Function() getCoefficient, - }) : _getSign = getSign, - _getCoefficient = getCoefficient; + static final _id_methodGenericListOf = _class.instanceMethodId( + r'methodGenericListOf', + r'(Ljava/lang/Object;)Ljava/util/List;', + ); - final _$jni.JString? Function() _getSign; - final double Function() _getCoefficient; + static final _methodGenericListOf = _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); - _$jni.JString? getSign() { - return _getSign(); + /// from: `public final java.util.List methodGenericListOf(V object)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<$V> methodGenericListOf<$V extends _$jni.JObject>( + $V object, { + _$jni.JObjType<$V>? V, + }) { + V ??= _$jni.lowestCommonSuperType([ + object.$type, + ]) as _$jni.JObjType<$V>; + final _$object = object.reference; + return _methodGenericListOf(reference.pointer, + _id_methodGenericListOf as _$jni.JMethodIDPtr, _$object.pointer) + .object<_$jni.JList<$V>>(_$jni.JListType<$V>(V)); } - double getCoefficient() { - return _getCoefficient(); + static final _id_methodGenericNullableListOf = _class.instanceMethodId( + r'methodGenericNullableListOf', + r'(Ljava/lang/Object;)Ljava/util/List;', + ); + + static final _methodGenericNullableListOf = + _$jni.ProtectedJniExtensions.lookup< + _$jni.NativeFunction< + _$jni.JniResult Function( + _$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, + _$jni.VarArgs<(_$jni.Pointer<_$jni.Void>,)>)>>( + 'globalEnv_CallObjectMethod') + .asFunction< + _$jni.JniResult Function(_$jni.Pointer<_$jni.Void>, + _$jni.JMethodIDPtr, _$jni.Pointer<_$jni.Void>)>(); + + /// from: `public final java.util.List methodGenericNullableListOf(V object)` + /// The returned object must be released after use, by calling the [release] method. + _$jni.JList<$V> methodGenericNullableListOf<$V extends _$jni.JObject?>( + $V object, { + required _$jni.JObjType<$V> V, + }) { + final _$object = object?.reference ?? _$jni.jNullReference; + return _methodGenericNullableListOf( + reference.pointer, + _id_methodGenericNullableListOf as _$jni.JMethodIDPtr, + _$object.pointer) + .object<_$jni.JList<$V>>(_$jni.JListType<$V>(V)); } } -final class $MeasureUnit$NullableType extends _$jni.JObjType { +final class $Nullability$NullableType<$T extends _$jni.JObject?, + $U extends _$jni.JObject> extends _$jni.JObjType?> { @_$jni.internal - const $MeasureUnit$NullableType(); + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + const $Nullability$NullableType( + this.T, + this.U, + ); @_$jni.internal @_$core.override - String get signature => r'Lcom/github/dart_lang/jnigen/MeasureUnit;'; + String get signature => r'Lcom/github/dart_lang/jnigen/Nullability;'; @_$jni.internal @_$core.override - MeasureUnit? fromReference(_$jni.JReference reference) => reference.isNull - ? null - : MeasureUnit.fromReference( - reference, - ); + Nullability<$T, $U>? fromReference(_$jni.JReference reference) => + reference.isNull + ? null + : Nullability<$T, $U>.fromReference( + T, + U, + reference, + ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override - _$jni.JObjType get nullableType => this; + _$jni.JObjType?> get nullableType => this; @_$jni.internal @_$core.override final superCount = 1; @_$core.override - int get hashCode => ($MeasureUnit$NullableType).hashCode; + int get hashCode => Object.hash($Nullability$NullableType, T, U); @_$core.override bool operator ==(Object other) { - return other.runtimeType == ($MeasureUnit$NullableType) && - other is $MeasureUnit$NullableType; + return other.runtimeType == ($Nullability$NullableType<$T, $U>) && + other is $Nullability$NullableType<$T, $U> && + T == other.T && + U == other.U; } } -final class $MeasureUnit$Type extends _$jni.JObjType { +final class $Nullability$Type<$T extends _$jni.JObject?, + $U extends _$jni.JObject> extends _$jni.JObjType> { @_$jni.internal - const $MeasureUnit$Type(); + final _$jni.JObjType<$T> T; + + @_$jni.internal + final _$jni.JObjType<$U> U; + + @_$jni.internal + const $Nullability$Type( + this.T, + this.U, + ); @_$jni.internal @_$core.override - String get signature => r'Lcom/github/dart_lang/jnigen/MeasureUnit;'; + String get signature => r'Lcom/github/dart_lang/jnigen/Nullability;'; @_$jni.internal @_$core.override - MeasureUnit fromReference(_$jni.JReference reference) => - MeasureUnit.fromReference( + Nullability<$T, $U> fromReference(_$jni.JReference reference) => + Nullability<$T, $U>.fromReference( + T, + U, reference, ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override - _$jni.JObjType get nullableType => - const $MeasureUnit$NullableType(); + _$jni.JObjType?> get nullableType => + $Nullability$NullableType<$T, $U>(T, U); @_$jni.internal @_$core.override final superCount = 1; @_$core.override - int get hashCode => ($MeasureUnit$Type).hashCode; + int get hashCode => Object.hash($Nullability$Type, T, U); @_$core.override bool operator ==(Object other) { - return other.runtimeType == ($MeasureUnit$Type) && - other is $MeasureUnit$Type; + return other.runtimeType == ($Nullability$Type<$T, $U>) && + other is $Nullability$Type<$T, $U> && + T == other.T && + U == other.U; } } /// from: `com.github.dart_lang.jnigen.Speed` -class Speed extends Measure { +class Speed extends Measure { @_$jni.internal @_$core.override final _$jni.JObjType $type; @@ -501,7 +1576,7 @@ class Speed extends Measure { Speed.fromReference( _$jni.JReference reference, ) : $type = type, - super.fromReference(const $SpeedUnit$NullableType(), reference); + super.fromReference(const $SpeedUnit$Type(), reference); static final _class = _$jni.JClass.forName(r'com/github/dart_lang/jnigen/Speed'); @@ -531,9 +1606,9 @@ class Speed extends Measure { /// The returned object must be released after use, by calling the [release] method. factory Speed( double f, - SpeedUnit? speedUnit, + SpeedUnit speedUnit, ) { - final _$speedUnit = speedUnit?.reference ?? _$jni.jNullReference; + final _$speedUnit = speedUnit.reference; return Speed.fromReference(_new$(_class.reference.pointer, _id_new$ as _$jni.JMethodIDPtr, f, _$speedUnit.pointer) .reference); @@ -581,9 +1656,9 @@ class Speed extends Measure { /// from: `public com.github.dart_lang.jnigen.SpeedUnit getUnit()` /// The returned object must be released after use, by calling the [release] method. - SpeedUnit? getUnit$1() { + SpeedUnit getUnit$1() { return _getUnit$1(reference.pointer, _id_getUnit$1 as _$jni.JMethodIDPtr) - .object(const $SpeedUnit$NullableType()); + .object(const $SpeedUnit$Type()); } static final _id_toString$1 = _class.instanceMethodId( @@ -605,9 +1680,9 @@ class Speed extends Measure { /// from: `public java.lang.String toString()` /// The returned object must be released after use, by calling the [release] method. - _$jni.JString? toString$1() { + _$jni.JString toString$1() { return _toString$1(reference.pointer, _id_toString$1 as _$jni.JMethodIDPtr) - .object<_$jni.JString?>(const _$jni.JStringNullableType()); + .object<_$jni.JString>(const _$jni.JStringType()); } static final _id_component1 = _class.instanceMethodId( @@ -652,9 +1727,9 @@ class Speed extends Measure { /// from: `public final com.github.dart_lang.jnigen.SpeedUnit component2()` /// The returned object must be released after use, by calling the [release] method. - SpeedUnit? component2() { + SpeedUnit component2() { return _component2(reference.pointer, _id_component2 as _$jni.JMethodIDPtr) - .object(const $SpeedUnit$NullableType()); + .object(const $SpeedUnit$Type()); } static final _id_copy = _class.instanceMethodId( @@ -678,14 +1753,14 @@ class Speed extends Measure { /// from: `public final com.github.dart_lang.jnigen.Speed copy(float f, com.github.dart_lang.jnigen.SpeedUnit speedUnit)` /// The returned object must be released after use, by calling the [release] method. - Speed? copy( + Speed copy( double f, - SpeedUnit? speedUnit, + SpeedUnit speedUnit, ) { - final _$speedUnit = speedUnit?.reference ?? _$jni.jNullReference; + final _$speedUnit = speedUnit.reference; return _copy(reference.pointer, _id_copy as _$jni.JMethodIDPtr, f, _$speedUnit.pointer) - .object(const $Speed$NullableType()); + .object(const $Speed$Type()); } static final _id_hashCode$1 = _class.instanceMethodId( @@ -756,7 +1831,7 @@ final class $Speed$NullableType extends _$jni.JObjType { @_$jni.internal @_$core.override _$jni.JObjType get superType => - const $Measure$NullableType($SpeedUnit$NullableType()); + const $Measure$Type($SpeedUnit$Type()); @_$jni.internal @_$core.override @@ -792,7 +1867,7 @@ final class $Speed$Type extends _$jni.JObjType { @_$jni.internal @_$core.override _$jni.JObjType get superType => - const $Measure$NullableType($SpeedUnit$NullableType()); + const $Measure$Type($SpeedUnit$Type()); @_$jni.internal @_$core.override @@ -868,9 +1943,9 @@ class SpeedUnit extends _$jni.JObject { /// from: `public java.lang.String getSign()` /// The returned object must be released after use, by calling the [release] method. - _$jni.JString? getSign() { + _$jni.JString getSign() { return _getSign(reference.pointer, _id_getSign as _$jni.JMethodIDPtr) - .object<_$jni.JString?>(const _$jni.JStringNullableType()); + .object<_$jni.JString>(const _$jni.JStringType()); } static final _id_getCoefficient = _class.instanceMethodId( @@ -968,7 +2043,7 @@ final class $SpeedUnit$NullableType extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -1004,7 +2079,7 @@ final class $SpeedUnit$Type extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -1084,23 +2159,23 @@ class SuspendFun extends _$jni.JObject { /// from: `public final java.lang.Object sayHello(kotlin.coroutines.Continuation continuation)` /// The returned object must be released after use, by calling the [release] method. - _$core.Future<_$jni.JString?> sayHello() async { + _$core.Future<_$jni.JString> sayHello() async { final $p = _$jni.ReceivePort(); final _$continuation = _$jni.ProtectedJniExtensions.newPortContinuation($p); _sayHello(reference.pointer, _id_sayHello as _$jni.JMethodIDPtr, _$continuation.pointer) - .object<_$jni.JObject?>(const _$jni.JObjectNullableType()); + .object<_$jni.JObject>(const _$jni.JObjectType()); _$continuation.release(); final $o = _$jni.JGlobalReference(_$jni.JObjectPtr.fromAddress(await $p.first)); - final $k = const _$jni.JStringNullableType().jClass.reference; + final $k = const _$jni.JStringType().jClass.reference; if (!_$jni.Jni.env.IsInstanceOf($o.pointer, $k.pointer)) { $k.release(); throw 'Failed'; } $k.release(); - return const _$jni.JStringNullableType().fromReference($o); + return const _$jni.JStringType().fromReference($o); } static final _id_sayHello$1 = _class.instanceMethodId( @@ -1127,7 +2202,7 @@ class SuspendFun extends _$jni.JObject { /// from: `public final java.lang.Object sayHello(java.lang.String string, kotlin.coroutines.Continuation continuation)` /// The returned object must be released after use, by calling the [release] method. - _$core.Future<_$jni.JString?> sayHello$1( + _$core.Future<_$jni.JString> sayHello$1( _$jni.JString? string, ) async { final $p = _$jni.ReceivePort(); @@ -1135,17 +2210,17 @@ class SuspendFun extends _$jni.JObject { final _$string = string?.reference ?? _$jni.jNullReference; _sayHello$1(reference.pointer, _id_sayHello$1 as _$jni.JMethodIDPtr, _$string.pointer, _$continuation.pointer) - .object<_$jni.JObject?>(const _$jni.JObjectNullableType()); + .object<_$jni.JObject>(const _$jni.JObjectType()); _$continuation.release(); final $o = _$jni.JGlobalReference(_$jni.JObjectPtr.fromAddress(await $p.first)); - final $k = const _$jni.JStringNullableType().jClass.reference; + final $k = const _$jni.JStringType().jClass.reference; if (!_$jni.Jni.env.IsInstanceOf($o.pointer, $k.pointer)) { $k.release(); throw 'Failed'; } $k.release(); - return const _$jni.JStringNullableType().fromReference($o); + return const _$jni.JStringType().fromReference($o); } } @@ -1166,7 +2241,7 @@ final class $SuspendFun$NullableType extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override @@ -1202,7 +2277,7 @@ final class $SuspendFun$Type extends _$jni.JObjType { ); @_$jni.internal @_$core.override - _$jni.JObjType get superType => const _$jni.JObjectNullableType(); + _$jni.JObjType get superType => const _$jni.JObjectType(); @_$jni.internal @_$core.override diff --git a/pkgs/jnigen/test/kotlin_test/kotlin/src/main/kotlin/com/github/dart_lang/jnigen/Nullability.kt b/pkgs/jnigen/test/kotlin_test/kotlin/src/main/kotlin/com/github/dart_lang/jnigen/Nullability.kt new file mode 100644 index 000000000..159be46ba --- /dev/null +++ b/pkgs/jnigen/test/kotlin_test/kotlin/src/main/kotlin/com/github/dart_lang/jnigen/Nullability.kt @@ -0,0 +1,84 @@ +/* Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file + * for details. All rights reserved. Use of this source code is governed by a + * BSD-style license that can be found in the LICENSE file. + */ + +package com.github.dart_lang.jnigen + +public class Nullability(val t: T, val u: U, var nullableU: U?) { + public fun hello(): String { + return "hello" + } + + public fun nullableHello(returnNull: Boolean): String? { + return if (returnNull) null else "hello" + } + + public fun methodGenericEcho(v: V): V { + return v + } + + public fun methodGenericNullableEcho(v: V): V { + return v + } + + public fun classGenericEcho(u: U): U { + return u + } + + public fun classGenericNullableEcho(t: T): T { + return t + } + + public fun firstOf(list: List): String { + return list.first(); + } + + public fun firstOfNullable(list: List): String? { + return list.first(); + } + + public fun classGenericFirstOf(list: List): U { + return list.first(); + } + + public fun classGenericFirstOfNullable(list: List): T { + return list.first(); + } + + public fun methodGenericFirstOf(list: List): V { + return list.first(); + } + + public fun methodGenericFirstOfNullable(list: List): V { + return list.first(); + } + + public fun stringListOf(element: String): List { + return listOf(element) + } + + public fun nullableListOf(element: String?): List { + return listOf(element) + } + + public fun classGenericListOf(element: U): List { + return listOf(element) + } + + public fun classGenericNullableListOf(element: T): List { + return listOf(element) + } + + public fun methodGenericListOf(element: V): List { + return listOf(element) + } + + public fun methodGenericNullableListOf(element: V): List { + return listOf(element) + } + + public inner class InnerClass { + public fun f(t: T, u: U, v: V) {} + } +} diff --git a/pkgs/jnigen/test/kotlin_test/runtime_test_registrant.dart b/pkgs/jnigen/test/kotlin_test/runtime_test_registrant.dart index 1dca0b082..aceef678f 100644 --- a/pkgs/jnigen/test/kotlin_test/runtime_test_registrant.dart +++ b/pkgs/jnigen/test/kotlin_test/runtime_test_registrant.dart @@ -13,11 +13,11 @@ void registerTests(String groupName, TestRunnerCallback test) { test('Suspend functions', () async { await using((arena) async { final suspendFun = SuspendFun()..releasedBy(arena); - final hello = (await suspendFun.sayHello())!; + final hello = await suspendFun.sayHello(); expect(hello.toDartString(releaseOriginal: true), 'Hello!'); const name = 'Bob'; final helloBob = - (await suspendFun.sayHello$1(name.toJString()..releasedBy(arena)))!; + await suspendFun.sayHello$1(name.toJString()..releasedBy(arena)); expect(helloBob.toDartString(releaseOriginal: true), 'Hello $name!'); }); }); @@ -32,8 +32,217 @@ void registerTests(String groupName, TestRunnerCallback test) { test('Generics', () { using((arena) { - final speed = Speed(10, SpeedUnit.MetrePerSec)..releasedBy(arena); - expect(speed.convertValue(SpeedUnit.KmPerHour), closeTo(36, 1e-6)); + final speed = Speed(10, SpeedUnit.MetrePerSec!)..releasedBy(arena); + expect(speed.convertValue(SpeedUnit.KmPerHour!), closeTo(36, 1e-6)); + }); + }); + + group('Nullability', () { + Nullability testObject(Arena arena) { + return Nullability( + null, + 'hello'.toJString(), + null, + T: JString.nullableType, + U: JString.type, + )..releasedBy(arena); + } + + test('Getters', () { + using((arena) { + final obj = testObject(arena); + expect( + obj.getU().toDartString(releaseOriginal: true), + 'hello', + ); + expect(obj.getT(), null); + expect(obj.getNullableU(), null); + }); + }); + test('Setters', () { + using((arena) { + final obj = testObject(arena); + obj.setNullableU('hello'.toJString()..releasedBy(arena)); + expect( + obj.getNullableU()!.toDartString(releaseOriginal: true), + 'hello', + ); + obj.setNullableU(null); + expect( + obj.getNullableU(), + null, + ); + }); + }); + test('Methods', () { + using((arena) { + final obj = testObject(arena); + expect(obj.hello().toDartString(releaseOriginal: true), 'hello'); + expect( + obj.nullableHello(false)!.toDartString(releaseOriginal: true), + 'hello', + ); + expect(obj.nullableHello(true), null); + expect( + obj + .classGenericEcho('hello'.toJString()..releasedBy(arena)) + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .classGenericNullableEcho( + 'hello'.toJString()..releasedBy(arena))! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect(obj.classGenericNullableEcho(null), null); + expect( + obj + .methodGenericEcho( + 'hello'.toJString()..releasedBy(arena), + V: JString.type, + ) + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .methodGenericNullableEcho( + 'hello'.toJString()..releasedBy(arena), + V: JString.nullableType, + )! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj.methodGenericNullableEcho(null, V: JString.nullableType), + null, + ); + expect( + obj + .stringListOf('hello'.toJString()..releasedBy(arena))[0] + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .nullableListOf('hello'.toJString()..releasedBy(arena))[0]! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect(obj.nullableListOf(null)[0], null); + expect( + obj + .classGenericListOf('hello'.toJString()..releasedBy(arena))[0] + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .classGenericNullableListOf( + 'hello'.toJString()..releasedBy(arena))[0]! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect(obj.classGenericNullableListOf(null)[0], null); + expect( + obj + .methodGenericListOf('hello'.toJString()..releasedBy(arena))[0] + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .methodGenericNullableListOf( + 'hello'.toJString()..releasedBy(arena), + V: JString.nullableType, + )[0]! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj.methodGenericNullableListOf(null, V: JString.nullableType)[0], + null, + ); + expect( + obj + .firstOf(['hello'.toJString()..releasedBy(arena)] + .toJList(JString.type)) + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .firstOfNullable(['hello'.toJString()..releasedBy(arena), null] + .toJList(JString.nullableType))! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj.firstOfNullable([null, 'hello'.toJString()..releasedBy(arena)] + .toJList(JString.nullableType)), + null, + ); + expect( + obj + .classGenericFirstOf(['hello'.toJString()..releasedBy(arena)] + .toJList(JString.type)) + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .classGenericFirstOfNullable([ + 'hello'.toJString()..releasedBy(arena), + null, + ].toJList(JString.nullableType))! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj.classGenericFirstOfNullable([ + null, + 'hello'.toJString()..releasedBy(arena), + ].toJList(JString.nullableType)), + null, + ); + expect( + obj + .methodGenericFirstOf(['hello'.toJString()..releasedBy(arena)] + .toJList(JString.type)) + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj + .methodGenericFirstOfNullable([ + 'hello'.toJString()..releasedBy(arena), + null, + ].toJList(JString.nullableType))! + .toDartString(releaseOriginal: true), + 'hello', + ); + expect( + obj.methodGenericFirstOfNullable([ + null, + 'hello'.toJString()..releasedBy(arena), + ].toJList(JString.nullableType)), + null, + ); + }); + }); + test('Inner class', () { + using((arena) { + final obj = testObject(arena); + final innerObj = Nullability_InnerClass( + obj, + V: JInteger.type); + expect( + innerObj.f, + isA(), + ); + }); }); }); });