Você está observando uma combinação do comportamento peculiar de dd
com o comportamento peculiar do /dev/random
do Linux. Ambos, a propósito, raramente são a ferramenta certa para o trabalho.
O /dev/random
do Linux retorna dados com moderação. Baseia-se no pressuposto de que a entropia no gerador de números pseudo-aleatórios se extingue a uma taxa muito rápida. Como a coleta de nova entropia é lenta, /dev/random
geralmente desiste apenas alguns bytes de cada vez.
dd
é um programa antigo e mal-humorado inicialmente destinado a operar em dispositivos de fita. Quando você diz para ler um bloco de 1kB, ele tenta ler um bloco. Se a leitura retornar menos de 1024 bytes, difícil, é tudo que você recebe. Portanto, dd if=/dev/random bs=1K count=2
faz duas chamadas read(2)
. Como ele está lendo /dev/random
, as duas chamadas read
normalmente retornam apenas alguns bytes, em número variável, dependendo da entropia disponível. Veja também Quando o dd é adequado para copiar dados? (ou, quando são lidos () e escritos () parciais)
A menos que esteja projetando um instalador ou clonador de sistema operacional, você nunca deve usar /dev/random
no Linux, sempre /dev/urandom
. A página urandom
man é um tanto enganadora; /dev/urandom
é de fato adequado para criptografia, até mesmo para gerar chaves de longa duração. A única restrição com /dev/urandom
é que ela deve ser fornecida com entropia suficiente; As distribuições Linux normalmente salvam a entropia entre as reinicializações, portanto, a única vez em que você pode não ter entropia suficiente é em uma instalação nova. A entropia não se desgasta em termos práticos. Para obter mais informações, leia É um rand de / dev / urandom secure para uma chave de login? e Feeding / dev / pool de entropia aleatória? .
A maioria dos usos de dd
é melhor expressa com ferramentas como head
ou tail
. Se você quiser 2kB de bytes aleatórios, execute
head -c 2k </dev/urandom >rand
Com kernels mais antigos do Linux, você pode se safar com
dd if=/dev/urandom of=rand bs=1k count=2
porque /dev/urandom
felizmente retornou quantos bytes foram solicitados. Mas isso não é mais verdade desde o kernel 3.16, está agora limitado a 32MB .
Em geral, quando você precisa usar dd
para extrair um número fixo de bytes e sua entrada não vem de um arquivo ou dispositivo de bloco comum, você precisa ler byte por byte: dd bs=1 count=2048
.