/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
*/
/*
* routines in this module are meant to be called by other libvolmgt
* routines only
*/
#include <stdio.h>
#include <string.h>
#include <dirent.h>
#include <fcntl.h>
#include <string.h>
#ifdef DEBUG
#include <errno.h>
#endif
#include <libintl.h>
#include <limits.h>
#include <unistd.h>
#include <stdlib.h>
#include <volmgt.h>
#include "volmgt_private.h"
struct dk_cinfo *);
/*
* This is an ON Consolidation Private interface.
*
* Is the specified path mounted?
*
* This function is really inadequate for ejection testing. For example,
* ejected. There needs to be some better way to make this check, although
* short of looking up the mounted dev_t in the kernel mount table and
* building in all kinds of knowledge into this function, I'm not sure
* how to do it.
*/
int
{
int ret_val = 0;
/* ensure we have the block spcl pathname */
goto dun;
}
/* mtab is gone... let him go */
goto dun;
}
goto dun;
}
goto dun;
}
goto dun;
}
}
dun:
}
}
if (fd >= 0) {
}
return (ret_val);
}
static int call_unmount_prog(int, int, char *, int, char *,
char *);
static int get_media_info(char *, char **, int *, char **);
/*
* This is an ON Consolidation Private interface.
*
* Forks off rmmount and (in essence) returns the result
*
* a return value of 0 (FALSE) means failure, non-zero (TRUE) means success
*/
int
{
int media_info_gotten = 0;
int mnum = 0;
goto dun;
}
goto dun;
volume_is_not_managed = !volmgt_running() ||
/* decide of we should use rmmount to unmount the media */
if (!volume_is_not_managed) {
/* at least volmgt is running */
vr = (char *)volmgt_root();
/* the block path is rooted in /vol */
}
/* try to get info about media */
} else {
/* volmgt is *not* running */
/*
* volmgt is off and get_media_info() has returned
* info on the media -- soo (this is kinda' a hack)
* ... we iterate, looking for multiple slices
* of (say) a floppy being mounted
*
* note: if an unmount fails we don't want to try
* to unmount the same device on the next try, so
* we try to watch for that
*/
do {
/*
* don't call the unmount program is we're just
* trying to unmount the same device that
* failed last time -- if that's the case,
* then bail
*/
if (spcl_failed != NULL) {
break;
}
}
if (!ret_val) {
/* save spcl device name that failed */
} else {
/*
* unmount succeeded, so clean up
*/
if (spcl_failed != NULL) {
spcl_failed = NULL;
}
}
} else {
/* just do the unmmount cycle once */
}
}
}
}
if (spcl_failed != NULL) {
}
}
dun:
return (ret_val);
}
/*
* find a mnttab entry that has the same dev as the supplied dev,
* returning it and a non-zero value if found, else returning 0
*
* this is just like getmntany(), except that it scans based on st_rdev,
* code copied from format.c)
*/
static int
{
#ifdef DEBUG
#endif
/* reset the mnttab -- just in case */
/* scan each entry in mnttab */
/* don't even try unless it's a local pathname */
continue;
}
/* get char pathname */
continue;
}
continue; /* couldn't get raw name */
}
/* open the device */
/* if we can't open it *assume* it's not a match */
continue;
}
/* stat the device */
continue; /* ain't there: can't be a match */
}
/* ensure we have a spcl device (a double check) */
continue;
}
/* (almost) finally -- check the dev_t for equality */
break;
}
/*
* check that the major numbers match, since if they
* don't then there's no reason to use the DKIOCINFO
* really point to the same device
*/
/* no use continuing, since major devs are different */
continue;
}
continue;
}
/*
* even though minor numbers differ we have a
* match
*/
ret_val = 1;
break;
}
/* go around again */
}
return (ret_val);
}
char *
{
char *cp;
/* check for the degenerate case */
return (path);
}
/* look for the last slash in the name */
/* no slash */
return (path);
}
/* ensure something is after the slash */
return (cp);
}
/* a name that ends in slash -- back up until previous slash */
if (*--cp == '/') {
return (--cp);
}
}
/* the only slash is the end of the name */
return (path);
}
struct dk_cinfo *);
static int
{
/* mtab is gone... let him go */
goto dun;
}
/* get char spcl pathname */
goto dun;
}
goto dun;
}
goto dun;
}
goto dun;
}
goto dun;
}
/* if we found the entry then disect it */
char *cp;
char *mtype;
char *mnt_dir;
int mtype_len;
char *volname;
/* return the spcl device name found */
/*
* try to get the media type (e.g. "floppy") from the mount
*/
if (!volmgt_running() ||
(!volmgt_ownspath(*spclp) &&
goto dun;
}
/* get the first part of the mount point (e.g. "floppy") */
if (*cp++ != '/') {
goto dun;
}
goto dun;
}
/* get the volume name (e.g. "unnamed_floppy") */
/* scan for the symlink that points to our volname */
goto dun;
}
int lb_len;
continue; /* not even close */
}
continue; /* what? */
}
continue; /* not our baby */
}
sizeof (linkbuf))) < 0) {
continue;
}
continue;
}
/* now we have the name! */
/* found it !! */
mnump) == 1) {
}
break;
}
}
}
dun:
}
if (fd >= 0) {
}
}
#ifdef DEBUG
if (ret_val) {
dexit("get_media_info: returning mtype=%s, mnum=%d, spcl=%s\n",
*mnump,
} else {
dexit("get_media_info: FAILED\n");
}
#endif
return (ret_val);
}
/*
* call the appropriate unmount program, returning its success (TRUE)
* or failure (FALSE)
*/
static int
{
#ifdef DEBUG
"call_unmount_prog(%s, %s, \"%s\", %d, \"%s\", \"%s\"): entering\n",
bn);
#endif
/* create a child to unmount the path */
goto dun;
}
if (pid == 0) {
/* the child */
#ifndef DEBUG
int xfd;
#endif
#ifndef DEBUG
/* get rid of those nasty err messages */
}
#endif
if (use_rmm) {
/* set up environment vars */
(void) putenv("VOLUME_ACTION=eject");
if (mi_gotten) {
"VOLUME_MEDIATYPE=%s", mtype);
spcl);
vol_basename(spcl));
} else {
vol_basename(bn));
}
#ifdef DEBUG
#else
#endif
} else {
#ifdef DEBUG
dprintf("call_unmount_prog: calling \"%s %s\"\n",
#endif
NULL);
}
exit(-1);
/*NOTREACHED*/
}
/* wait for the umount command to exit */
if (WEXITSTATUS(rval) == 0) {
}
}
}
dun:
return (ret_val);
}