45 votes

Les UUID aléatoires de Java sont-ils prévisibles ?

Je voudrais utiliser une clé primaire cryptographiquement sécurisée pour les données sensibles d'une base de données. Cette clé ne peut pas être devinée/prévisible et ne peut pas être générée par la base de données (j'ai besoin de la clé avant la persistance de l'objet).

Je sais que Java utilise un UUID de type 4 avec un générateur de nombres aléatoires cryptographiquement sécurisé, mais je sais que l'UUID n'est pas complètement aléatoire. Ma question est donc de savoir s'il est sûr de supposer que les UUID ne peuvent pas être prédits à partir d'un ensemble d'UUID existants.

35voto

Robert Points 10865

Si vous voulez savoir à quel point un UUID est aléatoire, vous devez regarder à la source.

La section de code suivante est tirée de OpenJDK7 (et il est identique dans OpenJDK6 ):

public static UUID randomUUID() {
        SecureRandom ng = numberGenerator;
        if (ng == null) {
            numberGenerator = ng = new SecureRandom();
        }

        byte[] randomBytes = new byte[16];
        ng.nextBytes(randomBytes);
        randomBytes[6]  &= 0x0f;  /* clear version        */
        randomBytes[6]  |= 0x40;  /* set to version 4     */
        randomBytes[8]  &= 0x3f;  /* clear variant        */
        randomBytes[8]  |= 0x80;  /* set to IETF variant  */
        return new UUID(randomBytes);
    }

Comme vous pouvez le voir, seuls 2 des 16 octets ne sont pas complètement aléatoires. Dans le sixième octet, vous perdez 4 des 8 bits et dans l'octet 8, vous perdez 2 bits de caractère aléatoire.

Vous obtiendrez donc une valeur de 128 bits avec un caractère aléatoire de 122 bits.

Le seul problème que peut poser cette manipulation est qu'il y a de fortes chances que vos données soient identifiées comme un UUID. Par conséquent, si vous voulez le cacher dans d'autres données aléatoires, cela ne fonctionnera pas...

3voto

Peter Lawrey Points 229686

Si vous souhaitez générer une clé aléatoire sécurisée, je vous suggère d'utiliser SecureRandom. Il peut générer une clé de n'importe quel nombre de bits dont vous avez besoin. Il est plus lent que Random, mais beaucoup plus sûr.

2voto

MarianP Points 1303

J'ai toujours pensé que la note Javadoc sur le "générateur de nombres aléatoires cryptographiquement sécurisé" (en fait, le "générateur de nombres pseudo-aléatoires cryptographiquement fort") répondait à cette question.

http://download.oracle.com/javase/1,5.0/docs/api/java/util/UUID.html#randomUUID ()

Ce que dit Wikipedia http://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator une telle prédiction serait un algorithme non polynomial.

Si vous avez besoin de quelque chose de 'réellement' et pas seulement de 'pseudo' aléatoire, vous devez utiliser quelque chose d'externe, un générateur de bruit matériel, des points aléatoires générés après le déplacement d'une souris,...

EntropyPool semble aider, mais je ne l'ai pas encore essayé. http://random.hd.org/ D'après ce que j'ai compris, ça te laisse télécharger des bruits du monde réel et l'utiliser dans votre application Java. Il n'est pas connecté à l'api java.util.UUID, cependant, il pourrait probablement être branché en utilisant l'api nameUUIDFromBytes (ou autre ?).

Ce serait cool si vous nous faisiez savoir quelle voie vous avez choisi.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X