Ganz einfach, kann eine Instanz von javax.crypto.Cipher
(z.B Cipher.getInstance("RSA")
) aus mehreren Threads verwendet werden, oder muss ich mehrere davon in einen stecken ThreadLocal
(in meinem Fall)?
Ist Cipher Thread-sicher?
Bart van Heukelom
BalusC
Nein, ist es nicht. Die Instanz ist zustandsbehaftet. Sie müssen es also threadlokal speichern oder bei jedem Verschlüsselungs-/Entschlüsselungsaufruf eine neue Instanz erhalten oder es in eine synchronized(cipher)
Block.
Threadsafety wird normalerweise in Javadocs als “ist threadsicher” oder “ist nicht Thread sicher“. Dies ist nicht der Fall für Cipher
also sollten Sie nicht davon ausgehen, dass es threadsicher ist.
Paulo Ebermann
Selbst wenn eine Cipher Thread-sicher wäre, wäre es nicht wirklich sinnvoll, sie von mehreren Threads gleichzeitig zu verwenden.
Die Bytes, die Sie in die Chiffre einfügen und aus ihr herausholen (über its update
und finish
Methoden) sind ein kontinuierlicher Strom. Das bedeutet, dass sie am anderen Ende in der gleichen Reihenfolge übergeben werden müssen, um einen Sinn zu ergeben. Dies ist am einfachsten zu erreichen, wenn Sie nur einen Thread haben, der dies tut.
Wenn Sie mehrere Threads verwenden, möchten Sie normalerweise anrufen reset
zwischen den Anrufen – und dann benötigen Sie sowieso eine externe Synchronisation.
Ich würde keine Cipher-Objekte aus mehreren Threads ohne Synchronisierung verwenden. Wenn Sie sich die API ansehen, gibt es Methoden, die nur funktionieren können, indem Sie den internen Zustand ändern, wie z init()
und update()
. Das macht sie implizit nicht Thread-sicher.
-
Aus JavaDocs for Cipher init(): „Beachten Sie, dass ein Cipher-Objekt bei der Initialisierung alle zuvor erfassten Zustände verliert. Mit anderen Worten, das Initialisieren einer Cipher entspricht dem Erstellen einer neuen Instanz dieser Cipher und deren Initialisierung.“ docs.oracle.com/javase/7/docs/api/javax/crypto/…
– Darrell Teague
23. März 2016 um 14:23 Uhr
-
Richtig gesagt @ddso
– Rachit Sharma
30. Juni 2021 um 4:07 Uhr
Cipher ist nicht threadsicher.
Wenn Sie aus Leistungsgründen Multithreading verwenden und keine Synchronisierung durchführen möchten, können Sie Jasypt (http://www.jasypt.org/general-usage.html) Es hat gepoolte Verschlüsselungsprogramme: PooledPBEByteEncryptor, PooledPBEStringEncryptor.
Wenn die Synchronisierung für Sie in Ordnung ist und Sie Spring verwenden. Sie können Verschlüsselungsprogramme (https://docs.spring.io/spring-security/site/docs/4.2.5.RELEASE/apidocs/org/springframework/security/crypto/encrypt/Encryptors.html). Sie synchronisieren intern, um auf Cipher zuzugreifen.