Cómo restaurar una imagen de la partición de Android desde mi PC con Linux

Creé una imagen de mi disco flash de mi Nexus 4 como se describe en esta pregunta haciendo

# adb pull /dev/block/mmcblk0 mmcblk0.img

La imagen es completamente funcional, pero me gustaría enviar esta imagen a mi teléfono y el comando inverso no funciona porque permanece allí para siempre y no se realiza ningún cambio.

# adb push mmcblk0.img /dev/block/mmcblk0

¿Cómo puedo enviar esta imagen a mi teléfono?

Respuestas (3)

Tuve este problema al tratar de hacer retroceder una copia de seguridad de mi Samsung Galaxy S2, usando ADB con la herramienta de recuperación CWM (clockworkmod). Al enviar a un archivo de dispositivo, ADB simplemente elimina el archivo de dispositivo de bloque y crea un archivo normal en su lugar y, por lo tanto, ningún dato termina realmente en el dispositivo mmcblk0.

Desafortunadamente, la canalización de la salida de un comando en "adb shell" tampoco está implementada, y la función de sockets unix "adb forward" tampoco parece funcionar, por lo que es difícil recuperar la copia de seguridad en el dispositivo.

La solución es canalizar el archivo de imagen a netcat y usar el reenvío de puertos TCP de ADB para dirigir la transmisión a su dispositivo. Sin embargo, si su CWM/busybox no tiene herramientas de red, también deberá descargar la versión binaria estática arm-v7 de busybox con todos los subprogramas de http://www.busybox.net/downloads/binaries/latest / para poder ejecutar netcat en su dispositivo.

# wget "http://www.busybox.net/downloads/binaries/latest/busybox-armv7l"

# adb push busybox-armv7l /tmp/busybox

# adb forward tcp:6789 tcp:9876

# adb shell

~ # chmod +x /tmp/busybox

~ # /tmp/busybox nc -l -p 9876 > /dev/block/mmcblk0

Luego, en un nuevo shell:

# dd if=your-image-file.img | nc localhost 6789 &

"dd" es mejor que "cat" porque puede verificar el progreso de la copia a intervalos (reemplace 5647 con el PID del comando DD):

# kill -USR1 5647

48+0 records in
47+0 records out
49283072 bytes (49 MB) copied, 17.6145 s, 2.8 MB/s

Tenga en cuenta que escribir en mmcblk0 (o el equivalente en su dispositivo Android) eliminará incluso las particiones de arranque y recuperación, por lo que es una excelente manera de bloquear su dispositivo. Para que conste, mi restauración funcionó bien ;-)

Encontré una solución. Necesitas tener acceso de root para hacerlo. Lo mejor sería arrancar tu Nexus usando una imagen de arranque insegura.

1) Rompí la imagen en trozos más pequeños de esta manera:

# dd bs=4096 count=983040 if=mmcblk0.img of=mmcblk0-0.img
# dd bs=4096 count=983040 skip=983040 if=mmcblk0.img of=mmcblk0-1.img
# dd bs=4096 count=983040 skip=1966080 if=mmcblk0.img of=mmcblk0-2.img
# dd bs=4096 skip=2949120 if=mmcblk0.img of=mmcblk0-3.img

2) Completé todos los fragmentos con bzip2:

# bzip2 -k mmcblk0-0.img
# bzip2 -k mmcblk0-1.img
# bzip2 -k mmcblk0-2.img
# bzip2 -k mmcblk0-3.img

3) Creé un ramdisk en mi Nexus 4:

# adb shell mount -o size=1G -t tmpfs tmpfs /dev/ramdisk

4) Copié dd y bunzip2 en /dev/ramdisk/

5) Empujé, bunzip2ed y escribí los fragmentos de imagen en la partición en pedazos

# adb push mmcblk0-0.img.bz2 /dev/ramdisk
# adb shell "/dev/ramdisk/bunzip2 -c /dev/ramdisk/mmcblk0-0.img.bz2 | /dev/ramdisk/dd bs=4096 conv=notrunc of=/dev/block/mmcblk0"
# adb shell rm /dev/ramdisk/mmcblk0-0.img.bz2

# adb push mmcblk0-1.img.bz2 /dev/ramdisk
# adb shell "/dev/ramdisk/bunzip2 -c /dev/ramdisk/mmcblk0-1.img.bz2 | /dev/ramdisk/dd bs=4096 seek=983040 conv=notrunc of=/dev/block/mmcblk0"
# adb shell rm /dev/ramdisk/mmcblk0-1.img.bz2

# adb push mmcblk0-2.img.bz2 /dev/ramdisk
# adb shell "/dev/ramdisk/bunzip2 -c /dev/ramdisk/mmcblk0-2.img.bz2 | /dev/ramdisk/dd bs=4096 seek=1966080 conv=notrunc of=/dev/block/mmcblk0"
# adb shell rm /dev/ramdisk/mmcblk0-2.img.bz2

# adb push mmcblk0-3.img.bz2 /dev/ramdisk
# adb shell "/dev/ramdisk/bunzip2 -c /dev/ramdisk/mmcblk0-3.img.bz2 | /dev/ramdisk/dd bs=4096 seek=2949120 conv=notrunc of=/dev/block/mmcblk0"
# adb shell rm /dev/ramdisk/mmcblk0-3.img.bz2

El patrón inicial adb pull/push by-partition-id en la pregunta tiene mérito para los entornos de recuperación . Aunque no probé todo el flash ("mmcblk0"), una copia de seguridad y restauración por partición de datos de usuario funcionó en un adb activado dentro de un linaje y una recuperación "/ e/".

El dispositivo es un moto-g4-play "harpia" con cifrado de disco completo de la partición de datos de usuario y un esquema de partición de la era Android 6 (sin particiones A/B). El pie de página criptográfico vive en los últimos bytes de la partición y la clave se deriva del hardware, por lo que solo se puede usar para la copia de seguridad/restauración de un dispositivo.

Active adb en el "Menú avanzado" de recuperación, luego

adb shell ls -l /dev/block/by-name
# note down links for your partition
adb pull /dev/block/by-name/userdata userdata.img
# ... more partitions
# restore userdata again
adb push userdata.img /dev/block/mmcblk0p41

Al presionar /dev/block/by-name/paths, aparecerá el mensaje "No queda espacio en el dispositivo" tan pronto como se alcance el tamaño de tmpfs. Necesitaba abordar la identificación de partición adecuada directamente.

¿Qué tal 'adb pull /dev/block/dm-0' para obtener datos de usuario descifrados?
en la recuperación, los datos de usuario aún no están descifrados ni montados, solo un entorno de caja ocupada. Luego puede montar la partición /system y chroot o LD_LIBRARY_PATH para llegar a un funcional(?) vdc. Cuando lo intenté, no pasé de vdc, lo volveré a visitar. Entiendo que querrías hacer esto para hacer una migración en lugar de restaurar
no sabía que lineageos tiene tal limitación (nunca usé esa recuperación). solo conozco la recuperación de stock (donde adb debe deshabilitarse) o la recuperación de twrp (y clones) con soporte de cifrado
gracias por la información sobre empujar por /dev/block/by-name/ (obtuve "No hay espacio en el dispositivo", ahora intentaré usar /dev/block/sdaX)