最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

java - How to create a dll in Quarkus to be consumed in a C# application? - Stack Overflow

programmeradmin4浏览0评论

I need to create a dll file from a quarkus application. I have tried several approaches that didn't work (IKVM, IKVM, JNI,...) My current approach is by using GraalVM. I'm able to compile the Java classes using the command:

javac *.java

and I'm able to generate the dll using the command:

native-image --shared -H:Name=dbexample -H:-CheckToolchain --enable-native-access=ALL-UNNAMED --no-fallback

and when looking inside the generated dlls I can see that the java methods are there, inside the dll, using the command:

dumpbin /EXPORTS dbexample.dll

But when calling the method I get an error. A kind of a generic error, probably accessing the memory. Something like "Exited Thread 44280"

This is my Java application

import .graalvm.nativeimage.IsolateThread;
import .graalvm.nativeimage.c.function.CEntryPoint;

import .graalvm.nativeimage.Isolates;
import .graalvm.nativeimage.Isolates.CreateIsolateParameters;

public final class LogicConnectionImpl implements LogicConnection {

    @CEntryPoint(name = "IsolateCreate")
    public static IsolateThread createIsolate(@SuppressWarnings("unused") IsolateThread thread) {
    var context = Isolates.createIsolate(CreateIsolateParameters.getDefault());
    return context;
    }

    @CEntryPoint(name = "doSomething")
    public static void doSomething(@SuppressWarnings("unused") IsolateThread thread) {
        System.out.println("Hello, World from inside JAVA!");
    }

    @CEntryPoint(name = "test")
    public static int test(@SuppressWarnings("unused") IsolateThread thread) {
        return 23;
    }

    @CEntryPoint(name = "test2")
    public static void test2(@SuppressWarnings("unused") IsolateThread thread, int value) {
        int value2 = value + 1;
        System.out.println("Hello, World from inside JAVA!");
    }

    public void test3(String thisTest) {
        System.out.println("Hello, World from inside JAVA! " + thisTest);
    }
}

And this is my C# application:

using System;
using System.Runtime.InteropServices;

class Program
{
    // Define the P/Invoke signatures
    [DllImport("dbexample.dll", EntryPoint = "doSomething")]
    public static extern void DoSomething(IntPtr thread);

    [DllImport("dbexample.dll", EntryPoint = "test")]
    public static extern int Test(IntPtr thread);

    [DllImport("dbexample.dll", EntryPoint = "test2")]
    public static extern void Test2(IntPtr thread, int value);

    [DllImport("dbexample.dll", EntryPoint = "IsolateCreate")]
    public static extern IntPtr IsolateCreate(IntPtr thread);


    static void Main(string[] args)
    {
        try
        {
            IntPtr isolateThread = IsolateCreate(IntPtr.Zero);

            if (isolateThread == IntPtr.Zero)
            {
                Console.WriteLine("Failed to create IsolateThread.");
                return;
            }
        
            // Call the methods from the DLL
            DoSomething(isolateThread);
            int result = Test(isolateThread);
            Console.WriteLine("Result from test: " + result);
            Test2(isolateThread, 42);
        }
        catch (Exception ex)
        {
            Console.WriteLine("An error occurred: " + ex.Message);
        }
    }
}

The error happens on the following line:

IntPtr isolateThread = IsolateCreate(IntPtr.Zero);

I believe that it happens due to the method parameter (IntPtr.Zero). From what I saw, I need to have the "IsolateCreate" comming from the Java application. Meaning that I cannot call the following methods like for instance DoSomething with IntPtr.Zero, like this:

DoSomething(IntPtr.Zero);

Because if I do it that way, then the error will be in that line of code For that same reason I should call DoSomething with the "IsolateThread" coming from the Java application (method createIsolate), as it is from the examples I show above. However, by doing so, the method "createIsolate" that also must have the decorator "@CEntryPoint", so that it is exported to the dll, must also have a parameter of type "IsolateThread", which in turn in C# I need to pass a parameter "IsolateThread" and I'm calling it with "IntPtr.Zero".

I feel I'm close to importing the Java dll in C# but there is some tweak here that I'm missing. Can you please help?

发布评论

评论列表(0)

  1. 暂无评论