Pourquoi ne peux-je pas lire depuis / dev / urandom sous OSX?

35

Un collègue a suggéré de créer une clé aléatoire via la commande suivante:

tr -dc A-Za-z0-9_\!\@\#\$\%\^\&\*\(\)-+= < /dev/urandom | head -c 32 | xargs

Cela m'a donné l'erreur:

tr: séquence d'octets illégale

Je crains de ne pas avoir /dev/urandomsur mon système. J'ai essayé de googler pour savoir comment installer ce fichier, mais je suis arrivé vide. J'ai essayé locate urandomet suis aussi venu vide. (bon en fait, il a trouvé la page de manuel, mais ça n'aide pas)

Comment puis-je faire urandomsur mon système Mac OSX? (Lion)

Kirk Woll
la source
3
Utilisation intéressante de xargs...
sendmoreinfo

Réponses:

49

D'après le message d'erreur que vous obtenez, je ne pense pas que le problème réside dans / dev / urandom. Si c'était le cas, je m'attendrais à une erreur du type "aucun fichier ni répertoire".

J'ai cherché le message d'erreur que vous avez eu et trouvé ceci, ce qui semble pouvoir être pertinent pour votre problème: http://nerdbynature.de/s9y/2010/04/11/tr-Illegal-byte-sequence

En gros, spécifiez les paramètres régionaux en ajoutant la trcommande en ajoutant LC_CTYPE=C:

LC_CTYPE=C tr -dc A-Za-z0-9_\!\@\#\$\%\^\&\*\(\)-+= < /dev/urandom | head -c 32 | xargs
lk-
la source
Merci, ça a vraiment fait l'affaire. Une idée pourquoi je ne peux pas trouver urandomou random? S'agit-il de "fichiers" magiques spéciaux qui n'existent pas sur le système de fichiers actuel? (Aussi, j'ai suggéré une modification pour aider à atténuer le lien-pourriture)
Kirk Woll
1
Je crois locateque la recherche ne se fait pas directement dans votre système de fichiers, mais plutôt dans votre base de données pré-construite. Cette base de données est probablement configurée pour ignorer / dev / et d'autres systèmes de fichiers «spéciaux».
lk-
assez bien, mais je ne le vois pas quand je regarde directement dans /dev. Allez comprendre. Mais merci encore pour l'aide.
Kirk Woll
1
ne semble pas fonctionner sur 10.9; échoue toujours avec le même message d'erreur. LC_ALL=Cfait le tour tho.
Erik Kaplun
1
Veuillez modifier ce lien vers nerdbynature.de/s9y/2010/04/11/tr-Illegal-byte-sequence car il pointe actuellement vers la page de blog la plus récente ne contenant pas les trinformations.
Jeroen Wiert Pluimers
11

Vos trtentatives d’interpréter ses entrées en tant que texte au format UTF-8. Donc, il va se plaindre et abandonner sur la première séquence d'octets qui n'est pas valide UTF-8. Le préfixe travec LC_ALL=Cou LC_CTYPE=Cexportera cette variable dans l'environnement de tr, modifiant ainsi l'idée du jeu de caractères local sur le standard C, autrement dit, tout n'est qu'une séquence d'octets opaques.

Au fait, la séquence \)-+dans votre commande est-elle intentionnelle? Cela inclut *également ce que vous avez déjà inclus, mais ne s’inclut pas -comme vous le souhaitiez. Mieux vaut écrire un de ceux-ci à la place:

LC_ALL=C tr -dc 'A-Za-z0-9_!@#$%^&*()\-+=' < /dev/urandom
LC_CTYPE=C tr -dc A-Za-z0-9_\!\@\#\$\%\^\&\*\(\)\\-+= < /dev/urandom
MvG
la source
6

Comme d'autres l'ont indiqué, votre problème n'est pas ce qui /dev/urandommanque, mais plutôt comment trfonctionne sur OS X. Au lieu de jouer avec l'environnement, utilisez perlà la place de tr:

perl -pe 'binmode(STDIN, ":bytes"); tr/A-Za-z0-9_\!\@\#\$\%\^\&\*\(\)-+=//dc;' < /dev/urandom | head -c 32; echo

Cela présente l'avantage d'être portable sous OS X, Redhat et Ubuntu.

(J'ai aussi enlevé le tuyau pour xargsremplacer sorcière echo, pour obtenir une nouvelle ligne à la fin de la sortie.)

Trenton
la source
Tôt ou tard, je m'attends à ce que Perl rende binmode ":utf8"standard, à quel point votre solution Perl aura le même problème que celui- trci.
Marc
Répondez aux préoccupations de Mark en ajoutant binmode (STDIN, ": bytes") à l'exemple de code.
Trenton
2

Premièrement, aviez-vous l'intention d'inclure -ou *dans la liste des caractères valides? Le paramètre à trinclure la séquence )-+qui signifie "la plage d'octets commençant par )et se terminant par +, qui est en réalité )*+.

Deuxièmement, plutôt que de lire plusieurs kilo-octets dans le pool d'entropie du noyau (et de marquer ainsi le pool entier comme non sécurisé, ce qui affectera tout autre processus nécessitant une entropie sécurisée), envisagez de lire uniquement le nombre de bits dont vous avez besoin: utilisez-le head -c...comme première étape, puis traduisez plutôt que de supprimer les caractères indésirables.

Cette version particulière du problème est un peu inhabituelle car elle utilise 76 symboles différents; la plupart veulent juste des caractères alphanumériques, donc si vous êtes satisfait de seulement 64 symboles, alors l’ base64utilitaire minimisera la consommation du pool d’entropie (notez que 24 correspond à 6/8 sur 32):

head -c24 < /dev/random | base64
Martin Kealey
la source
1

Le codage de caractères de votre environnement local (avec lequel vous pouvez dire locale charmap) est un octet sur plusieurs octets.

Le plus courant de nos jours est UTF-8, où les caractères peuvent être codés sur 1 à 4 octets. Toutes les séquences d'octets ne forment pas des caractères valides dans UTF-8. Chaque caractère non-ASCII dans UTF-8 commence par un octet contenant les deux bits les plus élevés et indique le nombre d'octets avec le bit le plus élevé (mais pas le deuxième) suivi.

/dev/urandomcontient un flux aléatoire d'octets. trtransliterates caractère, il doit donc décoder ces octets en tant que caractères. Les caractères ASCII de votre plage sont tous codés sur un caractère dans UTF-8, mais trdoivent encore décoder tous les caractères. Il existe par exemple d'autres codages sur plusieurs octets dans lesquels certains caractères ne Acontiennent pas l'octet 0x41 (le code pour A).

Parce que ce flux d'octets aléatoire est lié à contenir des séquences non valides (par exemple, un octet 0x80 seul n'est pas valide dans UTF-8 puisqu'un caractère non-ASCII doit commencer par un octet supérieur à 0xc1 (0xc0 et 0xc1 ne sont pas en UTF- 8 caractère)), trrenvoie donc une erreur lorsque cela se produit.

Ce que vous voulez ici, c'est considérer ce flux d'octets comme des caractères dans un codage comportant un octet par caractère. Quelle que soit l'option choisie, tous les caractères de votre plage (en supposant par AZ, vous vouliez dire ABCDEFGHIJKLMNOPQRSTUVWXYZ et non des choses comme Ý, Ê) font partie du jeu de caractères portable afin d'être codés de la même manière dans tous les jeux de caractères pris en charge sur votre système.

Pour cela, vous devez créer la LC_CTYPEvariable de localisation qui est celui qui décide qui charset est utilisé et ce que les choses comme blank, les alphaclasses de caractères contiennent. Mais pour la définition de la plage AZ, vous voudrez également définir la LC_COLLATEvariable (celle qui décide du classement des chaînes).

La locale Caka POSIXest celle qui garantit que les caractères sont des octets simples et AZ est ABCDEFGHIJKLMNOPQRSTUVWXYZ. Vous pourriez faire:

 LC_CTYPE=C LC_COLLATE=C tr -dc 'A-Za-z0-9_!@#$%^&*()+=-'

(ici déplacer le -à la fin, sinon, )-+serait prendre comme une gamme comme A-Z)

Mais notez que la LC_ALLvariable de l' emporte sur toutes les autres LC_*et les LANGvariables. Donc, si LC_ALLest déjà défini, ce qui précède n'aura aucun effet. Donc, au lieu de cela, vous pouvez simplement faire:

 LC_ALL=C tr -dc 'A-Za-z0-9_!@#$%^&*()+=-'

Cela affectera d'autres éléments, tels que la langue des messages d'erreur, mais le changement de LC_CTYPE aurait peut-être déjà posé problème pour les messages d'erreur (par exemple, aucun moyen d'exprimer des messages d'erreur en russe ou en japonais dans le jeu de caractères de la langue C).

Stéphane Chazelas
la source
0

Selon la page de manuel , / dev / random suffira probablement à vos besoins. Peut-être qu'Apple a cessé de créer le fichier / dev / urandom parce que c'est inutile?

jsbillings
la source
Je n'ai pas non /dev/randomplus.
Kirk Woll
MacOSX devrait avoir à la fois / dev / random et / dev / urandom. Peut-être qu'Apple n'inclut plus ces fichiers spéciaux? Ou peut-être que c'est seulement là si vous installez XCode?
jsbillings
1
FWIW, les deux périphériques sont présents sur mon poste de travail Lion mis à niveau par Lion. Je crois que c'était aussi présent sur Lion. Les nœuds sont également différents (13,0 contre 13,1)
mrb