use getopt, added --help and --version, some output cleanup

(Logical change 1.679)
edge.strict_endians
elisa-laajakaista.fi!szaka 2005-02-19 19:34:37 +00:00
parent 5a6cca21d6
commit f6a7caf21d
1 changed files with 92 additions and 42 deletions

View File

@ -51,12 +51,14 @@
#include <fcntl.h>
#include <errno.h>
#include <string.h>
#include <getopt.h>
#include "types.h"
#include "attrib.h"
#include "mft.h"
#include "device.h"
#include "logfile.h"
#include "utils.h"
#ifdef NO_NTFS_DEVICE_DEFAULT_IO_OPS
# error "No default device io operations! Cannot build ntfsfix. \
@ -64,13 +66,88 @@ You need to run ./configure without the --disable-default-device-io-ops \
switch if you want to be able to build the NTFS utilities."
#endif
GEN_PRINTF(Eprintf, stdout, NULL, FALSE)
GEN_PRINTF(Vprintf, stdout, NULL, FALSE)
GEN_PRINTF(Qprintf, stdout, NULL, FALSE)
const char *EXEC_NAME = "ntfsfix";
struct {
char *volume;
} opt;
static int usage(void)
{
printf("%s v%s\n"
"\n"
"Usage: %s [options] device\n"
" Attempt to fix an NTFS partition.\n"
"\n"
" -h, --help Display this help\n"
" -V, --version Display version information\n"
"\n"
"For example: %s /dev/hda6\n\n",
EXEC_NAME, VERSION, EXEC_NAME, EXEC_NAME);
printf("%s%s", ntfs_bugs, ntfs_home);
exit(1);
}
static void version (void)
{
printf("%s v%s\n\n"
"Attempt to fix an NTFS partition.\n\n"
"Copyright (c) 2000-2003 Anton Altaparmakov.\n\n",
EXEC_NAME, VERSION);
printf("%s\n%s%s", ntfs_gpl, ntfs_bugs, ntfs_home);
exit(1);
}
static void parse_options(int argc, char **argv)
{
char c;
static const char *sopt = "-hV";
static const struct option lopt[] = {
{ "help", no_argument, NULL, 'h' },
{ "version", no_argument, NULL, 'V' },
{ NULL, 0, NULL, 0 }
};
memset(&opt, 0, sizeof(opt));
while ((c = getopt_long (argc, argv, sopt, lopt, NULL)) != (char)-1) {
switch (c) {
case 1: /* A non-option argument */
if (!opt.volume)
opt.volume = argv[optind - 1];
else {
printf("ERROR: Too many arguments.\n");
usage();
}
break;
case 'h':
case '?':
usage();
case 'V':
version();
default:
printf("ERROR: Unknown option '%s'.\n", argv[optind - 1]);
usage();
}
}
if (opt.volume == NULL) {
printf("ERROR: You must specify a device.\n");
usage();
}
}
/**
* main
*/
int main(int argc, char **argv)
{
s64 l, br;
const char *EXEC_NAME = "NtfsFix";
const char *OK = "OK";
const char *FAILED = "FAILED";
unsigned char *m = NULL, *m2 = NULL;
@ -81,57 +158,32 @@ int main(int argc, char **argv)
u16 flags;
BOOL done, force = FALSE;
printf("\n");
if (argc != 2 || !argv[1]) {
printf("%s v%s - Attempt to fix an NTFS partition that "
"has been damaged by the\nLinux NTFS driver. Note that "
"you should run it every time after you have used\nthe "
"Linux NTFS driver to write to an NTFS partition to "
"prevent massive data\ncorruption from happening when "
"Windows mounts the partition.\nIMPORTANT: Run this "
"only *after* unmounting the partition in Linux but "
"*before*\nrebooting into Windows NT/2000/XP or you "
"*will* suffer! - You have been warned!\n\n"
/* Generic copyright / disclaimer. */
"Copyright (c) 2000-2003 Anton Altaparmakov.\n\n"
"%s is free software, released under the GNU "
"General Public License and you\nare welcome to "
"redistribute it under certain conditions.\n"
"%s comes with ABSOLUTELY NO WARRANTY; for details "
"read the file GNU\nGeneral Public License to be found "
"in the file COPYING in the main Linux-NTFS\n"
"distribution directory.\n\n"
/* Generic part ends here. */
"Syntax: ntfsfix partition_or_file_name\n"
" e.g. ntfsfix /dev/hda6\n\n", EXEC_NAME,
VERSION, EXEC_NAME, EXEC_NAME);
fprintf(stderr, "Error: incorrect syntax\n");
exit(1);
}
if (!ntfs_check_if_mounted(argv[1], &mnt_flags)) {
parse_options(argc, argv);
if (!ntfs_check_if_mounted(opt.volume, &mnt_flags)) {
if ((mnt_flags & NTFS_MF_MOUNTED) &&
!(mnt_flags & NTFS_MF_READONLY) && !force) {
fprintf(stderr, "Refusing to operate on read-write "
"mounted device %s.\n", argv[1]);
"mounted device %s.\n", opt.volume);
exit(1);
}
} else
fprintf(stderr, "Failed to determine whether %s is mounted: "
"%s\n", argv[1], strerror(errno));
"%s\n", opt.volume, strerror(errno));
/* Attempt a full mount first. */
printf("Mounting volume... ");
vol = ntfs_mount(argv[1], 0);
vol = ntfs_mount(opt.volume, 0);
if (vol) {
puts(OK);
printf("\nProcessing of $MFT and $MFTMirr completed "
"successfully.\n\n");
printf("Processing of $MFT and $MFTMirr completed "
"successfully.\n");
goto mount_ok;
}
puts(FAILED);
printf("Attempting to correct errors... ");
dev = ntfs_device_alloc(argv[1], 0, &ntfs_device_default_io_ops, NULL);
dev = ntfs_device_alloc(opt.volume, 0, &ntfs_device_default_io_ops, NULL);
if (!dev) {
puts(FAILED);
perror("Failed to allocate device");
@ -142,12 +194,12 @@ int main(int argc, char **argv)
if (!vol) {
puts(FAILED);
perror("Failed to startup volume");
fprintf(stderr, "Volume is corrupt. You should run chkdsk.");
fprintf(stderr, "Volume is corrupt. You should run chkdsk.\n");
ntfs_device_free(dev);
goto error_exit;
}
puts("Processing $MFT and $MFTMirr.");
puts("\nProcessing $MFT and $MFTMirr... ");
/* Load data from $MFT and $MFTMirr and compare the contents. */
m = (u8*)malloc(vol->mftmirr_size << vol->mft_record_size_bits);
@ -259,11 +311,11 @@ int main(int argc, char **argv)
free(m2);
m = m2 = NULL;
printf("Processing of $MFT and $MFTMirr completed successfully.\n\n");
printf("Processing of $MFT and $MFTMirr completed successfully.\n");
/* ntfs_umount() will invoke ntfs_device_free() for us. */
if (ntfs_umount(vol, 0))
ntfs_umount(vol, 1);
vol = ntfs_mount(argv[1], 0);
vol = ntfs_mount(opt.volume, 0);
if (!vol) {
perror("Remount failed");
goto error_exit;
@ -272,7 +324,7 @@ mount_ok:
m = NULL;
/* Check NTFS version is ok for us (in $Volume) */
printf("NTFS volume version is %i.%i.\n\n", vol->major_ver,
printf("NTFS volume version is %i.%i.\n", vol->major_ver,
vol->minor_ver);
if (ntfs_version_is_supported(vol)) {
fprintf(stderr, "Error: Unknown NTFS version.\n");
@ -294,7 +346,6 @@ mount_ok:
goto error_exit;
}
puts(OK);
printf("\n");
printf("Going to empty the journal ($LogFile)... ");
if (ntfs_logfile_reset(vol)) {
@ -303,7 +354,6 @@ mount_ok:
goto error_exit;
}
puts(OK);
printf("\n");
if (vol->major_ver >= 3) {
/* FIXME: If on NTFS 3.0+, check for presence of the usn journal and