In expert mode during RepairMFT, user can choose between MFT and MFTmirror if TestDisk can't find the correct one.
This commit is contained in:
parent
b9516d9e09
commit
cdb8cbe5fc
4 changed files with 80 additions and 28 deletions
|
@ -1068,7 +1068,7 @@ int ntfs_boot_sector(disk_t *disk_car, partition_t *partition, const int verbose
|
|||
dir_partition(disk_car, partition, 0,current_cmd);
|
||||
break;
|
||||
case 'M':
|
||||
repair_MFT(disk_car, partition, verbose, current_cmd);
|
||||
repair_MFT(disk_car, partition, verbose, expert, current_cmd);
|
||||
break;
|
||||
case 'R': /* R : rebuild boot sector */
|
||||
rebuild_NTFS_BS(disk_car,partition,verbose,dump_ind,1,expert,current_cmd);
|
||||
|
|
|
@ -402,7 +402,7 @@ int wmenuUpdate(WINDOW *window, int y, int x, const struct MenuItem *menuItems,
|
|||
{
|
||||
log_critical("\nBUG: %s\n",mi);
|
||||
}
|
||||
if(lenName > itemLength)
|
||||
if(lenName >= itemLength)
|
||||
{
|
||||
if( menuType & MENU_BUTTON )
|
||||
snprintf(buff, sizeof(buff),"[%s]",mi);
|
||||
|
|
|
@ -67,5 +67,5 @@ int test_NTFS(const disk_t *disk_car,const struct ntfs_boot_sector*ntfs_header,
|
|||
#define NTFS_GETU64(p) (le64(*(const uint64_t*)(p)))
|
||||
unsigned int ntfs_sector_size(const struct ntfs_boot_sector *ntfs_header);
|
||||
int rebuild_NTFS_BS(disk_t *disk_car,partition_t *partition, const int verbose, const int dump_ind,const int interface, const unsigned int expert, char**current_cmd);
|
||||
int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, char **current_cmd);
|
||||
int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, const unsigned int expert, char **current_cmd);
|
||||
int repair_MFT_Vol(disk_t *disk_car, partition_t *partition, const int verbose);
|
||||
|
|
102
src/ntfs_fix.c
102
src/ntfs_fix.c
|
@ -42,10 +42,14 @@
|
|||
#include "ntfs_dir.h"
|
||||
#include "io_redir.h"
|
||||
#include "log.h"
|
||||
#include "intrfn.h"
|
||||
#include "lang.h"
|
||||
|
||||
//#define DEBUG_REPAIR_MFT 1
|
||||
#define INTER_MFT_X 0
|
||||
#define INTER_MFT_Y 18
|
||||
|
||||
int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, char **current_cmd)
|
||||
int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, const unsigned int expert, char **current_cmd)
|
||||
{
|
||||
struct ntfs_boot_sector *ntfs_header;
|
||||
unsigned char *buffer_mft;
|
||||
|
@ -54,6 +58,10 @@ int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, char
|
|||
unsigned int mft_record_size;
|
||||
unsigned int mftmirr_size;
|
||||
unsigned int mftmirr_size_bytes;
|
||||
unsigned int use_MFT=0;
|
||||
/* 0: do nothing
|
||||
* 1: fix MFT mirror using MFT
|
||||
* 2: fix MFT using MFT mirror */
|
||||
uint64_t mft_pos;
|
||||
uint64_t mftmirr_pos;
|
||||
log_trace("repair_MFT\n");
|
||||
|
@ -192,28 +200,76 @@ int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, char
|
|||
{
|
||||
/* Use MFT */
|
||||
if(ask_confirmation("Fix MFT mirror ? (Y/N)")!=0)
|
||||
use_MFT=1;
|
||||
else
|
||||
log_info("Don't fix MFT mirror.\n");
|
||||
}
|
||||
else if(res1<res2)
|
||||
{
|
||||
if(disk_car->write(disk_car, mftmirr_size_bytes, buffer_mft, mftmirr_pos)!=0)
|
||||
{
|
||||
log_error("Failed to fix MFT mirror: write error.\n");
|
||||
display_message("Failed to fix MFT mirror: write error.\n");
|
||||
/* Use MFT mirror */
|
||||
if(ask_confirmation("Fix MFT ? (Y/N)")!=0)
|
||||
use_MFT=2;
|
||||
else
|
||||
log_info("Don't fix MFT.\n");
|
||||
}
|
||||
else
|
||||
{ /* res1==res2 */
|
||||
if(res1<0)
|
||||
log_error("MFT and MFT mirror are bad. Failed to repair them.\n");
|
||||
else
|
||||
log_error("Both MFT seems ok but they don't match, use chkdsk.\n");
|
||||
if(expert==0)
|
||||
{
|
||||
disk_car->sync(disk_car);
|
||||
log_info("MFT mirror fixed.\n");
|
||||
display_message("MFT mirror fixed.\n");
|
||||
}
|
||||
if(res1<0)
|
||||
display_message("MFT and MFT mirror are bad. Failed to repair them.\n");
|
||||
else
|
||||
display_message("Both MFT seems ok but they don't match, use chkdsk.\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
log_info("Don't fix MFT mirror.\n");
|
||||
#ifdef HAVE_NCURSES
|
||||
unsigned int menu=2;
|
||||
int real_key;
|
||||
int command;
|
||||
static struct MenuItem menuMFT[]=
|
||||
{
|
||||
{'B',"MFT", "Fix MFT using MFT mirror"},
|
||||
{'M',"MFT Mirror", "Fix MFT mirror using MFT"},
|
||||
{'Q',"Quit","Return to NTFS functions"},
|
||||
{0,NULL,NULL}
|
||||
};
|
||||
aff_copy(stdscr);
|
||||
wmove(stdscr,4,0);
|
||||
wprintw(stdscr,"%s",disk_car->description(disk_car));
|
||||
mvwaddstr(stdscr,5,0,msg_PART_HEADER_LONG);
|
||||
wmove(stdscr,6,0);
|
||||
aff_part(stdscr,AFF_PART_ORDER|AFF_PART_STATUS,disk_car,partition);
|
||||
wmove(stdscr,8,0);
|
||||
if(res1<0)
|
||||
wprintw(stdscr, "MFT and MFT mirror are bad.\n");
|
||||
else
|
||||
wprintw(stdscr, "Both MFT seems ok but they don't match.\n");
|
||||
command=wmenuSelect_ext(stdscr,INTER_MFT_Y, INTER_MFT_X, menuMFT, 10, "MBQ",
|
||||
MENU_VERT | MENU_VERT_WARN | MENU_BUTTON, &menu, &real_key);
|
||||
switch(command)
|
||||
{
|
||||
case 'b':
|
||||
case 'B':
|
||||
use_MFT=2;
|
||||
break;
|
||||
case 'm':
|
||||
case 'M':
|
||||
use_MFT=1;
|
||||
break;
|
||||
default:
|
||||
use_MFT=0;
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else if(res1<res2)
|
||||
{
|
||||
/* Use MFT mirror */
|
||||
if(ask_confirmation("Fix MFT ? (Y/N)")!=0)
|
||||
}
|
||||
}
|
||||
if(use_MFT==2)
|
||||
{
|
||||
if(disk_car->write(disk_car, mftmirr_size_bytes, buffer_mftmirr, mft_pos)!=0)
|
||||
{
|
||||
|
@ -227,22 +283,18 @@ int repair_MFT(disk_t *disk_car, partition_t *partition, const int verbose, char
|
|||
display_message("MFT fixed.\n");
|
||||
}
|
||||
}
|
||||
else
|
||||
else if(use_MFT==1)
|
||||
{
|
||||
log_info("Don't fix MFT.\n");
|
||||
}
|
||||
}
|
||||
else if(res1<0)
|
||||
if(disk_car->write(disk_car, mftmirr_size_bytes, buffer_mft, mftmirr_pos)!=0)
|
||||
{
|
||||
/* Both are bad */
|
||||
log_error("MFT and MFT mirror are bad. Failed to repair them.\n");
|
||||
display_message("MFT and MFT mirror are bad. Failed to repair them.\n");
|
||||
log_error("Failed to fix MFT mirror: write error.\n");
|
||||
display_message("Failed to fix MFT mirror: write error.\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Use chkdsk */
|
||||
log_error("Both MFT seems ok but they don't match, use chkdsk.\n");
|
||||
display_message("Both MFT seems ok but they don't match, use chkdsk.\n");
|
||||
disk_car->sync(disk_car);
|
||||
log_info("MFT mirror fixed.\n");
|
||||
display_message("MFT mirror fixed.\n");
|
||||
}
|
||||
}
|
||||
free(buffer_mftmirr);
|
||||
|
|
Loading…
Reference in a new issue