xref: /original-bsd/usr.sbin/amd/amd/umount_fs.c (revision 4092c5cc)
1398a5aebSmckusick /*
2398a5aebSmckusick  * Copyright (c) 1990 Jan-Simon Pendry
3398a5aebSmckusick  * Copyright (c) 1990 Imperial College of Science, Technology & Medicine
4*4092c5ccSbostic  * Copyright (c) 1990, 1993
5*4092c5ccSbostic  *	The Regents of the University of California.  All rights reserved.
6398a5aebSmckusick  *
7398a5aebSmckusick  * This code is derived from software contributed to Berkeley by
8398a5aebSmckusick  * Jan-Simon Pendry at Imperial College, London.
9398a5aebSmckusick  *
10398a5aebSmckusick  * %sccs.include.redist.c%
11398a5aebSmckusick  *
12*4092c5ccSbostic  *	@(#)umount_fs.c	8.1 (Berkeley) 06/06/93
13c626267eSpendry  *
14cc0207dcSpendry  * $Id: umount_fs.c,v 5.2.2.1 1992/02/09 15:09:10 jsp beta $
15c626267eSpendry  *
16398a5aebSmckusick  */
17398a5aebSmckusick 
18398a5aebSmckusick #include "am.h"
19398a5aebSmckusick 
20398a5aebSmckusick #ifdef NEED_UMOUNT_BSD
21398a5aebSmckusick 
228a89c22cSpendry int umount_fs P((char *fs_name));
umount_fs(fs_name)23398a5aebSmckusick int umount_fs(fs_name)
24398a5aebSmckusick char *fs_name;
25398a5aebSmckusick {
26398a5aebSmckusick 	int error;
27398a5aebSmckusick 
28398a5aebSmckusick eintr:
29d4dfefc4Smckusick 	error = unmount(fs_name, 0);
30398a5aebSmckusick 	if (error < 0)
31398a5aebSmckusick 		error = errno;
32398a5aebSmckusick 
33398a5aebSmckusick 	switch (error) {
34398a5aebSmckusick 	case EINVAL:
35398a5aebSmckusick 	case ENOTBLK:
368a89c22cSpendry 	case ENOENT:
37398a5aebSmckusick 		plog(XLOG_WARNING, "unmount: %s is not mounted", fs_name);
38398a5aebSmckusick 		error = 0;	/* Not really an error */
39398a5aebSmckusick 		break;
40398a5aebSmckusick 
41398a5aebSmckusick 	case EINTR:
42398a5aebSmckusick #ifdef DEBUG
43398a5aebSmckusick 		/* not sure why this happens, but it does.  ask kirk one day... */
44398a5aebSmckusick 		dlog("%s: unmount: %m", fs_name);
45398a5aebSmckusick #endif /* DEBUG */
46398a5aebSmckusick 		goto eintr;
47398a5aebSmckusick 
48398a5aebSmckusick #ifdef DEBUG
49398a5aebSmckusick 	default:
50398a5aebSmckusick 		dlog("%s: unmount: %m", fs_name);
51398a5aebSmckusick 		break;
52398a5aebSmckusick #endif /* DEBUG */
53398a5aebSmckusick 	}
54398a5aebSmckusick 
55398a5aebSmckusick 	return error;
56398a5aebSmckusick }
57398a5aebSmckusick 
58398a5aebSmckusick #endif /* NEED_UMOUNT_BSD */
59398a5aebSmckusick 
60cc0207dcSpendry #ifdef NEED_UMOUNT_OSF
61cc0207dcSpendry 
62cc0207dcSpendry #include <sys/mount.h>		/* For MNT_NOFORCE */
63cc0207dcSpendry 
umount_fs(fs_name)64cc0207dcSpendry int umount_fs(fs_name)
65cc0207dcSpendry char *fs_name;
66cc0207dcSpendry {
67cc0207dcSpendry 	int error;
68cc0207dcSpendry 
69cc0207dcSpendry eintr:
70cc0207dcSpendry 	error = umount(fs_name, MNT_NOFORCE);
71cc0207dcSpendry 	if (error < 0)
72cc0207dcSpendry 		error = errno;
73cc0207dcSpendry 
74cc0207dcSpendry 	switch (error) {
75cc0207dcSpendry 	case EINVAL:
76cc0207dcSpendry 	case ENOTBLK:
77cc0207dcSpendry 		plog(XLOG_WARNING, "unmount: %s is not mounted", fs_name);
78cc0207dcSpendry 		error = 0;	/* Not really an error */
79cc0207dcSpendry 		break;
80cc0207dcSpendry 
81cc0207dcSpendry 	case ENOENT:
82cc0207dcSpendry 		plog(XLOG_ERROR, "mount point %s: %m", fs_name);
83cc0207dcSpendry 		break;
84cc0207dcSpendry 
85cc0207dcSpendry 	case EINTR:
86cc0207dcSpendry #ifdef DEBUG
87cc0207dcSpendry 		/* not sure why this happens, but it does.  ask kirk one day... */
88cc0207dcSpendry 		dlog("%s: unmount: %m", fs_name);
89cc0207dcSpendry #endif /* DEBUG */
90cc0207dcSpendry 		goto eintr;
91cc0207dcSpendry 
92cc0207dcSpendry #ifdef DEBUG
93cc0207dcSpendry 	default:
94cc0207dcSpendry 		dlog("%s: unmount: %m", fs_name);
95cc0207dcSpendry 		break;
96cc0207dcSpendry #endif /* DEBUG */
97cc0207dcSpendry 	}
98cc0207dcSpendry 
99cc0207dcSpendry 	return error;
100cc0207dcSpendry }
101cc0207dcSpendry 
102cc0207dcSpendry #endif /* NEED_UMOUNT_OSF */
103cc0207dcSpendry 
104398a5aebSmckusick #ifdef NEED_UMOUNT_FS
105398a5aebSmckusick 
umount_fs(fs_name)106398a5aebSmckusick int umount_fs(fs_name)
107398a5aebSmckusick char *fs_name;
108398a5aebSmckusick {
109398a5aebSmckusick 	mntlist *mlist, *mp, *mp_save = 0;
110398a5aebSmckusick 	int error = 0;
111398a5aebSmckusick 
112398a5aebSmckusick 	mp = mlist = read_mtab(fs_name);
113398a5aebSmckusick 
114398a5aebSmckusick 	/*
115398a5aebSmckusick 	 * Search the mount table looking for
116398a5aebSmckusick 	 * the correct (ie last) matching entry
117398a5aebSmckusick 	 */
118398a5aebSmckusick 	while (mp) {
119398a5aebSmckusick 		if (strcmp(mp->mnt->mnt_fsname, fs_name) == 0 ||
120398a5aebSmckusick 				strcmp(mp->mnt->mnt_dir, fs_name) == 0)
121398a5aebSmckusick 			mp_save = mp;
122398a5aebSmckusick 		mp = mp->mnext;
123398a5aebSmckusick 	}
124398a5aebSmckusick 
125398a5aebSmckusick 	if (mp_save) {
126398a5aebSmckusick #ifdef DEBUG
127398a5aebSmckusick 		dlog("Trying unmount(%s)", mp_save->mnt->mnt_dir);
128398a5aebSmckusick #endif /* DEBUG */
129cc0207dcSpendry 		/*
130cc0207dcSpendry 		 * This unmount may hang leaving this
131cc0207dcSpendry 		 * process with an exlusive lock on
132cc0207dcSpendry 		 * /etc/mtab. Therefore it is necessary
133cc0207dcSpendry 		 * to unlock mtab, do the unmount, then
134cc0207dcSpendry 		 * lock mtab (again) and reread it and
135cc0207dcSpendry 		 * finally update it.
136cc0207dcSpendry 		 */
137cc0207dcSpendry 		unlock_mntlist();
138398a5aebSmckusick 		if (UNMOUNT_TRAP(mp_save->mnt) < 0) {
139398a5aebSmckusick 			switch (error = errno) {
140398a5aebSmckusick 			case EINVAL:
141398a5aebSmckusick 			case ENOTBLK:
142398a5aebSmckusick 				plog(XLOG_WARNING, "unmount: %s is not mounted", mp_save->mnt->mnt_dir);
143398a5aebSmckusick 				error = 0;	/* Not really an error */
144398a5aebSmckusick 				break;
145398a5aebSmckusick 
146398a5aebSmckusick 			case ENOENT:
147398a5aebSmckusick 				plog(XLOG_ERROR, "mount point %s: %m", mp_save->mnt->mnt_dir);
148398a5aebSmckusick 				break;
149398a5aebSmckusick 
150398a5aebSmckusick 			default:
151398a5aebSmckusick #ifdef DEBUG
152398a5aebSmckusick 				dlog("%s: unmount: %m", mp_save->mnt->mnt_dir);
153398a5aebSmckusick #endif /* DEBUG */
154398a5aebSmckusick 				break;
155398a5aebSmckusick 			}
156398a5aebSmckusick 		}
157cc0207dcSpendry #ifdef DEBUG
158cc0207dcSpendry 		dlog("Finished unmount(%s)", mp_save->mnt->mnt_dir);
159cc0207dcSpendry #endif
160cc0207dcSpendry 
161398a5aebSmckusick 
162398a5aebSmckusick #ifdef UPDATE_MTAB
163398a5aebSmckusick 		if (!error) {
164cc0207dcSpendry 		        free_mntlist(mlist);
165cc0207dcSpendry 			mp = mlist = read_mtab(fs_name);
166cc0207dcSpendry 
167cc0207dcSpendry 			/*
168cc0207dcSpendry 			 * Search the mount table looking for
169cc0207dcSpendry 			 * the correct (ie last) matching entry
170cc0207dcSpendry 			 */
171cc0207dcSpendry 			mp_save = 0;
172cc0207dcSpendry 			while (mp) {
173cc0207dcSpendry 				if (strcmp(mp->mnt->mnt_fsname, fs_name) == 0 ||
174cc0207dcSpendry 						strcmp(mp->mnt->mnt_dir, fs_name) == 0)
175cc0207dcSpendry 					mp_save = mp;
176cc0207dcSpendry 				mp = mp->mnext;
177cc0207dcSpendry 			}
178cc0207dcSpendry 
179cc0207dcSpendry 			if (mp_save) {
180398a5aebSmckusick 				mnt_free(mp_save->mnt);
181398a5aebSmckusick 				mp_save->mnt = 0;
182398a5aebSmckusick 				rewrite_mtab(mlist);
183398a5aebSmckusick 			}
184cc0207dcSpendry 		}
185398a5aebSmckusick #endif /* UPDATE_MTAB */
186398a5aebSmckusick 	} else {
187398a5aebSmckusick 		plog(XLOG_ERROR, "Couldn't find how to unmount %s", fs_name);
188398a5aebSmckusick 		/*
189398a5aebSmckusick 		 * Assume it is already unmounted
190398a5aebSmckusick 		 */
191398a5aebSmckusick 		error = 0;
192398a5aebSmckusick 	}
193398a5aebSmckusick 
194398a5aebSmckusick 	free_mntlist(mlist);
195398a5aebSmckusick 
196398a5aebSmckusick 	return error;
197398a5aebSmckusick }
198398a5aebSmckusick 
199398a5aebSmckusick #endif /* NEED_UMOUNT_FS */
200