Comment secourir un disque avec Linux et quelques outils (Ecrit en 2012)

Voila un petit article dédiée à Steph, la plus grosse casseuse de disque dur que je connaisse. Elle à probablement des action chez Maxtor et rue Montgallet ! En plus elle utilise Windows 7 pour gérer tout ça... :)

Comment fonctionne un disque dur et le stockage

Culture générale

Avant tout voila un article qui explique comment est fait un disque dur et comment il fonctionne: http://www.ac-nancy-metz.fr/services/tec/le_disque_dur.htm [cache pdf]

Le stockage de masse sous Linux

Linux voit un disque dur comme un gros fichier avec une place limité. Le disque dur est donc accédé depuis le user-space comme un fichier, on peut faire des lectures séquentielles et des sauts dans ce fichier. Si le disque est S-ATA ou USB, il sera vu dans le fichier spécial /dev/sdX avec X qui vaut une lettre de l'alphabet. Pour le premier disque ce sera /dev/sda. On nomme ce fichier un device. Tout ceci est aussi valable pour une clé USB qui est aussi un périphérique de stockage de masse.

Les partitions sous Linux

Le disque décrit précédemment est découpé en partitions. Les partitions permettent d'avoir plusieurs espace de stockage d'une taille limitée sur un même disque. La somme de ces espaces ne dépassera évidement pas la taille totale du disque. Le début du disque contient la table des partitions. C'est cette table qui détaille les début et fin de chaque partition. Chaque partition est vue sous Linux comme un fichier. De même que pour le disque, on peut faire des lectures séquentielles et des sauts dans ce fichier. Chaque partition est vue dans le fichier portant le même préfixe que le disque qui héberge ces partions, suivi d'un chiffre pour numéroter ces partitions. Par exemple /dev/sda1.


L'organisation d'un disque

Repérer un disque sous Linux

Lorsque l'on ajoute un disque dur USB sous Linux, on peut connaitre son device avec la commande dmesg. Il faut brancher le disque USB, attendre une dizaine de secondes, et taper la commande dmesg. Cette commande affiche les logs du kernel, c'est a dire l'activité de l'OS. Il va nous dire qu'il a détecté un nouveau disque, et il va nous donner son device et ses partitions.

Par exemple:

thierry@thierry:~$ dmesg 
[...]
usb 7-5: new high speed USB device using ehci_hcd and address 28
usb 7-5: configuration #1 chosen from 1 choice
scsi24 : SCSI emulation for USB Mass Storage devices
usb-storage: device found at 28
usb-storage: waiting for device to settle before scanning
scsi 24:0:0:0: Direct-Access              USB DISK 2.0     PMAP PQ: 0 ANSI: 0
CCS
sd 24:0:0:0: [sdb] 7905024 512-byte hardware sectors (4047 MB)
sd 24:0:0:0: [sdb] Write Protect is off
sd 24:0:0:0: [sdb] Mode Sense: 23 00 00 00
sd 24:0:0:0: [sdb] Assuming drive cache: write through
sd 24:0:0:0: [sdb] 7905024 512-byte hardware sectors (4047 MB)
sd 24:0:0:0: [sdb] Write Protect is off
sd 24:0:0:0: [sdb] Mode Sense: 23 00 00 00
sd 24:0:0:0: [sdb] Assuming drive cache: write through
 sdb: sdb1
sd 24:0:0:0: [sdb] Attached SCSI removable disk
usb-storage: device scan complete

On retrouve en gras et dans l'ordre:

  • La nature du péripherique, ici un high speed USB device
  • Le nombre total de secteurs. Ici/ 7905024
  • La taille d'un secteur. Ici 512 Octets
  • La taille de stockage du periphérique qui est juste la multiplication du nombre de secteurs par la taille d'un secteur. Ici 4Go
  • Le nom de device contenant le disque. ici sdb. Il sera donc accessible via /dev/sdb
  • Le nombre de partitions et leur numéros. Ici une seul partition qui est /dev/sdb1

On peut obtenir plus d'informations sur les partitions en utilisant la commande fdisk -l /dev/sdX, en remplaçant le X par la lettre du disque. Il y a plus d'information sur cette commande en tapant "man fdisk" - [cache]. Par exemple:

thierry@thierry:~$ fdisk -l -u /dev/sdb

Disk /dev/sdb: 4047 MB, 4047372288 bytes
13 heads, 32 sectors/track, 19002 cylinders, total 7905024 sectors
Units = sectors of 1 * 512 = 512 bytes
Disk identifier: 0x92eb87a5

   Device Boot      Start         End      Blocks   Id  System
/dev/sdb1            8064     7905023     3948480   b   W95 FAT32

On retrouve ici:

  • Le device du disque. Ici /dev/sdb
  • La taille totale du disque. Ici 4Go
  • En italique, la notation CHS, que l'on ne va pas utliser, mais qui est détaillée dans le lien "culture générale"
  • On retrouve la taille d'un secteur. Ici 512 bytes
  • Le device de la première partition. Ici /dev/sdb1
  • Le secteur de démarrage de cette partition. Ici 8064
  • Le secteur de fin de cette partition. Ici 7905023
  • Un indice sur le filesystem utilisé. Ici W95 FAT32

Les filesystems

Disque est donc un gros espace de stockage ou l'on met des données enchaînées les unes au autres. Pour que l'OS puisse retrouver les données en question, il doit mettre en place une organisation sur ce vaste espace. Cette organisation est appelées système de fichiers (filesystem). Le filesystem permet de créer une organisation pour les fichiers. Il gère principalement l'organisation de la place sur le disque, mais aussi les répertoires et les droits d'accès. On trouve une multitude de filesystems qui ont chacun leur avantages et leur défauts. Des explications sur les filesystems:

Comment s'endommage un disque

Un disque s'abîme généralement lorsqu'il est maltraité, typiquement lors d'une chute, ou lorsque le courant d'alimentation n'est pas stable. Un disque mécanique est composé d'un ou plusieurs plateaux de stockage des données. Chaque position de ce plateau contient une donnée qui correspond a un emplacement. Lorsque un de ces emplacement est endommagé, la donnée qu'il contient n'est plus accessible.

Si la donnée inaccessible est situé sur les bloc contenant la table de partitions ou sur un bloc structurant le filesystem, la récupération sera beaucoup plus complexe que si elle est au milieu d'un fichier.

Généralement un disque dur légèrement endommagé, fini par se détériorer complètement. Il suffit qu'il y ait un minuscule copeau de disque qui se promène a l'intérieur pour qu'il finisse de tout détruire. Si un disque est endommagé, il vaut mieux ne plus l'utiliser tant que l'on n'est pas en mesure de copier les données.

Comment tenter de récupérer les données

Le concept

On va essayer de recopier ce qui est recopiable d'une partition endommagée vers un disque sain. Lorsque ces données seront recopiées, on essayera de les reconstruire. Il va donc falloir se procurer un disque de plus grande taille qui sera destiné a recevoir les données.

Avant tout

La plupart des commande utilisées ci-après nécessitent d'avoir les droits root. Pour cela, il faut soit travailler en tant que l'utilisateur root, soit préfixer les commande de "sudo" qui donne les droits root a la commande exécutée.

Copie d'une partition endomagée vers une partition saine

Tout d'abord, on crée une partition sur le disque sain. Dans l'idéal cette partition devrait faire la même taille que la partition que l'on tente de sauver. On va donc récupérer ces tailles avec la commande "fisk -u -l /dev/sdX" détaillée précédemment. Attention a ne pas mélanger des device du disque sain et du disque a récupérer. Pour éviter ce mélange, il convient de brancher d'abord le disque sain, repérer son device, puis brancher l'autre disque et repérer également son device. Attention, sur les OS Linux "magiques" (comme Ubuntu), dès que le disque sera connecté, il va essayer de le "monter". Il faut désactiver avant tout cette option. Avant de brancher les disque, on peut essayer de désactiver l'automount de cette manière (c'est sans garanti, je n'ai pas d'OS "magique" pour tester):

thierry@thierry:~$ /etc/init.d/autofs stop
thierry@thierry:~$ /etc/init.d/haldaemon stop

Il faut retenir les chiffres "start" et "end". Ces chiffres sont à reporter sur le device sain en utilisant toujours la commande "fdisk" mais en mode interactif (Les commandes sont en gras):

thierry@thierry:~$ fdisk -u /dev/sdb

The number of cylinders for this disk is set to 19002.
There is nothing wrong with that, but this is larger than 1024,
and could in certain setups cause problems with:
1) software that runs at boot time (e.g., old versions of LILO)
2) booting and partitioning software from other OSs
   (e.g., DOS FDISK, OS/2 FDISK)

Command (m for help): n
Command action
   e   extended
   p   primary partition (1-4)
p
Partition number (1-4): 1
First sector (32-7905023, default 32): 8064
Last sector or +size or +sizeM or +sizeK (8064-7905023, default 7905023): 7905023

Command (m for help): t
Selected partition 1
Hex code (type L to list codes): L

 0  Empty           1e  Hidden W95 FAT1 80  Old Minix       be  Solaris boot   
 1  FAT12           24  NEC DOS         81  Minix / old Lin bf  Solaris        
 2  XENIX root      39  Plan 9          82  Linux swap / So c1  DRDOS/sec (FAT-
 3  XENIX usr       3c  PartitionMagic  83  Linux           c4  DRDOS/sec (FAT-
 4  FAT16 <32M      40  Venix 80286     84  OS/2 hidden C:  c6  DRDOS/sec (FAT-
 5  Extended        41  PPC PReP Boot   85  Linux extended  c7  Syrinx         
 6  FAT16           42  SFS             86  NTFS volume set da  Non-FS data    
 7  HPFS/NTFS       4d  QNX4.x          87  NTFS volume set db  CP/M / CTOS / .
 8  AIX             4e  QNX4.x 2nd part 88  Linux plaintext de  Dell Utility   
 9  AIX bootable    4f  QNX4.x 3rd part 8e  Linux LVM       df  BootIt         
 a  OS/2 Boot Manag 50  OnTrack DM      93  Amoeba          e1  DOS access     
 b  W95 FAT32       51  OnTrack DM6 Aux 94  Amoeba BBT      e3  DOS R/O        
 c  W95 FAT32 (LBA) 52  CP/M            9f  BSD/OS          e4  SpeedStor      
 e  W95 FAT16 (LBA) 53  OnTrack DM6 Aux a0  IBM Thinkpad hi eb  BeOS fs        
 f  W95 Ext'd (LBA) 54  OnTrackDM6      a5  FreeBSD         ee  EFI GPT        
10  OPUS            55  EZ-Drive        a6  OpenBSD         ef  EFI (FAT-12/16/
11  Hidden FAT12    56  Golden Bow      a7  NeXTSTEP        f0  Linux/PA-RISC b
12  Compaq diagnost 5c  Priam Edisk     a8  Darwin UFS      f1  SpeedStor      
14  Hidden FAT16 <3 61  SpeedStor       a9  NetBSD          f4  SpeedStor      
16  Hidden FAT16    63  GNU HURD or Sys ab  Darwin boot     f2  DOS secondary  
17  Hidden HPFS/NTF 64  Novell Netware  b7  BSDI fs         fd  Linux raid auto
18  AST SmartSleep  65  Novell Netware  b8  BSDI swap       fe  LANstep        
1b  Hidden W95 FAT3 70  DiskSecure Mult bb  Boot Wizard hid ff  BBT            
1c  Hidden W95 FAT3 75  PC/IX          
Hex code (type L to list codes): b
Changed system type of partition 1 to b (W95 FAT32)

Command (m for help): wq
The partition table has been altered!

Calling ioctl() to re-read partition table.

WARNING: Re-reading the partition table failed with error 13: Permission non accordée.
The kernel still uses the old table.
The new table will be used at the next reboot.

WARNING: If you have created or modified any DOS 6.x
partitions, please see the fdisk manual page for additional
information.
Syncing disks.
  • new: on veux faire une nouvelle partition.
  • primary: ce sera une partition primaire.
  • 1 Ce sera la première partition du disque
  • 8064 La partition commencera au bloc 8064. Ce sera presque toujours vrai.
  • 7905023 La partition se terminera au bloc 7905023. Une frappe sur entrée sans saisie fonctionne ausi lorsque l'on souhaite prendre toute la place disponible. Dans cet exemple le résultat sera le même. Si la table de partitions est endommagée sur le disque a récupérée, on prendra toute la place disponible, et ça ira très bien. A partir d'ici la partition est créée.
  • type of system. On va positionner le type du filessytem que l'on va utiliser. Ce n'est pas obligatoire, mais c'est mieux.
  • List: liste les types disponibles.
  • b: on choisit le type b. C'est "W95 FAT32". Généralement, ce sera le bon filesystem à choisir.
  • wq Write and quit. On écrit les modification sur le disque et on quitte. Le système d'exploitation va se mettre ajour et pourra utiliser ces nouvelles partitions.

La copie des données

On va utiliser "dd_rescue" pour copier les données. Je laisse une version 32 bits compilé en statique disponible: dd_rescue-1.25.static.i386.bin. On va maintenant copier ce que l'on peut de la partition endomagée vers la partition saine. Cette opération peut prendre plusieurs heures. Pour utiliser la version de dd_rescue compilée fournie ici, il suffit de la copier dans le répertoire courant du linux qui sert à faire la manipulation. Voila la commande à exécuter:

thierry@thierry:~$ ./dd_rescue-1.25.static.i386.bin -d -D -A /dev/sdb1 /dev/sda1

Les option -d et -D servent à utiliser un acces direct aux données. Par défaut Linux utilise des caches pour les données. Ces cache permettent d'accélérer les option en utilisation normale, dans le cas d'une récupération de données, il vaut mieux que les données lues le soit directement du disque et les données écrites le soient sur le disque et non dans un cache. L'option -A remplace les données qui ne peuvent pas être lues par des 0 (zéros).

Comment faire si la table de partitions est endommagée

Il faut retrouver le début des partitions, en fonction des filesystems utilisés, on peut rechercher certains tags qui marque le dubut de la partition. Je ne vais pas détailler cette recherche ici. Le plus simple sera de considérer qu'il y a qu'une partition sur le disque (cas typique des disques dur externe). On sautera l'espace dédié à la table de partitions On considère que le disque. La commande a taper sera donc la suivante.

thierry@thierry:~$ ./dd_rescue-1.25.static.i386.bin -d -D -A -s 4128768 /dev/sdb /dev/sda1

Je n'ai pas testé cette commande. Elle devrait fonctionner. Attention au device d'entrée, on utilise le disque complet et non une partition. On note donc /dev/sdb au lieu de /dev/sdb1. 4128768 est le nombre d'octet a sauter au début de la copie. Ces octets correspondent à la table de partitions. On retrouve cette valeur ainsi: 512 x 8064. 8064 étant l'adresse de la première partition en blocks.

Tentative d'accès aux données

Maintenant que les données on été copiées tant bien que mal sur une nouvelle partition, on peut essayer d'y accéder. Pour cela, on va monter la partition. On la monte en lecture pour être sur de ne rien endommager.

thierry@thierry:~$ mkdir toto
thierry@thierry:~$ mount /dev/sdb1 toto

La commande mkdir toto crée un répertoire qui va servir de point de montage. Le pointe de montage est le répertoire dans lequel apparaitront les données de la partition récupérée. mount /dev/sdb1 toto est la commande qui va servir à monter la partition "sdb1" dans toto. Si il n'y a pas eu de message d'erreur c'est bon signe, vous n'avez plus qu'a verifier si toutes les données sont là. Il y aura très certainement des données endommagées, mais la plupart seront saines.

Si le "mount" ne se passe pas bien, le filesystem est probablement endommagé, on peut essayer de le récupérer avec la commande:

thierry@thierry:~$ fsck.vfat -a /dev/sdb1

Cette commande va tenter de réparer le filesystem. Il se peut qu'elle détruise tout, mais dans ce cas, il sera de toute façon très complexe de récupérer les données. Lorsque cette commande a fini de s'exécuter, on va tenter a nouveau le "mount". Si il se passe bien, tant mieux, regardez les données restante, si il se passe mal, vous allez sûrement faire le bonheur d'un récupérateur de données professionnel :).