2015-06-03 6 views
5

Я работаю над чтением функции C# (dll) из java через jni4net и в ядре ядра. Мне удалось получить значение из функции dll, но теперь я создал одну динамическую сеть Project и попытался использовать ту же функциональность в сервлет. Но теперь только файл dll загружается успешно, функция не называется succesfuly. Ниже то, что я пытался до сих пор:Исключение исключения UnsatisfiedLinkError при работе с dll и java jni4net

Мой Servlet:

public class LoginProcess extends HttpServlet { 
    private static final long serialVersionUID = 1L; 

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { 

     try { 

      Bridge.setVerbose(true); 
      Bridge.init(); 
      Console.WriteLine("Hello .NET world!\n"); 

      Bridge.LoadAndRegisterAssemblyFrom(new File("C:/Users/ashish.it/workspace/FinalJniWeb/WebContent/WEB-INF/lib/ADHelper.j4n.dll")); 

     } catch (IOException e) { 
      e.printStackTrace(); 
     } 
     Enum output; 
     output=ADHelper.Login("user", "pass"); 
     System.out.println(output); 
    } 
} 

Единственная разница, когда я сделал это в ядре ява было то, что я не использовал полный путь вместо этого я использовал только «LIB/ADHelper.j4n.dll "для пути, но каким-то образом он не работал в сервлете, поэтому я изменил его на полный путь. В любом случае файл dll загружается успешно.

ADHelper.generated.cs

namespace ADHelper { 
    public partial class ADHelper_ { 

methods.Add(global::net.sf.jni4net.jni.JNINativeMethod.Create(@__type, "Login", "Login2", "(Ljava/lang/String;Ljava/lang/String;)Lsystem/Enum;")); 

    private static global::net.sf.jni4net.utils.JniHandle Login2(global::System.IntPtr @__envp, global::net.sf.jni4net.utils.JniLocalHandle @__class, global::net.sf.jni4net.utils.JniLocalHandle UserName, global::net.sf.jni4net.utils.JniLocalHandle Password) { 
      // (Ljava/lang/String;Ljava/lang/String;)Lsystem/Enum; 
      // (LSystem/String;LSystem/String;)LADHelper/ADHelper+LoginResult; 
      global::net.sf.jni4net.jni.JNIEnv @__env = global::net.sf.jni4net.jni.JNIEnv.Wrap(@__envp); 
      global::net.sf.jni4net.utils.JniHandle @__return = default(global::net.sf.jni4net.utils.JniHandle); 
      try { 
      @__return = global::net.sf.jni4net.utils.Convertor.StrongC2Jp<global::ADHelper.ADHelper.LoginResult>(@__env, global::ADHelper.ADHelper.Login(global::net.sf.jni4net.utils.Convertor.StrongJ2CString(@__env, UserName), global::net.sf.jni4net.utils.Convertor.StrongJ2CString(@__env, Password))); 
      }catch (global::System.Exception __ex){@__env.ThrowExisting(__ex);} 
      return @__return; 
     } 
} 

underdscore примешивался к классу имя ADHelper, когда я побежал proxygen команду. в длл файл существует два класса с именем ADHelper и ADHelper

Функция Логин() также изменено на Имя_входа2(), но Имя_входа2() не распознается сервлет, тогда как Логин() признается.

Сгенерированный класс Java ADHelper.java

package adhelper; 

@net.sf.jni4net.attributes.ClrType 
public class ADHelper extends system.Object { 

private static system.Type staticType; 

    protected ADHelper(net.sf.jni4net.inj.INJEnv __env, long __handle) { 
      super(__env, __handle); 
    } 

    @net.sf.jni4net.attributes.ClrConstructor("()V") 
    public ADHelper() { 
      super(((net.sf.jni4net.inj.INJEnv)(null)), 0); 
     adhelper.ADHelper.__ctorADHelper0(this); 
    } 

@net.sf.jni4net.attributes.ClrMethod("(LSystem/String;LSystem/String;)LADHelper/ADHelper+LoginResult;") 
    public native static system.Enum Login(java.lang.String UserName, java.lang.String Password); 

public static system.Type typeof() { 
     return adhelper.ADHelper.staticType; 
    } 

private static void InitJNI(net.sf.jni4net.inj.INJEnv env, system.Type staticType) { 
     adhelper.ADHelper.staticType = staticType; 
    } 
} 

Все отображение является правильным, но мой Логин функция дает unsatisfiedLinkError. Благодарим за терпение во время чтения, пожалуйста, дайте решение моей проблемы.

После ошибка приходит на консоли:

*All Dll file loaded message* 
Jun 3, 2015 10:56:39 AM org.apache.catalina.core.StandardWrapperValve invoke 
SEVERE: Servlet.service() for servlet LoginProcess threw exception 
java.lang.UnsatisfiedLinkError: adhelper.ADHelper.Login(Ljava/lang/String;Ljava/lang/String;)Lsystem/Enum; 
    at adhelper.ADHelper.Login(Native Method) 
    at com.karvy.login.LoginProcess.doGet(LoginProcess.java:62) 
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:617) 
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:723) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233) 
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) 
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) 
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103) 
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293) 
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:861) 
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:606) 
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489) 
    at java.lang.Thread.run(Thread.java:662) 

ответ

1

Я считал, что это проблема с загрузчиком классов, которая была не тогда, когда я позже подавил свои файлы для загрузки из одного загрузчика классов.

Дальнейшая проверка показала, что путь, который я дал, был прямым путем к файлу в каталоге и не указывал на то же направление, что и в файле в контексте контекста сервлета. Для этого мне пришлось создать servlet context object, после чего был вызван метод getResuorce, так что я могу получить свой файл и быть готовым к использованию.

Вот код, чтобы получить файл из контекста сервлета рамки:

ServletContext context = getServletContext(); 
String realPath = context.getRealPath("/WEB-INF/lib/ADHelper.j4n.dll"); 
File file = new File(realPath); 

Спасибо @ сурабхи-рая за вашу поддержку. Я опубликовал этот вопрос, если в будущем кто-нибудь может решить эту проблему. Благодарю вас и приветствую. ☻

2

Может быть, вы можете проверить для класса-загрузчик загружает файл из различных классов погрузчиков в другом контексте.

+1

Я заставляю dll загружаться из загрузчика классов web context, но никаких изменений нет. –

1

Получить ссылку на файл через объект контекста сервлета, а затем вызвать метод getResource на нем.

Прямо сейчас вы указываете на локальный каталог, который не находится в контексте контекста сервлета.