2010-03-22 22 views
2

J'essaie de défragmenter un seul fichier via l'API de défragmentation Windows (http://msdn.microsoft.com/en-us/library/aa363911(VS.85).aspx) mais s'il n'y a pas de bloc d'espace libre assez grand pour mon fichier, je voudrais déplacer d'autres parties de fichiers pour faire de la place.Comment puis-je trouver des informations sur un fichier à partir d'un numéro de cluster logique en NTFS/FAT32?

L'article lié mentionne des parties mobiles d'autres fichiers mais je ne trouve aucune information sur la façon de trouver les fichiers à déplacer. De l'espace libre bitmap je peux trouver un espace assez grand et je connais les numéros de cluster logique qui l'entoure, mais de cela je ne peux pas savoir quels fichiers l'entourent et un handle pour les fichiers est nécessaire pour faire FSCTL_MOVE_FILE qui se déplace parties de fichiers. Existe-t-il un moyen, via l'API ou en analysant la MFT, de savoir de quel fichier fait partie un numéro de cluster logique et quel numéro de cluster virtuel correspond au numéro de cluster logique trouvé dans le bitmap?

Répondre

1

La méthode lente mais compatible consiste à analyser récursivement tous les répertoires pour les fichiers et à utiliser le FSCTL_GET_RETRIEVAL_POINTERS. Ensuite, analysez le mappage VCN-LCN résultant pour le cluster en question.

Une autre option consiste à interroger le journal USN du lecteur pour obtenir les ID de référence de fichier, puis utilisez FSCT_GET_NTFS_FILE_RECORD pour obtenir l'enregistrement de fichier $ MFT. Je travaille actuellement sur un simple programme Defrag (écrit en Java) dans le but de regrouper des fichiers d'un répertoire (par exemple tous les fichiers d'un grand jeu) afin de réduire les temps de chargement et de chargement.

J'utilise une méthode plus rapide pour récupérer les mappages de fichiers sur le lecteur NTFS ou FAT32.

J'analyse directement le fichier $ MFT (le format a quelques pièges), ou la table d'allocation de fichiers FAT32 avec les répertoires.

L'astuce consiste à ouvrir le lecteur (par exemple "c:") avec FileCreate pour une lecture GENERIC entièrement partagée. Le handle résultant peut ensuite être lu avec FileRead et FileSeek sur une granularité d'octets. Cela fonctionne uniquement en mode administrateur (ou élevé). Sur NTFS, le MFT $ peut être fragmenté et est un peu difficile à localiser à partir des informations sur le secteur de démarrage. J'utilise le FSCTL_GET_RETRIEVAL_POINTERS sur le fichier C: \ $ MFT pour obtenir ses clusters.

Sur FAT32, il faut analyser le secteur de démarrage pour localiser la table FAT et le cluster contenant le fichier de répertoire racine. Vous devez analyser les entrées du répertoire et localiser récursivement les clusters des sous-répertoires.

+3

Comme une mise à jour, Windows 7 a 'FSCTL_LOOKUP_STREAM_FROM_CLUSTER' qui semble faire exactement ce que l'OP veut, en une seule opération. – Damon

0

Il n'y a pas de correspondance O (1) du bloC# au fichier. Vous devez parcourir toute la MFT à la recherche de fichiers contenant ce bloc.

Bien sûr, dans un système en direct, une fois que vous avez lu ces données, elles sont périmées et vous devez vous préparer à des échecs dans les données de déplacement FSCTL.