Estou investigando um problema em que a criptografia de um dispositivo de bloco impõe uma enorme penalidade de desempenho ao gravá -lo. Horas de leitura e experiências na Internet não me proporcionaram um entendimento adequado, muito menos uma solução.
A questão é resumida: por que obtenho velocidades de gravação perfeitamente rápidas ao colocar um btrfs em um dispositivo de bloco (~ 170MB / s), enquanto a velocidade de gravação cai (~ 20MB / s) ao colocar um dm-crypt / LUKS entre o sistema de arquivos e dispositivo de bloco, embora o sistema seja mais do que capaz de sustentar uma taxa de transferência de criptografia suficientemente alta?
Cenário
/home/schlimmchen/random
é um arquivo de 4,0 GB preenchido com dados /dev/urandom
anteriores.
dd if=/dev/urandom of=/home/schlimmchen/Documents/random bs=1M count=4096
Lê-lo é super rápido:
$ dd if=/home/schlimmchen/Documents/random of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 6.58036 s, 648 MB/s
$ dd if=/home/schlimmchen/Documents/random of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 0.786102 s, 5.4 GB/s
(na segunda vez, o arquivo foi obviamente lido do cache).
Btrfs não criptografados
O dispositivo é formatado diretamente com btrfs (nenhuma tabela de partição no dispositivo de bloco).
$ sudo mkfs.btrfs /dev/sdf
$ sudo mount /dev/sdf /mnt
$ sudo chmod 777 /mnt
A velocidade de gravação chega a ~ 170MB / s:
$ dd if=/home/schlimmchen/Documents/random of=/mnt/dd-test1 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 27.1564 s, 157 MB/s
$ dd if=/home/schlimmchen/Documents/random of=/mnt/dd-test2 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 25.1882 s, 169 MB/s
$ dd if=/home/schlimmchen/Documents/random of=/mnt/dd-test3 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 29.8419 s, 143 MB/s
A velocidade de leitura está bem acima de 200 MB / s.
$ dd if=/mnt/dd-test1 of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 19.8265 s, 215 MB/s
$ dd if=/mnt/dd-test2 of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 19.9821 s, 213 MB/s
$ dd if=/mnt/dd-test3 of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 19.8561 s, 215 MB/s
Btrfs criptografados no dispositivo de bloco
O dispositivo está formatado com LUKS e o dispositivo resultante está formatado com btrfs:
$ sudo cryptsetup luksFormat /dev/sdf
$ sudo cryptsetup luksOpen /dev/sdf crypt
$ sudo mkfs.btrfs /dev/mapper/crypt
$ sudo mount /dev/mapper/crypt /mnt
$ sudo chmod 777 /mnt
$ dd if=/home/schlimmchen/Documents/random of=/mnt/dd-test1 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 210.42 s, 20.3 MB/s
$ dd if=/home/schlimmchen/Documents/random of=/mnt/dd-test2 bs=1M
4265841146 bytes (4.3 GB) copied, 207.402 s, 20.6 MB/s
A velocidade de leitura sofre apenas um pouco (por que isso acontece?):
$ dd if=/mnt/dd-test1 of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 22.2002 s, 192 MB/s
$ dd if=/mnt/dd-test2 of=/dev/null bs=1M
4265841146 bytes (4.3 GB) copied, 22.0794 s, 193 MB/s
luksDump: http://pastebin.com/i9VYRR0p
Btrfs criptografados no arquivo btrfs no dispositivo de bloco
A velocidade de gravação "dispara" para mais de 150 MB / s ao gravar em um arquivo criptografado. Coloquei um btrfs no dispositivo de bloco, aloquei um arquivo de 16GB que eu lukfsFormat
montei e montei.
$ sudo mkfs.btrfs /dev/sdf -f
$ sudo mount /dev/sdf /mnt
$ sudo chmod 777 /mnt
$ dd if=/dev/zero of=/mnt/crypted-file bs=1M count=16384 conv=fsync
17179869184 bytes (17 GB) copied, 100.534 s, 171 MB/s
$ sudo cryptsetup luksFormat /mnt/crypted-file
$ sudo cryptsetup luksOpen /mnt/crypted-file crypt
$ sudo mkfs.btrfs /dev/mapper/crypt
$ sudo mount /dev/mapper/crypt /tmp/nested/
$ dd if=/home/schlimmchen/Documents/random of=/tmp/nested/dd-test1 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 26.4524 s, 161 MB/s
$ dd if=/home/schlimmchen/Documents/random of=/tmp/nested/dd-test2 bs=1M conv=fsync
4265841146 bytes (4.3 GB) copied, 27.5601 s, 155 MB/s
Por que o desempenho de gravação está aumentando assim? O que esse aninhamento específico de sistemas de arquivos e dispositivos de bloco alcança para ajudar em altas velocidades de gravação?
Configuração
O problema é reproduzível em dois sistemas executando a mesma distribuição e kernel. No entanto, também observei as baixas velocidades de gravação no kernel 3.19.0 no System2.
- Equipamento: SanDisk Extreme 64GB USB3.0 USB Stick
- System1: Intel NUC 5i5RYH, i5-5250U (Broadwell), 8 GB de RAM, SSD Samsung 840 EVO 250 GB
- System2: Lenovo T440p, i5-4300M (Haswell), 16 GB de RAM, SSD Samsung 850 PRO 256 GB
- Distro / Kernel: Debian Jessie, 3.16.7
- cryptsetup: 1.6.6
/proc/crypto
para System1: http://pastebin.com/QUSGMfiScryptsetup benchmark
para System1: http://pastebin.com/4RxzPFeT- btrfs (-tools) é a versão 3.17
lsblk -t /dev/sdf
: http://pastebin.com/nv49tYWc
Pensamentos
- Alinhamento não é a causa, tanto quanto eu posso ver. Mesmo se o tamanho da página do stick for 16KiB, o início da carga útil da criptografia é alinhado a 2MiB de qualquer maneira.
--allow-discards
(para luksOpen do cryptsetup) não ajudou, como eu esperava.- Ao fazer muito menos experimentos com ele, observei um comportamento muito semelhante com um disco rígido externo, conectado através de um adaptador USB3.0.
- Parece-me que o sistema está escrevendo blocos de 64KiB. Um script de armadilha do sistema que tentei indica isso pelo menos.
/sys/block/sdf/stat
apoia essa hipótese, já que muitas gravações são mescladas. Então, meu palpite é que escrever em blocos muito pequenos não é a causa. - Não teve sorte alterar o agendador de filas do dispositivo de bloco para NOOP.
- Colocar a cripta em um volume LVM não ajudou.