haxe icon indicating copy to clipboard operation
haxe copied to clipboard

[cs/java(not-jvm)] invalid closure generation with @:generic + structure typing

Open nadako opened this issue 5 years ago • 3 comments

class Main {
	@:generic
	static function d<T:{function dispose():Void;}>(o:T):()->Void {
		return o.dispose;
	}

	function new() {}

	static function main() {
		var dispose = d(new Main());
		dispose();
	}

	public function dispose() {
		trace("Disposing");
	}
}

this generates the following C#:

public static global::haxe.lang.Function d_Main(global::Main o) {
	return ((global::haxe.lang.Function) (o.dispose) );
}

which then of course fails on native compilation, because o.dispose is indeed not a haxe.lang.Function


if we remove @:generic it will work via dynamic access:

public static global::haxe.lang.Function d<T>(T o) {
	return ((global::haxe.lang.Function) (global::haxe.lang.Runtime.getField(o, "dispose", 994869407, true)) );
}

but with @:generic it should generate the same code as if we'd have T:Main instead of a structure:

public static global::haxe.lang.Function d_Main(global::Main o) {
	return ((global::haxe.lang.Function) (new global::haxe.lang.Closure(o, "dispose", 994869407)) );
}

nadako avatar May 07 '20 13:05 nadako

This might be an issue with the AST (cc @Simn @RealyUniqueName) - note FClosure has None for a class.

@:noCompletion @:noUsing @:genericInstance
static function d_Main[Function:(o : Main) -> (Void -> Void)]
	[Arg:Main] [Local o(141964):Main]
	[Block:Dynamic]
		[Return:Dynamic]
			[Field:Void -> Void]
				[Local o(141964):Main:Main]
				[FClosure:Void -> Void]
					None
					dispose:Void -> Void

nadako avatar May 07 '20 13:05 nadako

Looks like a typer issue in generic_substitute_expr

RealyUniqueName avatar May 15 '20 16:05 RealyUniqueName

I'm not closing this one even though it's Java/C# specific, because the AST looks wrong here.

Simn avatar Feb 22 '22 10:02 Simn