1*18c2aff7Sartem /* 2*18c2aff7Sartem * CDDL HEADER START 3*18c2aff7Sartem * 4*18c2aff7Sartem * The contents of this file are subject to the terms of the 5*18c2aff7Sartem * Common Development and Distribution License (the "License"). 6*18c2aff7Sartem * You may not use this file except in compliance with the License. 7*18c2aff7Sartem * 8*18c2aff7Sartem * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9*18c2aff7Sartem * or http://www.opensolaris.org/os/licensing. 10*18c2aff7Sartem * See the License for the specific language governing permissions 11*18c2aff7Sartem * and limitations under the License. 12*18c2aff7Sartem * 13*18c2aff7Sartem * When distributing Covered Code, include this CDDL HEADER in each 14*18c2aff7Sartem * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15*18c2aff7Sartem * If applicable, add the following below this CDDL HEADER, with the 16*18c2aff7Sartem * fields enclosed by brackets "[]" replaced with your own identifying 17*18c2aff7Sartem * information: Portions Copyright [yyyy] [name of copyright owner] 18*18c2aff7Sartem * 19*18c2aff7Sartem * CDDL HEADER END 20*18c2aff7Sartem */ 21*18c2aff7Sartem /* 22*18c2aff7Sartem * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23*18c2aff7Sartem * Use is subject to license terms. 24*18c2aff7Sartem */ 25*18c2aff7Sartem 26*18c2aff7Sartem #pragma ident "%Z%%M% %I% %E% SMI" 27*18c2aff7Sartem 28*18c2aff7Sartem #include <stdio.h> 29*18c2aff7Sartem #include <stdlib.h> 30*18c2aff7Sartem #include <sys/types.h> 31*18c2aff7Sartem #include <sys/stat.h> 32*18c2aff7Sartem #include <dirent.h> 33*18c2aff7Sartem #include <signal.h> 34*18c2aff7Sartem #include <unistd.h> 35*18c2aff7Sartem #include <fcntl.h> 36*18c2aff7Sartem #include <strings.h> 37*18c2aff7Sartem #include <libgen.h> 38*18c2aff7Sartem #include <libintl.h> 39*18c2aff7Sartem #include <errno.h> 40*18c2aff7Sartem #include <sys/syscall.h> 41*18c2aff7Sartem 42*18c2aff7Sartem #include <dbus/dbus.h> 43*18c2aff7Sartem #include <dbus/dbus-glib.h> 44*18c2aff7Sartem #include <dbus/dbus-glib-lowlevel.h> 45*18c2aff7Sartem #include <libhal.h> 46*18c2aff7Sartem 47*18c2aff7Sartem #include <rmm_common.h> 48*18c2aff7Sartem 49*18c2aff7Sartem char *progname; 50*18c2aff7Sartem 51*18c2aff7Sartem static boolean_t d_opt, l_opt, o_opt, u_opt, eject_opt, 52*18c2aff7Sartem closetray_opt, query_opt; 53*18c2aff7Sartem 54*18c2aff7Sartem static void usage(); 55*18c2aff7Sartem static void nomem(); 56*18c2aff7Sartem 57*18c2aff7Sartem static void 58*18c2aff7Sartem usage() 59*18c2aff7Sartem { 60*18c2aff7Sartem if (!u_opt) { 61*18c2aff7Sartem (void) fprintf(stderr, 62*18c2aff7Sartem "%s: [-dlu] [-o options] [nickname | device] " 63*18c2aff7Sartem "[mount_point]\n", progname); 64*18c2aff7Sartem } else { 65*18c2aff7Sartem (void) fprintf(stderr, 66*18c2aff7Sartem "%s: [-dl] [nickname | device]\n", progname); 67*18c2aff7Sartem } 68*18c2aff7Sartem } 69*18c2aff7Sartem 70*18c2aff7Sartem static int 71*18c2aff7Sartem rmmount(int argc, char **argv) 72*18c2aff7Sartem { 73*18c2aff7Sartem int c; 74*18c2aff7Sartem action_t action; 75*18c2aff7Sartem LibHalContext *hal_ctx; 76*18c2aff7Sartem DBusError error; 77*18c2aff7Sartem rmm_error_t rmm_error; 78*18c2aff7Sartem LibHalDrive *d; 79*18c2aff7Sartem GSList *volumes; 80*18c2aff7Sartem const char *default_name; 81*18c2aff7Sartem char **opts = NULL; 82*18c2aff7Sartem int num_opts = 0; 83*18c2aff7Sartem char *mountpoint = NULL; 84*18c2aff7Sartem char **p; 85*18c2aff7Sartem int ret = 0; 86*18c2aff7Sartem 87*18c2aff7Sartem progname = basename(argv[0]); 88*18c2aff7Sartem 89*18c2aff7Sartem if (strcmp(progname, "rmumount") == 0) { 90*18c2aff7Sartem u_opt = B_TRUE; 91*18c2aff7Sartem } 92*18c2aff7Sartem 93*18c2aff7Sartem if (getenv("RMMOUNT_DEBUG") != NULL) { 94*18c2aff7Sartem rmm_debug = 1; 95*18c2aff7Sartem } 96*18c2aff7Sartem 97*18c2aff7Sartem while ((c = getopt(argc, argv, "?dlo:u")) != -1) { 98*18c2aff7Sartem switch (c) { 99*18c2aff7Sartem case 'd': 100*18c2aff7Sartem d_opt = B_TRUE; 101*18c2aff7Sartem break; 102*18c2aff7Sartem case 'l': 103*18c2aff7Sartem l_opt = B_TRUE; 104*18c2aff7Sartem break; 105*18c2aff7Sartem case 'o': 106*18c2aff7Sartem o_opt = B_TRUE; 107*18c2aff7Sartem if ((opts = g_strsplit(optarg, ",", 10)) == NULL) { 108*18c2aff7Sartem nomem(); 109*18c2aff7Sartem } 110*18c2aff7Sartem for (num_opts = 0, p = &opts[0]; *p != NULL; p++) { 111*18c2aff7Sartem num_opts++; 112*18c2aff7Sartem } 113*18c2aff7Sartem break; 114*18c2aff7Sartem case 'u': 115*18c2aff7Sartem u_opt = B_TRUE; 116*18c2aff7Sartem break; 117*18c2aff7Sartem case '?': 118*18c2aff7Sartem usage(); 119*18c2aff7Sartem return (0); 120*18c2aff7Sartem default: 121*18c2aff7Sartem usage(); 122*18c2aff7Sartem return (1); 123*18c2aff7Sartem } 124*18c2aff7Sartem } 125*18c2aff7Sartem 126*18c2aff7Sartem if (u_opt) { 127*18c2aff7Sartem action = UNMOUNT; 128*18c2aff7Sartem } else if (closetray_opt) { 129*18c2aff7Sartem action = CLOSETRAY; 130*18c2aff7Sartem } else if (eject_opt) { 131*18c2aff7Sartem action = EJECT; 132*18c2aff7Sartem } else { 133*18c2aff7Sartem action = INSERT; 134*18c2aff7Sartem } 135*18c2aff7Sartem 136*18c2aff7Sartem if ((hal_ctx = rmm_hal_init(0, 0, 0, &error, &rmm_error)) == NULL) { 137*18c2aff7Sartem (void) fprintf(stderr, gettext("warning: %s\n"), 138*18c2aff7Sartem rmm_strerror(&error, rmm_error)); 139*18c2aff7Sartem rmm_dbus_error_free(&error); 140*18c2aff7Sartem if ((rmm_error == RMM_EDBUS_CONNECT) || 141*18c2aff7Sartem (rmm_error == RMM_EHAL_CONNECT)) { 142*18c2aff7Sartem return (99); 143*18c2aff7Sartem } else { 144*18c2aff7Sartem return (1); 145*18c2aff7Sartem } 146*18c2aff7Sartem } 147*18c2aff7Sartem 148*18c2aff7Sartem if (d_opt) { 149*18c2aff7Sartem /* -d: print default name and exit */ 150*18c2aff7Sartem if ((d = rmm_hal_volume_find_default(hal_ctx, &error, 151*18c2aff7Sartem &default_name, &volumes)) == NULL) { 152*18c2aff7Sartem default_name = "nothing inserted"; 153*18c2aff7Sartem } else { 154*18c2aff7Sartem rmm_volumes_free(volumes); 155*18c2aff7Sartem libhal_drive_free(d); 156*18c2aff7Sartem } 157*18c2aff7Sartem (void) printf(gettext("Default device is: %s\n"), default_name); 158*18c2aff7Sartem } else if (l_opt) { 159*18c2aff7Sartem /* -l: list volumes and exit */ 160*18c2aff7Sartem rmm_print_volume_nicknames(hal_ctx, &error); 161*18c2aff7Sartem } else if (optind == argc) { 162*18c2aff7Sartem /* no name provided, use default */ 163*18c2aff7Sartem if ((d = rmm_hal_volume_find_default(hal_ctx, &error, 164*18c2aff7Sartem &default_name, &volumes)) == NULL) { 165*18c2aff7Sartem (void) fprintf(stderr, 166*18c2aff7Sartem gettext("No default media available\n")); 167*18c2aff7Sartem ret = 1; 168*18c2aff7Sartem } else { 169*18c2aff7Sartem rmm_volumes_free(volumes); 170*18c2aff7Sartem libhal_drive_free(d); 171*18c2aff7Sartem 172*18c2aff7Sartem if (query_opt) { 173*18c2aff7Sartem ret = rmm_rescan(hal_ctx, default_name, 174*18c2aff7Sartem B_TRUE) ? 0 : 1; 175*18c2aff7Sartem } else { 176*18c2aff7Sartem ret = rmm_action(hal_ctx, default_name, action, 177*18c2aff7Sartem 0, 0, 0, 0) ? 0 : 1; 178*18c2aff7Sartem } 179*18c2aff7Sartem } 180*18c2aff7Sartem } else { 181*18c2aff7Sartem if (argc - optind > 1) { 182*18c2aff7Sartem mountpoint = argv[optind + 1]; 183*18c2aff7Sartem } 184*18c2aff7Sartem if (query_opt) { 185*18c2aff7Sartem ret = rmm_rescan(hal_ctx, argv[optind], 186*18c2aff7Sartem B_TRUE) ? 0 : 1; 187*18c2aff7Sartem } else { 188*18c2aff7Sartem ret = rmm_action(hal_ctx, argv[optind], action, 189*18c2aff7Sartem 0, opts, num_opts, mountpoint) ? 0 : 1; 190*18c2aff7Sartem } 191*18c2aff7Sartem } 192*18c2aff7Sartem 193*18c2aff7Sartem rmm_dbus_error_free(&error); 194*18c2aff7Sartem rmm_hal_fini(hal_ctx); 195*18c2aff7Sartem 196*18c2aff7Sartem return (ret); 197*18c2aff7Sartem } 198*18c2aff7Sartem 199*18c2aff7Sartem static int 200*18c2aff7Sartem rmumount(int argc, char **argv) 201*18c2aff7Sartem { 202*18c2aff7Sartem return (rmmount(argc, argv)); 203*18c2aff7Sartem } 204*18c2aff7Sartem 205*18c2aff7Sartem static int 206*18c2aff7Sartem eject(int argc, char **argv) 207*18c2aff7Sartem { 208*18c2aff7Sartem if (getenv("EJECT_CLOSETRAY") != NULL) { 209*18c2aff7Sartem closetray_opt = B_TRUE; 210*18c2aff7Sartem } else if (getenv("EJECT_QUERY") != NULL) { 211*18c2aff7Sartem query_opt = B_TRUE; 212*18c2aff7Sartem } else { 213*18c2aff7Sartem eject_opt = B_TRUE; 214*18c2aff7Sartem } 215*18c2aff7Sartem return (rmmount(argc, argv)); 216*18c2aff7Sartem } 217*18c2aff7Sartem 218*18c2aff7Sartem static void 219*18c2aff7Sartem nomem(void) 220*18c2aff7Sartem { 221*18c2aff7Sartem (void) fprintf(stderr, gettext("%s: Out of memory\n"), progname); 222*18c2aff7Sartem exit(1); 223*18c2aff7Sartem } 224*18c2aff7Sartem 225*18c2aff7Sartem 226*18c2aff7Sartem /* 227*18c2aff7Sartem * get the name by which this program was called 228*18c2aff7Sartem */ 229*18c2aff7Sartem static char * 230*18c2aff7Sartem get_progname(char *path) 231*18c2aff7Sartem { 232*18c2aff7Sartem char *s; 233*18c2aff7Sartem char *p; 234*18c2aff7Sartem 235*18c2aff7Sartem if ((s = strdup(path)) == NULL) { 236*18c2aff7Sartem perror(path); 237*18c2aff7Sartem exit(1); 238*18c2aff7Sartem } 239*18c2aff7Sartem 240*18c2aff7Sartem p = strrchr(s, '/'); 241*18c2aff7Sartem if (p != NULL) { 242*18c2aff7Sartem strcpy(s, p + 1); 243*18c2aff7Sartem } 244*18c2aff7Sartem 245*18c2aff7Sartem return (s); 246*18c2aff7Sartem } 247*18c2aff7Sartem 248*18c2aff7Sartem int 249*18c2aff7Sartem main(int argc, char **argv) 250*18c2aff7Sartem { 251*18c2aff7Sartem int ret = 1; 252*18c2aff7Sartem 253*18c2aff7Sartem vold_init(argc, argv); 254*18c2aff7Sartem 255*18c2aff7Sartem progname = get_progname(argv[0]); 256*18c2aff7Sartem 257*18c2aff7Sartem if (strcmp(progname, "rmmount") == 0) { 258*18c2aff7Sartem if ((getenv("VOLUME_ACTION") != NULL) && 259*18c2aff7Sartem (getenv("VOLUME_PATH") != NULL)) { 260*18c2aff7Sartem ret = vold_rmmount(argc, argv); 261*18c2aff7Sartem } else { 262*18c2aff7Sartem ret = rmmount(argc, argv); 263*18c2aff7Sartem } 264*18c2aff7Sartem } else if (strcmp(progname, "rmumount") == 0) { 265*18c2aff7Sartem ret = rmumount(argc, argv); 266*18c2aff7Sartem } else if (strcmp(progname, "eject") == 0) { 267*18c2aff7Sartem ret = eject(argc, argv); 268*18c2aff7Sartem } else { 269*18c2aff7Sartem (void) fprintf(stderr, "rmmount: invalid program name\n"); 270*18c2aff7Sartem ret = 1; 271*18c2aff7Sartem } 272*18c2aff7Sartem 273*18c2aff7Sartem return (ret); 274*18c2aff7Sartem } 275