256 lines
7.8 KiB
C
256 lines
7.8 KiB
C
/*
|
|
|
|
File: tdiskop.c
|
|
|
|
Copyright (C) 2008 Christophe GRENIER <grenier@cgsecurity.org>
|
|
|
|
This software is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; either version 2 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License along
|
|
with this program; if not, write the Free Software Foundation, Inc., 51
|
|
Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
|
|
*/
|
|
#ifdef HAVE_CONFIG_H
|
|
#include <config.h>
|
|
#endif
|
|
|
|
#ifdef HAVE_STRING_H
|
|
#include <string.h>
|
|
#endif
|
|
#include "types.h"
|
|
#include "common.h"
|
|
#include "intrf.h"
|
|
#ifdef HAVE_NCURSES
|
|
#include "intrfn.h"
|
|
#else
|
|
#include <stdio.h>
|
|
#endif
|
|
#include "godmode.h"
|
|
#include "fnctdsk.h"
|
|
#include "adv.h"
|
|
#include "edit.h"
|
|
#include "log.h"
|
|
#include "hdaccess.h"
|
|
#include "toptions.h"
|
|
#include "tanalyse.h"
|
|
#include "tmbrcode.h"
|
|
#include "tdelete.h"
|
|
#include "tdiskop.h"
|
|
#include "geometry.h"
|
|
|
|
extern const arch_fnct_t arch_i386;
|
|
#define INTER_DISK_X 0
|
|
#define INTER_DISK_Y 7
|
|
|
|
|
|
static int menu_disk_cli(disk_t *disk_car, const int verbose,int dump_ind, const int saveheader, char **current_cmd)
|
|
{
|
|
int align=2;
|
|
int allow_partial_last_cylinder=0;
|
|
int ask_part_order=0;
|
|
unsigned int expert=0;
|
|
char options[16];
|
|
strcpy(options, "AGOPTQ");
|
|
while(1)
|
|
{
|
|
while(*current_cmd[0]==',')
|
|
(*current_cmd)++;
|
|
if(strncmp(*current_cmd,"analyze",7)==0 || strncmp(*current_cmd,"analyse",7)==0)
|
|
{
|
|
(*current_cmd)+=7;
|
|
{
|
|
int search_vista_part=0;
|
|
list_part_t *list_part;
|
|
list_part=interface_analyse(disk_car, verbose, saveheader, current_cmd);
|
|
if(disk_car->arch==&arch_i386)
|
|
{
|
|
const int old_allow_partial_last_cylinder=allow_partial_last_cylinder;
|
|
const list_part_t *element;
|
|
for(element=list_part;element!=NULL;element=element->next)
|
|
{
|
|
if(element->part->part_offset%(2048*512)==0 && element->part->part_size%(2048*512)==0)
|
|
search_vista_part=1;
|
|
}
|
|
while(*current_cmd[0]==',')
|
|
(*current_cmd)++;
|
|
if(strncmp(*current_cmd,"mode_vista",10)==0)
|
|
{
|
|
(*current_cmd)+=10;
|
|
search_vista_part=1;
|
|
}
|
|
if(search_vista_part==1)
|
|
allow_partial_last_cylinder=1;
|
|
if(old_allow_partial_last_cylinder!=allow_partial_last_cylinder)
|
|
hd_update_geometry(disk_car,allow_partial_last_cylinder,verbose);
|
|
log_info("Allow partial last cylinder : %s\n", allow_partial_last_cylinder>0?"Yes":"No");
|
|
log_info("search_vista_part: %d\n", search_vista_part);
|
|
}
|
|
interface_recovery(disk_car, list_part, verbose, dump_ind, align, ask_part_order, expert, search_vista_part, current_cmd);
|
|
part_free_list(list_part);
|
|
}
|
|
}
|
|
else if(strncmp(*current_cmd,"geometry,",9)==0)
|
|
{
|
|
(*current_cmd)+=9;
|
|
change_geometry(disk_car, current_cmd);
|
|
}
|
|
else if(strncmp(*current_cmd,"advanced",8)==0)
|
|
{
|
|
(*current_cmd)+=8;
|
|
interface_adv(disk_car, verbose, dump_ind, expert,current_cmd);
|
|
}
|
|
else if(strncmp(*current_cmd,"options,",8)==0)
|
|
{
|
|
const int old_allow_partial_last_cylinder=allow_partial_last_cylinder;
|
|
(*current_cmd)+=8;
|
|
interface_options(&dump_ind, &align,&allow_partial_last_cylinder,&expert,current_cmd);
|
|
if(old_allow_partial_last_cylinder!=allow_partial_last_cylinder)
|
|
hd_update_geometry(disk_car,allow_partial_last_cylinder,verbose);
|
|
}
|
|
else if(strncmp(*current_cmd,"delete",6)==0)
|
|
{
|
|
(*current_cmd)+=6;
|
|
write_clean_table(disk_car);
|
|
}
|
|
else if(strncmp(*current_cmd,"mbr_code",8)==0)
|
|
{
|
|
(*current_cmd)+=8;
|
|
write_MBR_code(disk_car);
|
|
}
|
|
else
|
|
{
|
|
return 0;
|
|
}
|
|
}
|
|
}
|
|
|
|
#ifdef HAVE_NCURSES
|
|
static int menu_disk_ncurses(disk_t *disk_car, const int verbose,int dump_ind, const int saveheader, char **current_cmd)
|
|
{
|
|
int align=2;
|
|
int allow_partial_last_cylinder=0;
|
|
int ask_part_order=0;
|
|
int command;
|
|
unsigned int menu=0;
|
|
int real_key;
|
|
unsigned int expert=0;
|
|
char options[16];
|
|
static struct MenuItem menuMain[]=
|
|
{
|
|
{'A',"Analyse","Analyse current partition structure and search for lost partitions"},
|
|
{'T',"Advanced","Filesystem Utils"},
|
|
{'G',"Geometry", "Change disk geometry" },
|
|
{'O',"Options","Modify options"},
|
|
{'C',"MBR Code","Write TestDisk MBR code to first sector"},
|
|
{'D',"Delete","Delete all data in the partition table"},
|
|
{'Q',"Quit","Return to disk selection"},
|
|
{'E',"Editor","Basic disk editor"},
|
|
{0,NULL,NULL}
|
|
};
|
|
strcpy(options, "AGOPTQ");
|
|
if(disk_car->arch->write_MBR_code!=NULL)
|
|
strcat(options,"C");
|
|
if(disk_car->arch->erase_list_part!=NULL)
|
|
strcat(options,"D");
|
|
while(1)
|
|
{
|
|
aff_copy(stdscr);
|
|
wmove(stdscr,5,0);
|
|
wprintw(stdscr,"%s\n",disk_car->description(disk_car));
|
|
wmove(stdscr,20,0);
|
|
wprintw(stdscr,"Note: Correct disk geometry is required for a successful recovery. 'Analyse'");
|
|
wmove(stdscr,21,0);
|
|
wprintw(stdscr,"process may give some warnings if it thinks the logical geometry is mismatched.");
|
|
command = wmenuSelect_ext(stdscr, 23, INTER_DISK_Y, INTER_DISK_X, menuMain, 10,
|
|
options, MENU_VERT | MENU_VERT_WARN | MENU_BUTTON | MENU_ACCEPT_OTHERS, &menu,&real_key);
|
|
/* e for editor will be added when the editor will be better */
|
|
switch(command)
|
|
{
|
|
case 'a':
|
|
case 'A':
|
|
{
|
|
int search_vista_part=0;
|
|
list_part_t *list_part;
|
|
list_part=interface_analyse(disk_car, verbose, saveheader, current_cmd);
|
|
if(disk_car->arch==&arch_i386)
|
|
{
|
|
const int old_allow_partial_last_cylinder=allow_partial_last_cylinder;
|
|
const list_part_t *element;
|
|
for(element=list_part;element!=NULL;element=element->next)
|
|
{
|
|
if(element->part->part_offset%(2048*512)==0 && element->part->part_size%(2048*512)==0)
|
|
search_vista_part=1;
|
|
}
|
|
if(search_vista_part==0)
|
|
{
|
|
log_info("Ask the user for vista mode\n");
|
|
if(ask_confirmation("Should TestDisk search for partition created under Vista ? [Y/N] (answer Yes if unsure)")!=0)
|
|
search_vista_part=1;
|
|
}
|
|
if(search_vista_part==1)
|
|
allow_partial_last_cylinder=1;
|
|
if(old_allow_partial_last_cylinder!=allow_partial_last_cylinder)
|
|
hd_update_geometry(disk_car,allow_partial_last_cylinder,verbose);
|
|
log_info("Allow partial last cylinder : %s\n", allow_partial_last_cylinder>0?"Yes":"No");
|
|
log_info("search_vista_part: %d\n", search_vista_part);
|
|
}
|
|
interface_recovery(disk_car, list_part, verbose, dump_ind, align, ask_part_order, expert, search_vista_part, current_cmd);
|
|
part_free_list(list_part);
|
|
}
|
|
break;
|
|
case 'd':
|
|
case 'D':
|
|
write_clean_table(disk_car);
|
|
break;
|
|
case 'c':
|
|
case 'C':
|
|
write_MBR_code(disk_car);
|
|
break;
|
|
case 'g':
|
|
case 'G':
|
|
change_geometry(disk_car, current_cmd);
|
|
break;
|
|
case 'o':
|
|
case 'O':
|
|
{
|
|
const int old_allow_partial_last_cylinder=allow_partial_last_cylinder;
|
|
interface_options(&dump_ind, &align,&allow_partial_last_cylinder,&expert, current_cmd);
|
|
if(old_allow_partial_last_cylinder!=allow_partial_last_cylinder)
|
|
hd_update_geometry(disk_car,allow_partial_last_cylinder,verbose);
|
|
}
|
|
break;
|
|
case 't':
|
|
case 'T':
|
|
interface_adv(disk_car, verbose, dump_ind, expert, current_cmd);
|
|
break;
|
|
case 'e':
|
|
case 'E':
|
|
interface_editor(disk_car);
|
|
break;
|
|
case 'q':
|
|
case 'Q':
|
|
return 0;
|
|
}
|
|
}
|
|
}
|
|
#endif
|
|
|
|
int menu_disk(disk_t *disk_car, const int verbose,int dump_ind, const int saveheader, char **current_cmd)
|
|
{
|
|
if(*current_cmd!=NULL)
|
|
return menu_disk_cli(disk_car, verbose, dump_ind, saveheader, current_cmd);
|
|
#ifdef HAVE_NCURSES
|
|
return menu_disk_ncurses(disk_car, verbose, dump_ind, saveheader, current_cmd);
|
|
#else
|
|
return 0;
|
|
#endif
|
|
}
|