jextract generates downcallHandles where I need upcallStubs
Sebastian Stenzel
sebastian.stenzel at gmail.com
Mon Jan 4 11:31:05 UTC 2021
Yes, this is exactly what I need! Thank you for responding so promptly to feedback! :)
> Am 04.01.2021 um 12:00 schrieb Jorn Vernee <jorn.vernee at oracle.com>:
>
> On 28/12/2020 13:13, Sebastian Stenzel wrote:
>>
>>>> On 28. Dec 2020, at 12:38, Maurizio Cimadamore <maurizio.cimadamore at oracle.com> wrote:
>>>
>>>
>>>
>>> On 26/12/2020 09:23, Sebastian Stenzel wrote:
>>>>> On 15. Dec 2020, at 12:31, Maurizio Cimadamore <maurizio.cimadamore at oracle.com <mailto:maurizio.cimadamore at oracle.com>> wrote:
>>>>>
>>>>> Now, it's true that the function pointer type behind "readdir" takes its own function pointer (filler), but that shouldn't be a concern when creating the upcall for (1) - a function pointer is just some MemoryAddress parameter that the upcall receives (and that the runtime of the libfuse library will provide). And, it is true that, in this case jextract will also generate functional interfaces for e.g. the filler upcall, but you don't have to use them in this case (since the filler function pointer will never be generated by you - but by the library) - of course jextract sees a function pointer and generates the corresponding functional interface, it has no way to know which party will allocate the function pointer.
>>>> After experimenting with the latest snapshot version of Panama, I was now able to implement aforementioned readdir() method. However I still don't manage to use the filler function.
>>>>
>>>> jextract will generate a Java method interface from readdir [1] that looks like this:
>>>>
>>>> ```
>>>> int readdir(MemoryAddress path, MemoryAddress buf, MemoryAddress filler, long offset, MemoryAddress fi)
>>>> ```
>>>>
>>>> Note that the filler is merely a MemoryAddress. From within my Java implementation I'd need to call filler, however in order to create a downcallHandle from this address, I'd need to know the FunctionDescriptor, which is kept package-private within the code generated by jextract.
>>>>
>>>> It would be even easier, if there was some way to retrieve a MethodHandle from a given MemoryAddress and a known FunctionDescriptor.
>>>>
>>>> Or am I missing something, again?
>>> So, if I understand correctly, what you need here is to pass a function pointer to the routine that does the "filling" - which is probably a Java upcall.
>>>
>> No, it's a downcall from within an upcall method (more on this below).
>>> Since `fuse_fill_dir_t` is defined as a function type, there should be a functional interface generated for that parameter (probably called something like readdir$filler). If you don't see the functional interface, it is possible you might be missing the fix for:
>>>
>>> https://github.com/openjdk/panama-foreign/pull/424 <https://github.com/openjdk/panama-foreign/pull/424>
>>> Which, judging from the date in which it has been integrated, it is not part of the EA.
>>>
>>> Are you in a position to do a build of the Panama repo? If so, you could try if the functional interface is generated in that case.
>>>
>>> We plan to spin up another EA as soon as IntelliJ is updated to support Java 16 in full.
>>>
>>> Cheers
>>> Maurizio
>>>
>>>
>> Hi,
>>
>> first of all, I did build the latest version myself and can confirm, that the upcall interfaces for function pointers are being generated now.
>>
>> I.e. we now get `fuse_h.fuse_operations.readdir` with the correct signature mentioned in my previous email. I can now implement this method, but from within its implementation I need to make a downcall (!) invocation of the "filler" function passed as the second param of the method.
>>
>> Only an upcall interface for this method gets generated (`fuse_h.fuse_fs_readdir$filler`), which is incorrect in this case. In order to retrieve a downcall handle, I need to pass this address to CLinker together with the Java MethodType and the C FunctionDescriptor. However the FunctionDescriptor is kept package-private in `fuse_h_constants_4.fuse_fs_readdir$filler$FUNC()` and the MethodType is hidden in some string representation.
>>
>> Maybe seeing this implementation helps to understand the role of readdir (upcall) and the filler callback (downcall):
>>
>> https://github.com/skymatic/fuse-panama/blob/b56bb6782f52499279883672972e53ec38942934/src/main/java/de/skymatic/fusepanama/examples/HelloFileSystem.java#L79-L81 <https://github.com/skymatic/fuse-panama/blob/b56bb6782f52499279883672972e53ec38942934/src/main/java/de/skymatic/fusepanama/examples/HelloFileSystem.java#L79-L81>
>>
>> Best regards
>> Sebastian
> I think I understand the problem;
>
> You have some upcall/callback that takes a function pointer as MemoryAddress, and would like to make it callable, and it would be useful if jextract, but the MethodType and FunctionDescriptor associated with the function pointers type are non-accessible. FWIW, these were accessible in the past, but making them inaccessible was done on purpose to see what kind of use-cases would pop up.
>
> In this case, I think it would be useful if jextract generated a helper method for converting a MemoryAddress that is a function pointer into a MethodHandle (or a functional interface instance), so it is easier to call from Java as well. e.g. add something like this to the generated function interfaces for function pointer types:
>
> public interface myHeader$foo$f {
> ...
> public static myHeader$foo$f ofAddress(MemoryAddress);
> }
>
> That would than call the linker with the right MethodType and FunctionDescriptor for you.
>
> Does that sound like it would work for your use case?
>
> Jorn
More information about the panama-dev
mailing list