Время от времени мне говорят, что для увеличения скорости «dd» я должен тщательно выбирать правильный «размер блока».
Даже здесь, на ServerFault, кто-то другой написал который "... оптимальный размер блока зависит от оборудования ..." (iain) или "... идеальный размер будет зависеть от вашей системной шины, контроллера жесткого диска, конкретного диска и драйверов для каждого из них ..." (chris-s)
Поскольку мои ощущения были немного другими (Кстати: я думал, что время, необходимое для глубокой настройки параметра bs, было намного выше, чем полученное усиление, с точки зрения экономии времени, и что значение по умолчанию было разумным.), сегодня я прошел несколько быстрых тестов.
Чтобы снизить внешние воздействия, я решил прочитать:
и:
В следующей таблице я сообщил о своих выводах, прочитав 1 ГБ данных с разными значениями «bs» (вы можете найти необработанные числа в конце этого сообщения):
В основном выходит, что:
MMC: с bs = 4 (да! 4 байта) я достиг пропускной способности 12 МБ / с. Не такие уж далекие значения относительно максимума 14,2 / 14,3, которые я получил от bs = 5 и выше;
HDD: с bs = 10 я достиг 30 МБ / с. Конечно, меньше, чем 95,3 МБ со значением по умолчанию bs = 512, но ... тоже значительным.
Кроме того, было очень ясно, что системное время CPU было обратно пропорционально значению bs (но это звучит разумно, поскольку чем ниже bs, тем больше количество системных вызовов, генерируемых dd).
Сказав все вышесказанное, теперь вопрос: может ли кто-нибудь объяснить (хакер ядра?), Какие основные компоненты / системы участвуют в такой пропускной способности, и действительно ли стоит усилий указать bs выше, чем по умолчанию?
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=1M count=1000
1000+0 record dentro
1000+0 record fuori
1048576000 byte (1,0 GB) copiati, 74,1239 s, 14,1 MB/s
real 1m14.126s
user 0m0.008s
sys 0m1.588s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=1k count=1000000
1000000+0 record dentro
1000000+0 record fuori
1024000000 byte (1,0 GB) copiati, 72,7795 s, 14,1 MB/s
real 1m12.782s
user 0m0.244s
sys 0m2.092s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=512 count=2000000
2000000+0 record dentro
2000000+0 record fuori
1024000000 byte (1,0 GB) copiati, 72,867 s, 14,1 MB/s
real 1m12.869s
user 0m0.324s
sys 0m2.620s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=10 count=100000000
100000000+0 record dentro
100000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 70,1662 s, 14,3 MB/s
real 1m10.169s
user 0m6.272s
sys 0m28.712s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=5 count=200000000
200000000+0 record dentro
200000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 70,415 s, 14,2 MB/s
real 1m10.417s
user 0m11.604s
sys 0m55.984s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=4 count=250000000
250000000+0 record dentro
250000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 80,9114 s, 12,4 MB/s
real 1m20.914s
user 0m14.436s
sys 1m6.236s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=2 count=500000000
500000000+0 record dentro
500000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 161,974 s, 6,2 MB/s
real 2m41.976s
user 0m28.220s
sys 2m13.292s
root@iMac-Chiara:/tmp# time dd if=/dev/sdc of=/dev/null bs=1 count=1000000000
1000000000+0 record dentro
1000000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 325,316 s, 3,1 MB/s
real 5m25.318s
user 0m56.212s
sys 4m28.176s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=1 count=1000000000
1000000000+0 record dentro
1000000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 341,461 s, 2,9 MB/s
real 5m41.463s
user 0m56.000s
sys 4m44.340s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=2 count=500000000
500000000+0 record dentro
500000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 164,072 s, 6,1 MB/s
real 2m44.074s
user 0m28.584s
sys 2m14.628s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=4 count=250000000
250000000+0 record dentro
250000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 81,471 s, 12,3 MB/s
real 1m21.473s
user 0m14.824s
sys 1m6.416s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=5 count=200000000
200000000+0 record dentro
200000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 66,0327 s, 15,1 MB/s
real 1m6.035s
user 0m11.176s
sys 0m54.668s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=10 count=100000000
100000000+0 record dentro
100000000+0 record fuori
1000000000 byte (1,0 GB) copiati, 33,4151 s, 29,9 MB/s
real 0m33.417s
user 0m5.692s
sys 0m27.624s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=512 count=2000000 skip=6000000
2000000+0 record dentro
2000000+0 record fuori
1024000000 byte (1,0 GB) copiati, 10,7437 s, 95,3 MB/s
real 0m10.746s
user 0m0.360s
sys 0m2.428s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=1k count=1000000 skip=6000000
1000000+0 record dentro
1000000+0 record fuori
1024000000 byte (1,0 GB) copiati, 10,6561 s, 96,1 MB/s
real 0m10.658s
user 0m0.164s
sys 0m1.772s
root@iMac-Chiara:/tmp# time dd if=/dev/sda3 of=/dev/null bs=1M count=1000 skip=7000
1000+0 record dentro
1000+0 record fuori
1048576000 byte (1,0 GB) copiati, 10,7391 s, 97,6 MB/s
real 0m10.792s
user 0m0.008s
sys 0m1.144s
Вы сделали только тест скорости чтения. если вы фактически копируете блоки на другое устройство, у вас есть паузы в чтении, в то время как другое устройство принимает данные, которые вы хотите записать, когда это произойдет, вы можете столкнуться с проблемами задержки вращения на устройстве чтения (если это жесткий диск) и т. часто значительно быстрее читать 1M фрагментов с жесткого диска, поскольку таким образом вы реже сталкиваетесь с задержкой вращения.
Я знаю когда я копирование жесткие диски я получаю более высокую скорость, указав bs=1M
чем с помощью bs=4k
или по умолчанию. Я говорю об улучшении скорости от 30 до 300 процентов. Нет необходимости настраивать его на лучшее, если только это не все, что вы делаете каждый день. но выбор чего-то лучшего, чем стандартное, может сократить время выполнения на несколько часов.
Когда вы используете его по-настоящему, попробуйте несколько разных чисел и отправьте dd
обработать SIGUSR1
сигнал, чтобы заставить его выдать отчет о состоянии, чтобы вы могли видеть, как это происходит.
✗ killall -SIGUSR1 dd
1811+1 records in
1811+1 records out
1899528192 bytes (1.9 GB, 1.8 GiB) copied, 468.633 s, 4.1 MB/s
Что касается внутреннего жесткого диска, по крайней мере - при чтении с устройства блочный слой по крайней мере должен получить один сектор размером 512 байт.
Таким образом, при обработке 1-байтового чтения вы действительно читаете с диска только выровненное по сектору байтовое извлечение. Остальные 511 раз обслуживаются кешем.
Вы можете доказать это следующим образом, в этом примере sdb
интересующий диск:
# grep sdb /proc/diskstats
8 16 sdb 767 713 11834 6968 13710 6808 12970792 6846477 0 76967 6853359
...
# dd if=/dev/sdb of=/dev/null bs=1 count=512
512+0 records in
512+0 records out
512 bytes (512 B) copied, 0.0371715 s, 13.8 kB/s
# grep sedb /proc/diskstats
8 16 sdb 768 713 11834 6968 13710 6808 12970792 6846477 0 76967 6853359
...
Четвертый столбец (в котором подсчитываются чтения) указывает, что произошло только одно чтение, несмотря на то, что вы запросили чтение одного байта. Это ожидаемое поведение, поскольку это устройство (диск SATA 2) должно минимум вернуть размер его сектора. Ядро просто кеширует весь сектор.
Самым большим фактором, влияющим на эти запросы размера, являются накладные расходы на выполнение системного вызова для чтения или записи. Фактически, вызов <512 неэффективен. Для чтения очень больших объемов требуется меньше системных вызовов за счет использования для этого большего объема памяти.
4096 обычно является «безопасным» числом для чтения, потому что: