¿Cómo monitorea el progreso de dd?

654

ddEs una maravilla. Le permite duplicar un disco duro a otro, poner a cero completamente un disco duro, etc. Pero una vez que inicia un ddcomando, no hay nada que le informe sobre su progreso. Simplemente se sienta allí en el cursor hasta que el comando finalmente termina. Entonces, ¿cómo se monitorea el progreso de dd?

James
fuente

Respuestas:

729

Actualización 2016 : si usa GNU coreutils> = 8.24 (predeterminado en Ubuntu Xenial 16.04 hacia arriba), consulte el método 2 a continuación para ver una forma alternativa de mostrar el progreso.


Método 1: utilizando pv

Instalar pvy ponerlo entre ddcomandos de entrada / salida solamente .

Nota : no puede usarlo cuando ya comenzó dd.

A partir de la descripción del paquete :

pv- Pipe Viewer: es una herramienta basada en terminal para monitorear el progreso de los datos a través de una tubería. Se puede insertar en cualquier canalización normal entre dos procesos para dar una indicación visual de la rapidez con la que pasan los datos, cuánto tiempo han tardado, cuán cerca de su finalización y una estimación de cuánto tiempo pasará hasta su finalización.

Instalación

sudo apt-get install pv

Ejemplo

dd if=/dev/urandom | pv | dd of=/dev/null

Salida

1,74MB 0:00:09 [ 198kB/s] [      <=>                               ]

Puede especificar el tamaño aproximado con --sizesi desea una estimación de tiempo.


Ejemplo suponiendo que se copia un disco de 2GB desde / dev / sdb

Comando sin pvsería:

sudo dd if=/dev/sdb of=DriveCopy1.dd bs=4096

Comando con pv:

sudo dd if=/dev/sdb | pv -s 2G | dd of=DriveCopy1.dd bs=4096

Salida:

440MB 0:00:38 [11.6MB/s] [======>                             ] 21% ETA 0:02:19

Otros usos

Por supuesto, puede usar pvdirectamente para canalizar la salida a stdout:

pv /home/user/bigfile.iso | md5sum

Salida

50,2MB 0:00:06 [8,66MB/s] [=======>         ] 49% ETA 0:00:06

Tenga en cuenta que en este caso, pvreconoce el tamaño automáticamente.


Método 2: Nueva statusopción agregada a dd(GNU Coreutils 8.24+)

dden GNU Coreutils 8.24+ (Ubuntu 16.04 y más reciente) tiene una nueva statusopción para mostrar el progreso:

Ejemplo

dd if=/dev/urandom of=/dev/null status=progress

Salida

462858752 bytes (463 MB, 441 MiB) copied, 38 s, 12,2 MB/s
phoibos
fuente
76
pv bigfile.iso | dd de = / dev / yourdevice
Ion Br.
18
Tenga en cuenta que los parámetros para "dd" son apropiadas en la primera mitad (la parte de entrada de la tubería): dd if=/dev/zero bs=1M count=35000 | pv | dd of=VirtualDisk.raw.
Sopalajo de Arrierez
66
pv bigfile.iso | dd of=VirtualDisk.raw bs=1M count=35000obras verificadas. @SopalajodeArrierez, los parámetros se pueden dar en el segundo dd.
SiddharthaRT
11
usando pv < /dev/sda > /dev/sdbparece mejorar la velocidad ( fuente )
Nicola Feltrin
14
FYI en velocidad. Pruebas en mi computadora con Samsung 840 PRO SSD: dd if=/dev/urandom | pv | of=/dev/sdbproporciona ~ 18 MB / s de escritura, dd if=/dev/zero | pv | of=/dev/sdbproporciona ~ 80 MB / s, y la dd if=/dev/zero of=/dev/sdbversión anterior proporciona ~ 550 MB / s (cerca de la velocidad máxima de escritura SSD). Todo ello con bs=4096000.
Tedd Hansen
461

De Cómo : Monitorear el progreso de dd

Puede controlar el progreso de dd sin detenerlo utilizando el killcomando

Para ver el progreso de dduna vez que se está ejecutando, abra otra terminal e ingrese:

sudo kill -USR1 $(pgrep ^dd)

Esto mostrará el ddprogreso en la ddventana del terminal sin detener el proceso. Si estás en BSD o OS X, úsalo en INFOlugar de USR1. La USR1señal terminará dd.

Si desea recibir actualizaciones periódicas del ddprogreso, ingrese:

watch -n5 'sudo kill -USR1 $(pgrep ^dd)'

watchinvestigará el ddproceso cada -n segundos ( -n5= 5 segundos) e informará sin detenerlo.

Tenga en cuenta las comillas simples adecuadas en los comandos anteriores.

James
fuente
19
Esto funcionó, pero un par de comentarios. En primer lugar, no estoy seguro de por qué escapaste de tus backticks (si es para el editor SO, lo hiciste incorrectamente). En segundo lugar, recomendaría usar ^ dd $, en caso de que se ejecute algo más con el prefijo dd. Finalmente, no necesita sudo para enviar la señal USR1. De lo contrario, buena respuesta, +1.
gsingh2011
22
¡NÓTESE BIEN! De esta manera, las interrupciones funcionan en OSX.
Maxim Kholyavkin
26
@Speakus Debe usarlo kill -INFO $(pgrep ^dd$)en sistemas BSD (como OSX).
Torben
20
sudo pkill -usr1 ddes más fácil de recordar, funciona perfectamente bien (al menos en Ubuntu 14.04) y es menos difícil de escribir.
Phises
21
Me gusta esto porque me temo pvque ralentizará la transferencia, como lo demostró TeddHansen. Además, apuesto a que mucha gente está buscando en Google porque ya comenzaron la ddoperación;)
sudo
104

Algunos ejemplos de usos útiles con pvmenos tipeo o más progreso que otras respuestas:

Primero deberá instalar pv, con el comando:

sudo apt-get install pv

Entonces algunos ejemplos son:

pv -n /dev/urandom | dd of=/dev/null
pv -tpreb source.iso | dd of=/dev/BLABLA bs=4096 conv=notrunc,noerror

Nota: la primera muestra tiene 5 caracteres menos escribiendo entonces dd if=/dev/urandom | pv | dd of=/dev/null.

Y mi favorito para clonar una unidad de disco (reemplazar X con letras de unidad):

(pv -n /dev/sdX | dd of=/dev/sdX bs=128M conv=notrunc,noerror) 2>&1 | dialog --gauge "Running dd command (cloning), please wait..." 10 70 0

captura de pantalla

fuente: http://www.cyberciti.biz/faq/linux-unix-dd-command-show-progress-while-coping/

También por archivarme a mí mismo.

JSBach
fuente
3
deberá instalar también dialogcon el comandoapt-get install dialog
k7k0
77
Me encanta el dialogejemplo. SERENIDAD AHORA !
alex gray
¿Solo puedes llamar a ese diálogo con python?
mikeymop
1
gracias a esta respuesta, descubrí que dialogesto ayudará increíblemente a escribir scripts de shell: D
holms
2
brew install pv dialogpara Mac. También este caballero calcula con estilo. Bravo.
evilSnobu
62

Use Ctrl+ Shift+ Tmientras se ddestá ejecutando, y generará el progreso (en bytes):

load: 1.51  cmd: dd 31215 uninterruptible 0.28u 3.67s
321121+0 records in
321120+0 records out
164413440 bytes transferred in 112.708791 secs (1458745 bytes/sec)
01010101
fuente
55
No funciona para mí en Kubuntu Trusty. Posiblemente combinaciones de teclas en conflicto?
jamadagni
14
Gran manera. Funciona bajo OSX, pero no funciona bajo ubuntu 14.04
Maxim Kholyavkin
1
La primera línea es generada por el OS X, solo las últimas 3 líneas son de dd.
Itay Grudev
3
Debería poder usar kill -INFO en un BSD como OS X
macshome
3
Esto no funciona en Ubuntu. Ctrl-T / Ctrl-Shift-T solo se envía ^Tal terminal (excepto que muchas aplicaciones de terminal interceptarán Ctrl-Shift-T y abrirán una nueva pestaña). Muchos buscadores de OSX / BSD pueden apreciar esta respuesta, pero debe quedar claro que no es para Ubuntu (o GNU / Linux en general?)
mwfearnley
60

En aras de la exhaustividad:

La versión 8.24 de GNU coreutils incluye un parche para dd que introduce un parámetro para imprimir el progreso.

El commit que presenta este cambio tiene el comentario:

dd: nuevo estado = nivel de progreso para imprimir estadísticas periódicamente

Muchas distribuciones, incluida Ubuntu 16.04.2 LTS, usan esta versión.

davidDavidson
fuente
solo quiero agregar cómo he compilado 8.24 coreutils: apt install build-essentialy apt-get build-dep coreutilsluego descargar coreutils-8.25.tar.xz tar xvf coreutils-8.25.tar.xz configure --prefix=$HOME/usr/localy ejecutar make. Recién compilado ddestará bajo srcdir. Puede copiarlo en / bin y reemplazar uno existente o simplemente ejecutar como src / dd
holms
2
¡Bueno! Me gusta esta característica Y tomó solo unos 30 años enseñar a dd a imprimir el resultado del progreso. :-)
Johannes Overmann
¡Qué alivio! Agregaré inmediatamente este argumento en un alias de shell dd.
Stephan Henningsen
Tenga en cuenta que el estado a veces se imprimirá con dos números, uno en unidades SI y el valor equivalente en unidades binarias (por ejemplo, 10 MB, 9,5 MiB).
palswim
33

Lo mejor es usar http://dcfldd.sourceforge.net/ , es fácil de instalar a través de apt-get

TheNano
fuente
3
gracias por el puntero a dcfldd, muy compatible con dd pero algunas buenas características nuevas. Me gusta especialmente el progreso estándar.
Floyd
44
Por qué dcfldd no es más conocido es un completo misterio para mí.
Freedom_Ben
28
Probablemente por su nombre.
Giovanni Toraldo
Tiene las opciones ddy opción status=onpor defecto, para mensajes de progreso, statusinterval=N(N en bloques) para la frecuencia de actualización de mensajes y sizeprobe=[if|of]para un indicador de porcentaje. Lo alias DD:) :)
kavadias
25

El estado de progreso nativo se agregó a dd !!!

La nueva versión de Coreutils (8.24) agrega un estado de progreso a la ddherramienta:

Uso en Xubuntu 15.10:

Abra una terminal y escriba estos comandos:

wget ftp://ftp.gnu.org/pub/gnu/coreutils/coreutils-8.24.tar.xz
tar -xf coreutils-8.24.tar.xz
cd coreutils-8.24
./configure && make -j $(nproc)

Ejecutar ddcomo root:

sudo su
cd src
./dd if=/dev/sdc of=/dev/sda conv=noerror status=progress

Verá: Bytes, segundos y velocidad (Bytes / segundo).

Para verificar las versiones de dd:

Nativo:

dd --version

Nuevo:

cd coreutils-8.24/src
./dd --version
usuario3394963
fuente
18

Si ya ha comenzado dd, y está escribiendo un archivo como cuando crea una copia de un pendrive en el disco, puede usar el comando watch para observar constantemente el tamaño del archivo de salida para ver los cambios y estimar la finalización.

watch ls -l /pathtofile/filename

Para ver solo el tamaño del archivo (vista h-humana):

watch ls -sh /pathtofile/filename
fabricante4
fuente
También es un método viable ...
ζ--
3
Es útil, aunque esto no necesariamente funciona si está canalizando la salida dd a algo que no sea un archivo (por ejemplo, gzip'ing antes de escribirlo en el disco).
Ponkadoodle
No funciona en archivos especiales.
Johannes Overmann
13

La dd | pv | ddtríada hizo que mi copia de 50GB vm tomara 800 segundos, en lugar de 260 segundos usando solo dd. Con esta canalización, al menos, pv no tiene idea de qué tan grande es el archivo de entrada, por lo que no podrá decirle qué tan avanzado está, por lo que no hay inconveniente en hacerlo de la siguiente manera, y obtiene una buena ventaja de velocidad:

Evitaría pv en cualquier cosa grande y (si utilizo Bash):

Control-Z el proceso dd

bgpara ponerlo en segundo plano. Observe que bgle dará resultados como [1] 6011donde el último número es una identificación de proceso. Entonces, haz:

while true; do kill -USR1 process_id ; sleep 5; done

donde process_id es la identificación del proceso que observaste. Presiona Control-C cuando veas algo como:

[1]+  Done dd if=/path/file.qcow2 of=/dev/kvm/pxetest bs=4194304 conv=sparse
-bash: kill: (60111) - No such process

Estás listo.

Editar: Silly Systems Administrator! ¡Automatiza tu vida, no trabajes! Si tengo un largo proceso de dd que quiero monitorear, aquí hay una frase que se encargará de toda la enchilada por usted; pon todo esto en una línea:

 dd if=/path/to/bigimage of=/path/to/newimage conv=sparse bs=262144 & bgid=$!; while true; do sleep 1; kill -USR1 $bgid || break; sleep 4; done

Puede, por supuesto, escribirlo, tal vez convertir $ 1 en su archivo de entrada y $ 2 en su archivo de salida. Esto se deja como un ejercicio para el lector. Tenga en cuenta que necesita dormir un poco antes de matar o matar puede intentar enviar una señal a dd cuando aún no está listo. Ajuste sus sueños como desee (tal vez incluso elimine el segundo sueño por completo).

Bash- FTW! :-)

Mike S
fuente
1
Comprime el whilebucle. Utilizar watch.
muru
1
@muru depende. No sé acerca de su sistema, pero en CentOS7 * la salida es un poco confusa; es legible pero no se ve ordenado. También pisotea su salida anterior para que pierda el historial de la velocidad de su dd; la mía varía entre 20 MB / sy 300 MB / s. Es interesante ver que los números varían y también son instructivos. Creo que parte de la gran variación se debe a que los grupos delgados de LVM aumentan la asignación para un LV en el que estoy escribiendo. * sí, este es un foro de ubuntu pero llegué aquí buscando "progreso del monitor dd". Es el primer resultado en Google.
Mike S
Oh, quise decir en otra terminal o ventana de pantalla, ejecutar sudo watch pkill dd. Luego mira cómo se ddmuestran las estadísticas cómodamente.
Muru
¿No enviará SIGTERM por defecto? Ni siquiera quiero experimentar, ya que pgrep dd aparece con 3 pid cuando se ejecuta un solo dd: kthreadd, oddjob y dd. Tengo miedo de lo que pkill hará. Podrías enviar la señal -USR1 con pkill, pero de nuevo no sé si es seguro enviarlo al hilo del núcleo o al obbjob. El comando watch parece más limpio, pero parece que hay muchos pasos adicionales solo para evitar un ciclo while. En general, si estoy haciendo un dd en una ventana, haré algo inmediatamente después en el mismo shell. El ciclo while es seguro: usted sabe EXACTAMENTE qué pid recibe la señal.
Mike S
sobre todo no me importa qué pids reciben la señal, ya que uso watch pkill -USR1 -x dd. Como también lo uso watchpara otras tareas similares, esta viene naturalmente.
Muru
7

Lo más fácil es:

 dd if=... of=... bs=4M status=progress oflag=dsync

oflag=dsyncmantendrá su escritura sincronizada, por lo que la información status=progresses más precisa. Sin embargo, podría ser un poco más lento.

zevero
fuente
1
de acuerdo con gnu.org/software/coreutils/manual/html_node/dd-invocation.html , usar conv=fsynces mejor
Chen Deng-Ta
¡Gracias por esto! Estoy haciendo dd a un lvm2 remoto y el bs = 4M aumentó mi transferencia en un factor de 20 y la indicación de progreso es maravillosa.
Lonnie Best
6

En Ubuntu 16.04

Ubuntu 16.04 viene con dd (coreutils) Versión 8.25 . Por lo tanto, la opción status=progress es compatible :-)

Para usarlo, solo agregue status=progressjunto con su ddcomando.

Ejemplo:

dd bs=4M if=/media/severus/tools-soft/OperatingSystems/ubuntu-16.04-desktop-amd64.iso of=/dev/null status=progress && sync

Da el estado como

1282846183 bytes (1.2 GiB, 1.1 GiB) copied, 14.03 s, 101.9 MB/s

ingrese la descripción de la imagen aquí

Severus Tux
fuente
5

Use la opción status=progresspara obtener el progreso durante la transferencia.

Además, conv=fsyncmostrará errores de E / S.

Ejemplo:

sudo dd if=mydistrib.iso of=/dev/sdb status=progress conv=fsync
MUY Bélgica
fuente
3

He creado bash wrapper ddque se usará pvpara mostrar el progreso. Póngalo en su .bashrcy use ddcomo de costumbre:

# dd if=/dev/vvg0/root of=/dev/vvg1/root bs=4M
    2GB 0:00:17 [ 120MB/s] [===========================================================>] 100%            
0+16384 records in
0+16384 records out
2147483648 bytes (2.1 GB) copied, 18.3353 s, 117 MB/s

Fuente:

dd()
{
    local dd=$(which dd); [ "$dd" ] || {
        echo "'dd' is not installed!" >&2
        return 1
    }

    local pv=$(which pv); [ "$pv" ] || {
        echo "'pv' is not installed!" >&2
        "$dd" "$@"
        return $?
    }

    local arg arg2 infile
    local -a args
    for arg in "$@"
    do
        arg2=${arg#if=}
        if [ "$arg2" != "$arg" ]
        then
            infile=$arg2
        else
            args[${#args[@]}]=$arg
        fi
    done

    "$pv" -tpreb "$infile" | "$dd" "${args[@]}"
}
midenok
fuente
Buena manera, pero no funciona con comandos como sudo o time.
Maxim Kholyavkin
1
Ponerlo en / / / bin / usr dd locales con este en la parte superior: #!/bin/bash. En la parte inferior: tmp=":${PATH}:"; tmp=${tmp/:/usr/local/bin:/:}; tmp=${tmp%:}; PATH=${tmp#:}; dd "$@"O tal vez desee codificar la ddubicación. Entonces usar local dd=/usr/bin/dd. No se olvide de añadir bit de ejecución: chmod +x /usr/local/dd.
midenok
2

Así que hoy me sentí un poco frustrado al intentar ejecutar killen un bucle mientras ddestaba en ejecución, y se me ocurrió este método para ejecutarlos en paralelo, fácilmente:

function vdd {
    sudo dd "$@" &
    sudo sh -c "while pkill -10 ^dd$; do sleep 5; done"
}

Ahora solo use vddcualquier lugar que normalmente usaría dd(pasa todos los argumentos directamente) y obtendrá un informe de progreso impreso cada 5 segundos.

El único inconveniente es que el comando no regresa inmediatamente cuando se completa dd; por lo tanto, es posible que este comando lo mantenga esperando 5 segundos adicionales después de que dd regrese antes de que se dé cuenta y salga.

robru
fuente
2

Éste obliga a dd a proporcionar estadísticas cada 2 segundos, lo cual es predeterminado para el reloj:

watch killall -USR1 dd

Para cambiar de cada 2 segundos a cada 5 segundos, agregue la opción -n 5 de esta manera:

watch -n 5 killall -USR1 dd
Kostyantyn
fuente
2

En caso de que alguien de CentOS land encuentre este hilo ...

La opción 'estado = progreso' funciona con CentOS 7.5 y 7.6

La respuesta anterior de @davidDavidson implica que la característica se agregó recientemente en Coreutils 8.24.

La versión 8.24 de GNU coreutils incluye un parche para dd que introduce un parámetro para imprimir el progreso.

Este puede ser el caso, pero CentOS podría no estar siguiendo el mismo esquema de versiones.

La versión de Coreutils que viene con CentOS 7.6.1810 es:

coreutils-8.22-23.el7.x86_64 : A set of basic GNU tools commonly used in shell scripts

Y la versión de dd que está instalada es:

[root@hostname /]# dd --version
dd (coreutils) 8.22
Copyright (C) 2013 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Written by Paul Rubin, David MacKenzie, and Stuart Kemp.

Esto muestra las versiones 8.22 .

Sin embargo, he probado el 'estado = progreso' con dd en CentOS 7.5 y CentOS 7.6 (ambos con la versión 8.22 de Coreutils) y funciona correctamente.

No sé por qué RedHat elige usar una versión tan antigua de Coreutils, pero la funcionalidad existe con 8.22.

J Hauss
fuente
1

Como se mencionó anteriormente, al menos con el 'dd' de GNU coreutils, u busybox, responderá a una señal USR1 imprimiendo información de progreso en stderr.

Escribí un pequeño script de envoltura para dd que muestra un buen indicador de porcentaje completo e intenta no interferir con el proceso o la forma de funcionamiento de dd de ninguna manera. Puedes encontrarlo en github:

http://github.com/delt01/dd_printpercent

Desafortunadamente, este truco SIGUSR1 solo funciona con GNU dd (del paquete coreutils) o el modo 'dd' de busybox con esa característica específica habilitada en el momento de la compilación. No funciona con el stock 'dd' incluido con la mayoría de los sistemas BSD, incluidos FreeBSD y OS X ... :(

delt
fuente
El enlace está muerto.
ismael
1

Puede ver el progreso de cualquier programa coreutils usando progress - Coreutils Progress Viewer.

Puede monitorear:

cp mv dd tar cat rsync grep fgrep egrep cut sort md5sum sha1sum sha224sum sha256sum sha384sum sha512sum adb gzip gunzip bzip2 bunzip2 xz unxz lzma unlzma 7z 7za zcat bzcat lzcat split gpg

Puedes ver la página de manual

Puede usarlo en una ventana de terminal separada mientras se ejecuta el comando o ejecutarlo con el comando dd:

dd if=/dev/sda of=file.img & progress -mp $!

Aquí se &bifurca el primer comando y continúa de inmediato en lugar de esperar hasta que finalice el comando.

El comando de progreso se inicia con: -mpor lo tanto, espera hasta que finalice el proceso monitoreado, -ppor lo que supervisa un pedido determinado y $!es el último comando pid.

Si emite dd con sudo, también debe hacerlo con el progreso:

sudo dd if=/dev/sda of=file.img &
sudo progress -m
# with no -p, this will wait for all coreutil commands to finish
# but $! will give the sudo command's pid
labsin
fuente