thread-unsichere, native Bibliotheken

KrokoDiehl

Top Contributor
Hallo zusammen.

Ich habe ein Problem mit Java und nativen Bibliotheken. Das Problem ist ziemlich betriebssystemnah (...glaube ich...) und betrifft ein Thema, in dem ich mich nicht sehr heimisch fühle.

Folgende Situation:
Ich habe einige C-Bibliotheken die schon recht alt sind und NICHT threadsicher sind, sprich u.a. globale Variablen haben. Diese auszubessern ist aber erstmal keine Option... (es wäre auch ein Heidenaufwand).
Diese "darf" ich aus einer Java-Anwendung heraus aufrufen. Das ist erstmal kein Problem. Ich habe das bisher über JNI und
Code:
System.loadLibrary()
gemacht und es läuft auch.

Aber das konkrete Problem: Wenn ich meine Java-Anwendung mehrmals instanziieren will, geht das nicht, weil dies aus Sicht des Betriebssystem (BS) immernoch der gleiche Prozess ist und dieser die native Bib. schon dazu geladen hat. Sprich es wird nicht ein zweites mal neu geladen. Damit tun die nativen Bibs. aber nicht, weil sie sich eben (v.a. wegen der Globalen) überschneiden. Ich hab's getestet, das Ganze schmiert recht schnell mit einer Speicherschutzverletzung ab ;)
Bisheriger Workaround: Es wird immer ein neuer Javaprozess (
Code:
Runtime.exec()
...) gestartet, sodass die Bib. immer neu geladen wird. Das ist aber schlecht, weil ich a) zwei separate Prozesse hab und dazwischen nur schwer kommunizieren kann (Thema IPC) und auch zwei separate VMs (und u.A. mehr Speicherverbrauch).

Nun meine Fragen: Gibt es eine Möglichkeit, innerhalb einer VM ein Java-Programm mehrmals separat auszuführen, sodass das Laden einer nativen Lib. auch mehrmals möglich ist? Oder geht es z.B. gar nicht, weil dies eben eine Sache vom BS ist (habe es bisher unter Windows NT und Linux getestet).

Oder wisst ihr irgendwie Suchbegriffe, Literatur, ... irgendwas mit dem ich meine Suche mal fortsetzen kann, weil bisher bin ich auf dem Standpunkt geht nicht anders.

Also danke für eure Zeit.
 

FArt

Top Contributor
Ich habe ein Problem mit Java und nativen Bibliotheken. Das Problem ist ziemlich betriebssystemnah
lol.. ja, das haben native Bibliotheken so an sich...

Eine VM wird die Library meines Wissens nur einmal laden, weil der Prozess ja die Library verwendet...

Evtl. ist es möglich, alle Zugriffe aus der VM auf die Library zu synchronisieren, z.B. über den selben Mutex. Das ginge relativ einfach, wenn die Zugriffe auf die Library nicht kreuz und quer im Code verstreut sind, sondern z.B. über einen Wrapper getätigt werden. Wenn das nicht der Fall ist, könnte man evtl. noch über AOP Mittel eine Synchronisierung hinbekommen. Aber auch da muss man angeben können, wo man einen Eingriff für die Synchronisierung durchführen möchte.
 

KrokoDiehl

Top Contributor
Danke für die Rückmeldung.
Das Problem ansich ist aber nicht die Synchonisation der Aufrufe, sondern das was diese Bibliothek intern macht. Sie speichert ihre Zustände z.B. in globalen Variablen. Sobald ich aber eine neue Instanz erstelle, wird zwar meine Java-Seite neu instanziiert, diese Bib. aber bleibt die gleiche (weils der gleiche Prozess ist), insbesondere auch deren Globalen. Also intern ist nichts mehr mit verschiedenen Zuständen ;)

Zu Beginn hatte ich ja die Hoffnung, dass dieses einfach durch folgendes lösbar wäre:
Java:
class MyNativeLibraryWrapper
{
    // dies wird einmal für alle MyNativeLibraryWrapper ausgeführt
    static {
        System.loadLibrary("myNativeLibrary");
    }    
}
// versus
class MyNativeLibraryWrapper
{
    public MyNativeLibraryWrapper()
    {
        // dies wird einmal pro Instanz gemacht... wäre cool wenn es auch die Bib. immer neu
        // laden würde, aber das wäre naiv (und in 99% aller Fälle eh nicht erwünscht)
        System.loadLibrary("myNativeLibrary");
    }
}
 

Empire Phoenix

Top Contributor
Nicht sicher ob es geht, aber wenn du über eine der Betriebsystem functionen die Bibliothek dynamisch entladen würdest, und danach wie oben neu laden müsste das dann klappen? Jetzt ist die frge wie man dynamisch entläd:
DLL entladen... - Entwickler-Forum
klingt alles andere als spaßig, evtl doch zwei prozesse nehmen? wobei der eine die dll läd und jedesmal neugestartet wird?
 

FArt

Top Contributor
Es geht um Zustände zwischen mehreren Calls? Das hat aber nichts mit Threadsicherheit zu tun, wie es in deinem ersten Posting steht sondern mit Zuständen.
Ergebnis: das wird nicht gehen.
 

KrokoDiehl

Top Contributor
Hallo.
Ok, ich fasse zusammen, dass mein Vorhaben mit den aktuell vorhandenen, thread- UND zustandsunsicheren nativen Bibliotheken nicht funktioniert, bzw. nur über jeweils neue Prozesse.
Der Ansatz von Empire Phoenix zeigt zwar, dass man theoretisch hier herumhacken kann, aber darauf möchte ich mich nicht begeben ;)

Eine weitere Frage in dem Kontext:
Ich habe eine Java-Anwendung, die ich via
Code:
java -cp ... pak1.pak2.MyMainClass
starte. Sprich ohne weitere Parameter für die JVM. Dieser Prozess heißt "java.exe" (in Windows) und hat ~20K Speicher, hauptsächlich wegen der JVM.
Das ist soweit kein Problem.

Aus dieser Anwendung heraus starte ich nun aber neue Java-Prozesse mittels
Code:
Runtime.getRuntime.exec("java pak1.pak2.MyOtherMainClass");
Geht auch wunderbar. ABER es erzeugt eben jeweils eine neue "java.exe" mit ~20K Speicher weil es eine neue JVM startet.
Gibt es hier eine Möglichkeit beide Java-Anwendungen in der gleichen JVM zu haben? Ich gebe zu, mit den JVM-Parametern habe ich mich bisher kaum beschäftigt, aber dass was ich probiert habe (Server-VM, Client-VM, Shared Mode, Mixed Mode, ...) hat hier nichts bewirkt.
 

FArt

Top Contributor
Natürlich kann man die beiden auch in einer VM laufen lassen: durch Aufruf der main-Methode der zweiten Applikation.
So aber die Theorie, die selten sinnvoll eingesetzt werden kann.

Ein System.exit() der zweiten Applikation beendet auch die "Hauptapplikation", die beiden Applikationen teilen sich statische Ressourcen, außer man hantiert auch noch mit Classloadern herum, die sowieso nötig werden, wenn sich die Klassenpfade der Applikationen stark unterscheiden usw.

Praktisch ist das also möglich, aber sehr aufwendig und nicht wirlich schön.
 
A

anonym

Gast
Ja, gibt es. Die "einfachere" ist, über einen JarClassLoader die Jar- Datei(en) der zweiten Anwendung zu laden und die main()- Methode der Main-Class aufzurufen.

Die kompliziertere ist aus beiden Jars OSGi- Bundles zu machen und dann das Bundle zu laden und zu starten.

Btw: Kann es sein, dass OSGi automatisch die DLL zweimal laden würde? Auf diesem Weg also ohne viel gehacke sein erstes Problem zu lösen wäre? Das hängt vermutlich von der OSGi- Implementierung ab, ich kenne mich leider nicht gut genug aus, um das zu beurteilen.
 

FArt

Top Contributor
Ja, gibt es. Die "einfachere" ist, über einen JarClassLoader die Jar- Datei(en) der zweiten Anwendung zu laden und die main()- Methode der Main-Class aufzurufen.
Das hört sich nur einfach an, ist aber alles andere als einfach.

Btw: Kann es sein, dass OSGi automatisch die DLL zweimal laden würde? Auf diesem Weg also ohne viel gehacke sein erstes Problem zu lösen wäre? Das hängt vermutlich von der OSGi- Implementierung ab, ich kenne mich leider nicht gut genug aus, um das zu beurteilen.
Die DLL wird vom Betriebssystem verwaltet. Sie sind genau dazu da, dass sie von mehreren Applikationen gleichzeitig verwendet werden, auch wenn das mit neueren Windosen etwas anders aussieht. Somit kann ich mir nicht vorstellen, dass man das über Javamittel beeinflussen können soll. Aber auch ich bin ja lernfähig ;-)
 
A

anonym

Gast
Das hört sich nur einfach an, ist aber alles andere als einfach.
Deshalb ja die Anführungszeichen ;)

Die DLL wird vom Betriebssystem verwaltet. Sie sind genau dazu da, dass sie von mehreren Applikationen gleichzeitig verwendet werden, auch wenn das mit neueren Windosen etwas anders aussieht. Somit kann ich mir nicht vorstellen, dass man das über Javamittel beeinflussen können soll. Aber auch ich bin ja lernfähig ;-)
Meine Idee war, dass OSGi ja bei JARs dependency- Entkopplung betreibt, also für jedes Bundle einen eigenen Classpath hat. Das würde ja für Dlls auch Sinn machen.
Aber nachdem ich gesehen habe, wie der Link von Empire Phoenix DLLs los wird, nehme ich das zurück. Mit DLLs scheint das nur auf Betriebssystemebene möglich zu sein.
 

Empire Phoenix

Top Contributor
wenne snur eine .exe gibt wird die dll nur einmal geladen, sogesehen MUSST du zwei jvms nehmen, und die eine halt ab und zu neustarten zum zurücksetzten der zustände (bzw, x wenn du die zustände noch brauchst, und die dann abschiessen wennse nicht mehr benötigt werden)

Als hinweis sei mal der security task manager genannt, der dir geladene dlls anzeigen kann, dann kannste sehen was die wohin lädt. Und demnach beurteilen was mehrfach vorhanden sein muss um die dll mehrfach zu haben.
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
R 11 GB File lesen ohne zu extrahieren Filedaten Bereich für Bereich adressieren dann mit Multi-Thread id die DB importieren Allgemeine Java-Themen 3
urmelausdemeis Exception in thread "main" java.lang.Error: Unresolved compilation problem: Allgemeine Java-Themen 7
smarterToby Wie stoppe ich diesen Thread Allgemeine Java-Themen 4
A Thread.sleep Problem Allgemeine Java-Themen 2
J Thread started nur einmal Allgemeine Java-Themen 19
W Server-Thread schreibt nicht alle Dateien Allgemeine Java-Themen 6
OnDemand Logfile pro User / Thread Allgemeine Java-Themen 7
OnDemand Thread / Service abbrechen Allgemeine Java-Themen 3
Thallius Ist meine static Helper Class Thread save? Allgemeine Java-Themen 9
P Swing Exception in thread "AWT-EventQueue-0" java.lang.IndexOutOfBoundsException: npoints > xpoints.length || npoints > ypoints.length Allgemeine Java-Themen 5
B Thread.sleep() in EJB Container wie lösen? Allgemeine Java-Themen 11
S Ist das Neuzuweisen von Feldern atomic und damit Thread-Safe? Allgemeine Java-Themen 2
S Exception in thread "main" java.lang.NullPointerException at FamilienApp.main(FamilienApp.java:15) Allgemeine Java-Themen 1
J Einen Thread in einer Schleife Allgemeine Java-Themen 2
E HILFE !! Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/commons/io/FileUtils Allgemeine Java-Themen 4
Flynn Thread-Problem... Allgemeine Java-Themen 2
G Thread-Programmierung Allgemeine Java-Themen 5
S Datei wird nicht gefunden Thread.currentThread().getContextClassLoader().getResourceAsStream() Allgemeine Java-Themen 1
G Beendet sich der Thread selbst?! Allgemeine Java-Themen 3
mrbig2017 Sleep wird ignoriert und der Thread wartet nicht Allgemeine Java-Themen 1
S Thread beenden Allgemeine Java-Themen 9
M Array aus Thread Objekten erstellen Allgemeine Java-Themen 2
Aruetiise Swing JOptionPane ohne denn Thread zu pausieren Allgemeine Java-Themen 1
M Nanosekunden-Pause innerhalb einen Thread-Loops Allgemeine Java-Themen 3
E Thread Exception Allgemeine Java-Themen 6
javaerd Binomialkoeffizient ausrechnen, Exception in thread "main" java.lang.StackOverflowError Allgemeine Java-Themen 6
T Merkwürdiges Thread-Verhalten Allgemeine Java-Themen 6
K Thread Problem Allgemeine Java-Themen 6
W Thread sleep 30 sekunden - wenn keine Antwort bis dahin neu senden Allgemeine Java-Themen 2
H Thread bleibt stehen bei jar in jar Allgemeine Java-Themen 1
J Threads HTTP Request (Thread) dauert lange - in Android Allgemeine Java-Themen 3
F CPU Last eines Thread ausfindig machen Allgemeine Java-Themen 0
V Compiler-Fehler Exception in thread "AWT-EventQueue-0" java.lang.IndexOutOfBoundsException: Index: 125, Size: 125 Allgemeine Java-Themen 11
Tausendsassa Threads Einen Thread sich selbst schließen lassen Allgemeine Java-Themen 17
P Threads BufferedImage, Thread Concurrency Allgemeine Java-Themen 1
M Klasse in separaten Thread ausführen.Wie genau? Allgemeine Java-Themen 2
llabusch Thread blockiert Dialog Allgemeine Java-Themen 1
J Thread wait() Allgemeine Java-Themen 2
V Thread.sleep und InterruptedException? Allgemeine Java-Themen 1
G Thread nicht von GC zerstört Allgemeine Java-Themen 6
J Wie erschaffe ich einen sicheren Datenaustausch zwischen Thread und Nicht-Threads Allgemeine Java-Themen 8
Sogomn Thread blocken bis Taste gedrückt Allgemeine Java-Themen 5
T Starten vom Thread Allgemeine Java-Themen 3
T Wait/Notify() bei Thread Allgemeine Java-Themen 6
J Exception in thread "main" java.lang.NoClassDefFoundError Allgemeine Java-Themen 4
M Exception in thread "AWT-EventQueue-0" Allgemeine Java-Themen 6
Q Thread wacht nicht auf Allgemeine Java-Themen 7
T Fragen zum Thread-Thema Allgemeine Java-Themen 4
T Threads Input/Output im Thread - Datei ohne Inhalt Allgemeine Java-Themen 1
T Fragen zum Thread-Thema Allgemeine Java-Themen 9
C Threads Variablen in einem Thread Aktualisieren Allgemeine Java-Themen 17
U Thread beenden Allgemeine Java-Themen 3
W Threads Mit Thread und Runtime externe Programme öffnen Allgemeine Java-Themen 0
N Thread interrupt Status debuggen Allgemeine Java-Themen 6
A Thread: Code paralell ausführen in mehreren Instanzen Allgemeine Java-Themen 1
E Threads linkedlist/multi-thread problem Allgemeine Java-Themen 3
B Erkennen, wann Prozess beendet ist, dann Thread beenden. Allgemeine Java-Themen 6
A Thread Fehler absichtlich provozieren Allgemeine Java-Themen 3
B Threads Java Thread kommunizieren Allgemeine Java-Themen 12
N Thread Sicherheit im komplexen Datenmodell Allgemeine Java-Themen 7
K Thread richtig benutzen Allgemeine Java-Themen 3
K Exception in thread "AWT-EventQueue-1" Allgemeine Java-Themen 2
vandread Problem bei kleiner Thread-Übung Allgemeine Java-Themen 2
G Thread erzeugt nicht plausible NullPointerException Allgemeine Java-Themen 7
H Netbeans Warning bei Thread.sleep in Schleife Allgemeine Java-Themen 4
P [Thread] Scheint nicht Sequenziell zu Arbeiten Allgemeine Java-Themen 9
A eine test thread.join() frage Allgemeine Java-Themen 2
tuttle64 Verständnisprobleme mit Thread Locks Allgemeine Java-Themen 4
G Threads Thread bei Datenabfrage Allgemeine Java-Themen 3
S Thread anhalten per Button ? Allgemeine Java-Themen 3
E Thread Programmierung Allgemeine Java-Themen 2
S Threads ServerSocket-Thread soll schlafen, bis er gebraucht wird Allgemeine Java-Themen 2
V Thread schneller stoppen Allgemeine Java-Themen 2
V anstatt thread.join() einfach while schleife? Allgemeine Java-Themen 8
B Mausbewegung im Thread erkennen (hoch/runter) Allgemeine Java-Themen 6
G Linux/C++/Pthreads auf JVM zugreifen, thread safe? Allgemeine Java-Themen 10
K Threads Probleme mit Thread Allgemeine Java-Themen 13
K Threads Thread überprüfen Allgemeine Java-Themen 3
Z Threads Thread für einen Client Allgemeine Java-Themen 9
M Thread JavaFish Allgemeine Java-Themen 10
G Thread.sleep Allgemeine Java-Themen 12
M Threads Viele Aufrufe aus Thread, komisches Verhalten Allgemeine Java-Themen 8
B Threads Main Thread warten auf abgebrochen Task warten lassen Allgemeine Java-Themen 25
K Timer Thread Allgemeine Java-Themen 8
M Methoden Static Methoden und Thread??? Allgemeine Java-Themen 4
N java.lang.IllegalMonitorStateException: object not locked by thread before notify() Allgemeine Java-Themen 2
C Mehothode in anderenm Thread aufrufen Allgemeine Java-Themen 10
R Thread läuft nicht?! Allgemeine Java-Themen 7
R ThreadPool - vorhandene thread liste überprüfen bzw. aufräumen Allgemeine Java-Themen 3
J Anderem Thread Variable mitgeben Allgemeine Java-Themen 2
C Argument an einen Thread übergeben Allgemeine Java-Themen 4
S java.util.ConcurrentModificationException - aber nur ein Thread Allgemeine Java-Themen 3
G JUnit Test Methoden in anderen Thread verlagern Allgemeine Java-Themen 4
P Java Probleme - java.lang.Thread.run(Unkown Source) Allgemeine Java-Themen 10
L Im Thread auf Eingaben warten Allgemeine Java-Themen 3
P aus Thread auf Form zugreifen Allgemeine Java-Themen 9
C Threads Thread blockieren Allgemeine Java-Themen 4
K Threads Thread für Sleep Allgemeine Java-Themen 6
H Threads Thread stirbt aber Objekte in ihm leben weiter?! Allgemeine Java-Themen 9
K Threads Thread aktualisiert Progressbar nicht Allgemeine Java-Themen 4

Ähnliche Java Themen

Neue Themen


Oben