1987da915Sopenharmony_ci/** 2987da915Sopenharmony_ci * ntfs-3g.probe - Probe NTFS volume mountability 3987da915Sopenharmony_ci * 4987da915Sopenharmony_ci * Copyright (c) 2007-2009 Szabolcs Szakacsits 5987da915Sopenharmony_ci * 6987da915Sopenharmony_ci * This program is free software; you can redistribute it and/or modify 7987da915Sopenharmony_ci * it under the terms of the GNU General Public License as published by 8987da915Sopenharmony_ci * the Free Software Foundation; either version 2 of the License, or 9987da915Sopenharmony_ci * (at your option) any later version. 10987da915Sopenharmony_ci * 11987da915Sopenharmony_ci * This program is distributed in the hope that it will be useful, 12987da915Sopenharmony_ci * but WITHOUT ANY WARRANTY; without even the implied warranty of 13987da915Sopenharmony_ci * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14987da915Sopenharmony_ci * GNU General Public License for more details. 15987da915Sopenharmony_ci * 16987da915Sopenharmony_ci * You should have received a copy of the GNU General Public License 17987da915Sopenharmony_ci * along with this program (in the main directory of the NTFS-3G 18987da915Sopenharmony_ci * distribution in the file COPYING); if not, write to the Free Software 19987da915Sopenharmony_ci * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 20987da915Sopenharmony_ci */ 21987da915Sopenharmony_ci 22987da915Sopenharmony_ci#include "config.h" 23987da915Sopenharmony_ci 24987da915Sopenharmony_ci#ifdef HAVE_STDLIB_H 25987da915Sopenharmony_ci#include <stdlib.h> 26987da915Sopenharmony_ci#endif 27987da915Sopenharmony_ci#ifdef HAVE_STRING_H 28987da915Sopenharmony_ci#include <string.h> 29987da915Sopenharmony_ci#endif 30987da915Sopenharmony_ci#ifdef HAVE_ERRNO_H 31987da915Sopenharmony_ci#include <errno.h> 32987da915Sopenharmony_ci#endif 33987da915Sopenharmony_ci#include <getopt.h> 34987da915Sopenharmony_ci 35987da915Sopenharmony_ci#include "compat.h" 36987da915Sopenharmony_ci#include "volume.h" 37987da915Sopenharmony_ci#include "misc.h" 38987da915Sopenharmony_ci 39987da915Sopenharmony_citypedef enum { 40987da915Sopenharmony_ci PROBE_UNSET, 41987da915Sopenharmony_ci PROBE_READONLY, 42987da915Sopenharmony_ci PROBE_READWRITE 43987da915Sopenharmony_ci} probe_t; 44987da915Sopenharmony_ci 45987da915Sopenharmony_cistatic struct options { 46987da915Sopenharmony_ci probe_t probetype; 47987da915Sopenharmony_ci char *device; 48987da915Sopenharmony_ci} opts; 49987da915Sopenharmony_ci 50987da915Sopenharmony_cistatic const char *EXEC_NAME = "ntfs-3g.probe"; 51987da915Sopenharmony_ci 52987da915Sopenharmony_cistatic const char *usage_msg = 53987da915Sopenharmony_ci"\n" 54987da915Sopenharmony_ci"%s %s - Probe NTFS volume mountability\n" 55987da915Sopenharmony_ci"\n" 56987da915Sopenharmony_ci"Copyright (C) 2007 Szabolcs Szakacsits\n" 57987da915Sopenharmony_ci"\n" 58987da915Sopenharmony_ci"Usage: %s <--readonly|--readwrite> <device|image_file>\n" 59987da915Sopenharmony_ci"\n" 60987da915Sopenharmony_ci"Example: ntfs-3g.probe --readwrite /dev/sda1\n" 61987da915Sopenharmony_ci"\n" 62987da915Sopenharmony_ci"%s"; 63987da915Sopenharmony_ci 64987da915Sopenharmony_cistatic int ntfs_open(const char *device) 65987da915Sopenharmony_ci{ 66987da915Sopenharmony_ci ntfs_volume *vol; 67987da915Sopenharmony_ci unsigned long flags = 0; 68987da915Sopenharmony_ci int ret = NTFS_VOLUME_OK; 69987da915Sopenharmony_ci 70987da915Sopenharmony_ci if (opts.probetype == PROBE_READONLY) 71987da915Sopenharmony_ci flags |= NTFS_MNT_RDONLY; 72987da915Sopenharmony_ci 73987da915Sopenharmony_ci vol = ntfs_mount(device, flags); 74987da915Sopenharmony_ci if (!vol) 75987da915Sopenharmony_ci ret = ntfs_volume_error(errno); 76987da915Sopenharmony_ci 77987da915Sopenharmony_ci if (ret == 0 && ntfs_umount(vol, FALSE) == -1) 78987da915Sopenharmony_ci ret = ntfs_volume_error(errno); 79987da915Sopenharmony_ci 80987da915Sopenharmony_ci return ret; 81987da915Sopenharmony_ci} 82987da915Sopenharmony_ci 83987da915Sopenharmony_cistatic void usage(void) 84987da915Sopenharmony_ci{ 85987da915Sopenharmony_ci ntfs_log_info(usage_msg, EXEC_NAME, VERSION, EXEC_NAME, ntfs_home); 86987da915Sopenharmony_ci} 87987da915Sopenharmony_ci 88987da915Sopenharmony_cistatic int parse_options(int argc, char *argv[]) 89987da915Sopenharmony_ci{ 90987da915Sopenharmony_ci int c; 91987da915Sopenharmony_ci 92987da915Sopenharmony_ci static const char *sopt = "-hrw"; 93987da915Sopenharmony_ci static const struct option lopt[] = { 94987da915Sopenharmony_ci { "readonly", no_argument, NULL, 'r' }, 95987da915Sopenharmony_ci { "readwrite", no_argument, NULL, 'w' }, 96987da915Sopenharmony_ci { "help", no_argument, NULL, 'h' }, 97987da915Sopenharmony_ci { NULL, 0, NULL, 0 } 98987da915Sopenharmony_ci }; 99987da915Sopenharmony_ci 100987da915Sopenharmony_ci opterr = 0; /* We handle errors. */ 101987da915Sopenharmony_ci opts.probetype = PROBE_UNSET; 102987da915Sopenharmony_ci 103987da915Sopenharmony_ci while ((c = getopt_long(argc, argv, sopt, lopt, NULL)) != -1) { 104987da915Sopenharmony_ci switch (c) { 105987da915Sopenharmony_ci case 1: /* A non-option argument */ 106987da915Sopenharmony_ci if (!opts.device) { 107987da915Sopenharmony_ci opts.device = ntfs_malloc(PATH_MAX + 1); 108987da915Sopenharmony_ci if (!opts.device) 109987da915Sopenharmony_ci return -1; 110987da915Sopenharmony_ci 111987da915Sopenharmony_ci strncpy(opts.device, optarg, PATH_MAX); 112987da915Sopenharmony_ci opts.device[PATH_MAX] = 0; 113987da915Sopenharmony_ci } else { 114987da915Sopenharmony_ci ntfs_log_error("%s: You must specify exactly " 115987da915Sopenharmony_ci "one device\n", EXEC_NAME); 116987da915Sopenharmony_ci return -1; 117987da915Sopenharmony_ci } 118987da915Sopenharmony_ci break; 119987da915Sopenharmony_ci case 'h': 120987da915Sopenharmony_ci usage(); 121987da915Sopenharmony_ci exit(0); 122987da915Sopenharmony_ci case 'r': 123987da915Sopenharmony_ci opts.probetype = PROBE_READONLY; 124987da915Sopenharmony_ci break; 125987da915Sopenharmony_ci case 'w': 126987da915Sopenharmony_ci opts.probetype = PROBE_READWRITE; 127987da915Sopenharmony_ci break; 128987da915Sopenharmony_ci default: 129987da915Sopenharmony_ci ntfs_log_error("%s: Unknown option '%s'.\n", EXEC_NAME, 130987da915Sopenharmony_ci argv[optind - 1]); 131987da915Sopenharmony_ci return -1; 132987da915Sopenharmony_ci } 133987da915Sopenharmony_ci } 134987da915Sopenharmony_ci 135987da915Sopenharmony_ci if (!opts.device) { 136987da915Sopenharmony_ci ntfs_log_error("ERROR: %s: Device is missing\n", EXEC_NAME); 137987da915Sopenharmony_ci return -1; 138987da915Sopenharmony_ci } 139987da915Sopenharmony_ci 140987da915Sopenharmony_ci if (opts.probetype == PROBE_UNSET) { 141987da915Sopenharmony_ci ntfs_log_error("ERROR: %s: Probe type is missing\n", EXEC_NAME); 142987da915Sopenharmony_ci return -1; 143987da915Sopenharmony_ci } 144987da915Sopenharmony_ci 145987da915Sopenharmony_ci return 0; 146987da915Sopenharmony_ci} 147987da915Sopenharmony_ci 148987da915Sopenharmony_ciint main(int argc, char *argv[]) 149987da915Sopenharmony_ci{ 150987da915Sopenharmony_ci int err; 151987da915Sopenharmony_ci 152987da915Sopenharmony_ci ntfs_log_set_handler(ntfs_log_handler_stderr); 153987da915Sopenharmony_ci 154987da915Sopenharmony_ci if (parse_options(argc, argv)) { 155987da915Sopenharmony_ci usage(); 156987da915Sopenharmony_ci exit(NTFS_VOLUME_SYNTAX_ERROR); 157987da915Sopenharmony_ci } 158987da915Sopenharmony_ci 159987da915Sopenharmony_ci err = ntfs_open(opts.device); 160987da915Sopenharmony_ci 161987da915Sopenharmony_ci free(opts.device); 162987da915Sopenharmony_ci if (err) 163987da915Sopenharmony_ci exit(err); 164987da915Sopenharmony_ci return (0); 165987da915Sopenharmony_ci} 166987da915Sopenharmony_ci 167