aboutsummaryrefslogtreecommitdiff
path: root/libfshelp
diff options
context:
space:
mode:
Diffstat (limited to 'libfshelp')
-rw-r--r--libfshelp/ChangeLog570
-rw-r--r--libfshelp/Makefile38
-rw-r--r--libfshelp/delegate.c65
-rw-r--r--libfshelp/drop-transbox.c28
-rw-r--r--libfshelp/exec-reauth.c152
-rw-r--r--libfshelp/fetch-control.c31
-rw-r--r--libfshelp/fetch-root.c193
-rw-r--r--libfshelp/fshelp.h263
-rw-r--r--libfshelp/get-identity.c88
-rw-r--r--libfshelp/lock-acquire.c134
-rw-r--r--libfshelp/lock-init.c32
-rw-r--r--libfshelp/locks.h28
-rw-r--r--libfshelp/perms-access.c43
-rw-r--r--libfshelp/perms-checkdirmod.c44
-rw-r--r--libfshelp/perms-isowner.c39
-rw-r--r--libfshelp/set-active.c63
-rw-r--r--libfshelp/set-options.c46
-rw-r--r--libfshelp/start-translator-long.c296
-rw-r--r--libfshelp/start-translator.c63
-rw-r--r--libfshelp/touch.c48
-rw-r--r--libfshelp/trans.h32
-rw-r--r--libfshelp/transbox-init.c35
-rw-r--r--libfshelp/translated.c28
23 files changed, 2359 insertions, 0 deletions
diff --git a/libfshelp/ChangeLog b/libfshelp/ChangeLog
new file mode 100644
index 00000000..dfe88e94
--- /dev/null
+++ b/libfshelp/ChangeLog
@@ -0,0 +1,570 @@
+1999-10-07 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * start-translator-long.c (fshelp_start_translator_long): Doc fix.
+ * fshelp.h (fshelp_start_translator_long): Document OWNER_UID.
+
+1999-10-07 Roland McGrath <roland@baalperazim.frob.com>
+
+ * start-translator-long.c (fshelp_start_translator_long): Take new
+ argument OWNER_UID. Get child's proc port and do proc_setowner on it.
+ * fshelp.h: Update decl.
+ * start-translator.c (fshelp_start_translator): Pass new arg to
+ fshelp_start_translator_long with value from geteuid ().
+ * fetch-root.c (fshelp_fetch_root): Pass UID as new arg to
+ fshelp_start_translator_long.
+
+1999-09-12 Roland McGrath <roland@baalperazim.frob.com>
+
+ * delegate.c (fshelp_delegate_translation): Free ARGZ after RPC.
+
+1999-07-11 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * set-options.c (fshelp_set_options): Explicitly cast first arg to
+ argz_extract to keep GCC quiet.
+
+1999-07-01 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * translated.c: New file; guts from fshelp.h.
+ * perms-isowner.c: Likewise.
+ * perms-access.c: Likewise.
+ * prems-checkdirmod.c: Likewise.
+ * touch.c: Likewise.
+ * fshelp.h (fshelp_translated, fshelp_isowner, fshelp_access,
+ fshelp_checkdirmod, fshelp_touch): Replace inline definitions with
+ ordinary declarations.
+ (FSHELP_EI): Removed macro.
+ * fshelp.c: Deleted file.
+ * Makefile (SRCS): Added translated.c, perms-isowner.c,
+ perms-access.c, perms-checkdirmod.c, touch.c. Removed fshelp.c.
+
+Wed Apr 28 03:06:19 1999 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Don't deallocate the
+ INIT_PORT_CWDIR after starting the passive translator; we still
+ need to keep our reference around until the getroot call happens.
+ Reported by Marcus Brinkmann (Marcus.Brinkmann@ruhr-uni-bochum.de).
+
+Tue Apr 20 21:43:20 1999 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): When starting a passive
+ translator, set cwd to be DOTDOT instead of our own cwd.
+
+Sat Mar 6 17:03:02 1999 Thomas Bushnell, BSG <tb@mit.edu>
+
+ * start-translator-long.c (service_fsys_startup): Doc fixes, and
+ omit unused member `dead' from REQUEST.
+
+1999-02-28 Roland McGrath <roland@baalperazim.frob.com>
+
+ * get-identity.c (fshelp_get_identity): Use ports_class_iterate.
+
+1998-12-19 Roland McGrath <roland@baalperazim.frob.com>
+
+ * fetch-root.c (fshelp_fetch_root): Cope when we have a null auth
+ server port (pass our own ports).
+
+1998-09-04 Roland McGrath <roland@baalperazim.frob.com>
+
+ * fshelp.h (fshelp_set_options): Use `const' for `char *' parameter.
+ * set-options.c (fshelp_set_options): Fix defn.
+
+1998-08-21 Roland McGrath <roland@baalperazim.frob.com>
+
+ * Makefile (SRCS): Remove return-buffer.c.
+
+1998-08-20 Roland McGrath <roland@baalperazim.frob.com>
+
+ * fshelp.h: Moved fshelp_return_malloced_buffer to libiohelp.
+ * return-buffer.c: Moved to ../libiohelp/return-buffer.c.
+ (fshelp_return_malloced_buffer): Renamed to iohelp_*.
+
+Tue Jul 1 16:45:27 1997 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * exec-reauth.c (fshelp_exec_reauth): If the new set of eff_uids
+ is empty, then still do proc_setowner, but this time to set it to
+ "unowned" status.
+
+1997-06-12 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_touch): New function.
+ (TOUCH_ATIME, TOUCH_MTIME, TOUCH_CTIME): New macros.
+ Include <maptime.h>.
+
+1997-06-11 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_fetch_root_callback1_t): Chage ARGZ_LEN to type
+ size_t.
+
+Fri Nov 15 14:43:44 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_access): Uh, shift bits the right direction.
+
+Tue Nov 12 22:07:41 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Name idvec members correctly.
+
+ * fshelp.h: <iohelp.h> -> <hurd/iohelp.h>.
+ Include <sys/stat.h>.
+ (fshelp_access): Declare `gotit'.
+
+Wed Nov 6 17:49:33 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_fetch_root): Delete args `uids', `gids',
+ `uids_len', and `gids_len'. New arg `user'.
+ * fetch-root.c (fshelp_fetch_root): Ditto.
+
+ * fshelp.h: Include <iohelp.h>.
+ (fshelp_access, fshelp_isowner, fshelp_checkdirmod): New
+ functions.
+
+Mon Oct 21 21:55:21 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * fshelp.h: Add extern inline protection.
+ * fshelp.c: New file.
+ * Makefile (SRCS): Add fshelp.c.
+
+Sun Oct 13 21:46:18 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * lock-acquire.c (fshelp_acquire_lock): Return success, not EBADF,
+ when unlocking a file which we don't have locked; this is netbsd's
+ behavior.
+
+Thu Oct 10 17:12:19 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * lock-acquire.c (fshelp_acquire_lock): Use hurd_condition_wait so
+ we are properly interruptible.
+
+Thu Sep 12 16:21:51 1996 Thomas Bushnell, n/BSG <thomas@gnu.ai.mit.edu>
+
+ * Makefile (HURDLIBS): New variable.
+ (libfshelp.so): Delete special dependency.
+
+Tue Jul 16 11:30:42 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * lock-acquire.c (EWOULDBLOCK): Define, to work around new libc
+ bug.
+
+Sun Jul 7 21:26:02 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * start-translator.c (fshelp_start_translator): Don't use unsafe
+ MOVE_SEND in call to fshelp_start_translator_long.
+ * fetch-root.c (fshelp_fetch_root): Don't use unsafe MOVE_SEND in
+ call to fshelp_start_translator_long.
+
+Thu Jul 4 15:38:36 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * get-identity.c (fshelp_get_identity): Bother to initialize
+ I->fileno.
+
+Wed Jul 3 11:29:49 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * get-identity.c: New file.
+ * fshelp.h (struct port_bucket): Mention name in global scope.
+ (fshelp_get_identity): New declaration.
+ * Makefile (SRCS): Add get-identity.c.
+
+Thu Jun 27 17:56:44 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * Makefile (LCLHDRS): Add trans.h.
+
+Mon Jun 24 16:00:48 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Deal properly with errors from
+ auth_makeauth.
+
+Fri Jun 21 00:07:26 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * set-options.c (fshelp_set_options): Add & use INPUT arg.
+ * fshelp.h (fshelp_set_options): Add INPUT argument.
+ (fshelp_return_malloced_buffer): New declaration.
+ * return-buffer.c: New file.
+ * Makefile (SRCS): Add return-buffer.c.
+
+Wed Jun 19 18:50:01 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * set-options.c: New file.
+ * fshelp.h: Add fshelp_set_options.
+ * Makefile (SRCS): Add set-options.c.
+
+Fri May 10 16:12:50 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * delegate.c (fshelp_delegate_translation): Don't cast ARGV when
+ calling arg_create.
+
+Thu May 9 11:17:08 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * exec-reauth.c (fshelp_exec_reauth): Provide new third arg to
+ proc_setowner.
+
+ * delegate.c (fshelp_delegate_translation): Cast first arg to
+ argz_create appropriately.
+
+ * fetch-root.c (fshelp_fetch_root) [reauth]: Use new args for
+ auth_user_authenticate.
+
+Fri Apr 26 18:51:07 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * start-translator-long.c (service_fsys_startup): Make mach_msg
+ calls interruptible.
+
+Wed Feb 21 17:09:12 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * set-active.c (fshelp_set_active): When EXCL, make sure the
+ active translator is really active.
+
+ * fetch-root.c (fshelp_fetch_root): Make sure the returned fsys control
+ port is valid.
+
+Wed Feb 14 16:42:31 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * start-translator-long.c (fshelp_start_translator_long):
+ Terminate TASK if the exec fails.
+
+Mon Jan 29 15:32:54 1996 Michael I. Bushnell, p/BSG <mib@gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Use hurd_condition_wait
+ instead of condition_wait.
+
+ * set-active.c (fshelp_set_active): Deal correctly with the case
+ where a passive translator is being started.
+
+Fri Jan 26 17:56:08 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): If io_reauthenticate returns
+ an error, just return MACH_PORT_NULL instead of aborting (the
+ server probably died; not a good sign for the health of the
+ translator, but it's better than dying ourselves...).
+
+Tue Jan 2 15:36:28 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * exec-reauth.c (fshelp_exec_reauth): Don't setgid the uids.
+
+Mon Jan 1 17:13:25 1996 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * exec-reauth.c (fshelp_exec_reauth): New function.
+ * fshelp.h (fshelp_exec_reauth): New declaration.
+ * Makefile (SRCS): Added exec-reauth.c
+
+Mon Nov 6 13:37:52 1995 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * start-translator-long.c (service_fsys_startup): Don't pass the
+ address of reply.realnodeType.msgt_name -- it's not really an int,
+ although the compiler pretends it is.
+
+ * fetch-root.c (fshelp_fetch_root): When PORT_TYPE is
+ MACH_MSG_TYPE_MAKE_SEND, make the right *before* using it.
+ (fshelp_fetch_root): Don't bother reauthenticating the underlying
+ node returned by CALLBACK2 -- it already has the right ids. This
+ also gets rid of a problem with giving away our auth port prematurely.
+
+Wed Nov 1 16:14:08 1995 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Uses two callbacks now. Pass
+ an appropiate function to fshelp_start_translator_long instead of
+ the actual underlying node.
+ * fshelp.h (fshelp_fetch_root_callback1_t,
+ fshelp_fetch_root_callback2_t): New types replacing fshelp_callback_t.
+ (fshelp_fetch_root): Takes two callback args now.
+
+ * start-translator.c (fshelp_start_translator): Change to use a
+ callback function instead of passing the actual node.
+ * start-translator-long.c (fshelp_start_translator_long,
+ service_fsys_startup): Ditto.
+ (service_fsys_startup): Support the open flags coming from the
+ translator.
+ (struct fsys_startup_request): Add the flags field.
+ (flagsCheck): New variable.
+ * fshelp.h (fshelp_open_fn_t): New type.
+ (fshelp_start_translator, fshelp_start_translator_long): Now take
+ a function that opens the underlying node instead of the node itself.
+
+Fri Oct 13 16:52:43 1995 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * start-translator-long.c (fshelp_start_translator_long): Undo
+ last change to file_exec args.
+
+Sat Oct 7 20:20:26 1995 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * start-translator-long.c (fshelp_start_translator_long): Add
+ values for the dealloc parameters to file_exec (all false).
+ Give away our send right to TASK when we do file_exec.
+ Initialize BOOTSTRAP & TASK so the cleanup code doesn't get confused.
+
+Fri Sep 29 17:44:00 1995 Miles Bader <miles@gnu.ai.mit.edu>
+
+ * transbox-init.c (fshelp_transbox_init): Initialize the flags field.
+
+Tue Sep 5 18:25:24 1995 Miles Bader <miles@churchy.gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_delegate_translation): New declaration.
+ * delegate.c (fshelp_delegate_translation): New file, new function.
+
+Fri Sep 1 12:01:06 1995 Miles Bader <miles@churchy.gnu.ai.mit.edu>
+
+ * Makefile (SRCS): Add delegate.c.
+ (REMHDRS): Removed.
+
+Tue Jul 11 14:11:24 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * start-translator-long.c (fshelp_start_translator_long): If
+ PORTS_TYPE is MACH_MSG_TYPE_COPY_SEND, then drop our right on
+ bootstrap after the call, because we are pretending we haven't
+ changed the calling user's state. For the same reason, save the
+ old BOOTSTRAP port value, and restore it after the call.
+
+Thu Jul 6 15:35:23 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * Makefile: Removed dependencies that are now automatically
+ generated.
+
+Mon Jun 26 15:36:21 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Wakeup other blocked calls
+ *before* returning errors provided by fshelp_start_translator_long
+ or CALLBACK.
+
+Fri Jun 23 14:25:52 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Parenthesize assert test
+ correctly.
+ * start-translator-long.c (service_fsys_startup): Parenthesize
+ construction of flags arg correctly.
+
+Thu Jun 22 17:06:51 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root) [reauth]: If PORT is null, then
+ just return it.
+
+ * fetch-root.c (fshelp_fetch_root): Pass type and length
+ parameters in the right order in calls to auth_makeauth and
+ fshelp_start_translator_long.
+
+Wed Jun 21 13:19:44 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fetch-root.c (fshelp_fetch_root): Pass new third arg to
+ fshelp_set_active.
+
+Mon Jun 19 16:41:51 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fetch-control.c (fshelp_fetch_control): Only frob refs if
+ control is non-null.
+
+ * fshelp.h (fshelp_set_active): New parm EXCL.
+ * set-active.c (fshelp_set_active): Implement new interface.
+
+ * fetch-control.c (fshelp_fetch_control): Don't frob obsolete
+ innerlock.
+ * transbox-init.c (fshelp_transbox_init): Don't init obsolete
+ innerlock. Do init TRANSBOX->wakeup.
+ * set-active.c (fshelp_set_active): Don't frob obsolete innerlock.
+ * fetch-root.c (fshelp_fetch_root): Reduce levels of loops. Only
+ change ACTIVE when we are holding the lock. Use condition
+ mechanism to serialize attempts to start the passive translator.
+ * fshelp.h (struct transbox): Delete member `innerlock'. Add
+ members `flags' and `wakeup'; and define values for flags.
+
+Wed Jun 14 13:06:17 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_fetch_root): New arg COOKIE.
+ (fshelp_callback_t): COOKIE->COOKIE1. New arg COOKIE2.
+ * fetch-root.c (fshelp_fetch_root): Take new arg COOKIE and pass
+ it to CALLBACK. Free ARGZ after we're done with them. Never
+ consume the right on DOTDOT.
+ * Makefile (LCLHDRS): Removed trans.h.
+ * handle-startup.c, init-trans.c, start-trans.c,
+ transboot-clean.c, kill-trans.c, trans-iter.c, trans-cntl.c,
+ trans-drop.c, trans.h: Deleted files.
+
+ * Makefile (SRCS): Remove translated.c.
+ * fshelp.h (fshelp_fetch_root): Don't actually need ROOT_TYPE.
+ UIDS and GIDS should be arrays.
+ (fshelp_callback_t): Should be error_t.
+
+Tue Jun 13 15:59:08 1995 Michael I Bushnell <mib@duality.gnu.ai.mit.edu>
+
+ Brand new translator support routines
+ * fshelp.h: Deleted `struct translink', fshelp_transboot_port_type,
+ fshelp_init_trans_link, fshelp_set_control,
+ fshelp_start_translator, fshelp_handle_fsys_startup,
+ fshelp_transboot_clean, fshelp_translator_iterate,
+ fshelp_translator_drop, fshelp_kill_translator.
+ * fshelp.h: Added fshelp_start_translator_long,
+ fshelp_start_translator, `struct transbox', fshelp_fetch_root,
+ fshelp_transbox_init, fshelp_callback_t, fshelp_translated,
+ fshelp_set_active, fshelp_fetch_control, fshelp_drop_transbox.
+ * Makefile (SRCS): Removed handle-startup.c, init-trans.c,
+ start-trans.c, transboot-clean.c, kill-trans.c, trans-iter.c,
+ trans-cntl.c, trans-drop.c. Added start-translator-long.c,
+ start-translator.c, fetch-root.c, transbox-init.c, translated.c,
+ set-active.c, fetch-control.c, and drop-transbox.c.
+ (OBJS): Replaced with computation from $(SRCS).
+ * start-translator.c, fetch-root.c, transbox-init.c, set-active.c,
+ fetch-control.c, drop-transbox.c: New files.
+ * start-translator-long.c: Adapted from ../lib/start-trans.c.
+ Include "fshelp.h" and <assert.h>.
+ (service_fsys_startup): Declare static. Only pass
+ MACH_RCV_TIMEOUT if TIMEOUT is nonzero. New parm `node_type'.
+ (fshelp_start_translator_long): Renamed from start_translator.
+ Lookup up executable at NAME instead of ARGZ. Delete vars
+ INIT_PORTS, FD_PORTS, INIT_INTS, I, and CHILD_PROC. Don't set any
+ of the ports, fds, or ints, with the exception of the bootstrap
+ port. Don't bother getting the child's proc server port.
+ Don't use __USEPORT. If we fail before calling file_exec,
+ then deallocate the ports ourselves, if they were MOVE_SEND.
+
+Fri Oct 28 18:37:56 1994 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
+
+ * start-trans.c: Change `assert (!err)' to `assert_perror (err)'
+ throughout.
+ (fshelp_start_translator): Add assert_perror for io_reauthenticate
+ return.
+
+Mon Sep 19 20:58:35 1994 Michael I Bushnell <mib@churchy.gnu.ai.mit.edu>
+
+ * trans-iter.c (fshelp_translator_iterate): Bother to attach
+ ITEM onto LIST as it's constructed.
+
+Sat Sep 10 08:42:00 1994 Roland McGrath <roland@churchy.gnu.ai.mit.edu>
+
+ * transboot-clean.c (fshelp_transboot_clean): Use EDIED, not EINVAL.
+
+Wed Sep 7 10:34:13 1994 Michael I Bushnell <mib@churchy.gnu.ai.mit.edu>
+
+ * start-trans.c (fshelp_start_translator): RETRY label belongs
+ *after* initial lock of LINK. Unlock LINK before returning.
+
+Tue Sep 6 14:52:49 1994 Michael I Bushnell <mib@churchy.gnu.ai.mit.edu>
+
+ * fshelp.h (struct trans_link): New member `lock'.
+ (fshelp_start_translator): Omit `lock' arg.
+ * trans.h (struct transboot): Omit member `lock'.
+ * init-trans.c (fshelp_init_trans_link): Initialize LINK->lock.
+ * start-trans.c (fshelp_start_translator): Don't set TB->lock.
+ Omit `lock' arg; use LINK->lock instead.
+ (fshelp_start_translator): Don't deallocate DIR.
+ * handle-startup.c (fshelp_handle_fsys_startup): Lock
+ TB->link->lock instead of TB->lock.
+ * transboot-clean.c (fshelp_transboot_clean): Likewise.
+
+Thu Sep 1 16:46:53 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * fshelp.h (fshelp_start_translator): Doc fix.
+ * start-trans.c (fshelp_start_translator): Don't reauthenticate
+ NODE argument; expect fully authenticated node.
+
+Wed Aug 31 14:28:25 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * start-trans.c (fshelp_start_translator): Before call to
+ proc_reauthenticate, CALL mach_reply_port, not just refer to
+ confusing CPP macro.
+
+ * start-trans.c (fshelp_start_translator): Call proc_setowner
+ for new process.
+
+Tue Aug 30 16:19:45 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * start-trans.c: Include <string.h>.
+
+ * start-trans.c (fshelp_start_translator): Use new
+ reauthentication protocol throughout.
+
+ * start-trans.c (fshelp_start_translator): Use
+ hurd_file_name_lookup instead of hurd_path_lookup.
+
+Wed Aug 17 16:03:49 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * start-trans.c (fshelp_start_translator): Designate the new
+ process as our child; then make sure it's under its own
+ authentication. As long as we've gotten the proc port for
+ this operation, might as well pass it too.
+ (fshelp_start_translator): Zero init ints and init ports.
+
+ * transboot-clean.c (fshelp_transboot_clean): Only set an error
+ if we haven't gotten fsys_startup yet.
+
+Mon Aug 15 12:24:47 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * start-trans.c (fshelp_start_translator): Set LINK->starting
+ before blocking.
+ * handle-startup.c (fshelp_handle_fsys_startup): Clear
+ LINK->starting before waking up blocks.
+
+ * fshelp.h (struct trans_link): New member `error'.
+ * transboot-clean.c (fshelp_transboot_clean): Wakeup blocked
+ users with error.
+ * trans-cntl.c (fshelp_set_control): Clear LINK->error.
+ * init-trans.c (fshelp_init_trans_link): Likewise.
+
+ * start-trans.c (fshelp_start_translator): Fix
+ auth_user_authenticate to use the correct rendezvous port in
+ producing realnode from node..
+
+Fri Jul 22 12:03:14 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * Makefile: Rewritten in accord with new scheme.
+
+Wed Jul 20 13:31:39 1994 Michael I Bushnell <mib@geech.gnu.ai.mit.edu>
+
+ * start-trans.c (fshelp_start_translator): Missing first arg
+ to mach_port_deallocate of `dir'.
+
+Tue Jul 19 18:44:53 1994 Michael I Bushnell (mib@churchy.gnu.ai.mit.edu)
+
+ * fshelp.h (fshelp_start_translator): Doc fix.
+ (fshelp_handle_fsys_startup): Deleted dotdot args.
+ * trans.h (struct transboot): Removed member `dir'.
+ * start-trans.c (fshelp_start_translator): Don't initialize
+ TB->dir.
+ (fshelp_start_translator): Deallocate DIR arg when we're
+ done with it.
+ * handle-startup.c (fshelp_handle_fsys_startup): Deleted
+ dotdot args.
+ * transboot-clean.c (fshelp_transboot_clean): Don't free
+ no-longer-existent TB->dir.
+
+Fri Jul 8 12:58:54 1994 Michael I Bushnell (mib@churchy.gnu.ai.mit.edu)
+
+ * trans-cntl.c: Include <assert.h>.
+
+Thu Jul 7 18:08:49 1994 Michael I Bushnell (mib@churchy.gnu.ai.mit.edu)
+
+ * trans-drop.c: New file.
+ * fshelp.h (fshelp_translator_drop): New declaration.
+ * Makefile (OBJS): Added trans-drop.o.
+ (SRCS): ADded trans-drop.c.
+
+Tue Jul 5 14:14:53 1994 Michael I Bushnell (mib@churchy.gnu.ai.mit.edu)
+
+ * Makefile (DIST_FILES): New variable.
+
+Thu Jun 16 16:27:39 1994 Michael I Bushnell (mib@geech.gnu.ai.mit.edu)
+
+ * fshelp.h (fshelp_get_node_port, fshelp_done_with_node): Deleted
+ prototypes.
+ (fshelp_start_translator): Changed types of DIR and NODE to be
+ file_t.
+ * trans.h (struct transboot): Deleted members UID and GID.
+ Changed types of DIR and NODE to be file_t.
+ * transboot-clean.c (fshelp_transboot_clean): Deallocate ports
+ TB->node and TB->dir instead of calling fshelp_done_with_node.
+ * start-trans.c (fshelp_start_translator): Changed types of
+ DIR and MODE to be file_t. Rewritten to behave correctly in
+ numerous ways.
+ * handle-startup.c (fshelp_handle_fsys_startup): Return REAL
+ and DIR from ports in TB instead of calling fshelp_get_node_port.
+
+Fri Jun 3 18:13:04 1994 Michael I Bushnell (mib@churchy.gnu.ai.mit.edu)
+
+ * fshelp.h (fshelp_set_control): New declaration.
+ * trans-cntl.c: New file.
+ * Makefile (SRCS): Added trans-cntl.c.
+ (OBJS): Added trans-cntl.o.
+ trans-cntl.o: Depend on trans.h.
+
+Thu May 5 07:46:00 1994 Roland McGrath (roland@churchy.gnu.ai.mit.edu)
+
+ * Makefile: Change uses of $(headers) to $(includedir).
+
+Mon Feb 14 11:32:59 1994 Roland McGrath (roland@churchy.gnu.ai.mit.edu)
+
+ * Makefile (install): New target.
diff --git a/libfshelp/Makefile b/libfshelp/Makefile
new file mode 100644
index 00000000..6dc47da6
--- /dev/null
+++ b/libfshelp/Makefile
@@ -0,0 +1,38 @@
+#
+# Copyright (C) 1994, 95, 96, 98, 1999 Free Software Foundation, Inc.
+#
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation; either version 2, or (at
+# your option) any later version.
+#
+# This program is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+dir := libfshelp
+makemode := library
+
+libname = libfshelp
+SRCS = lock-acquire.c lock-init.c \
+ start-translator-long.c start-translator.c \
+ fetch-root.c transbox-init.c set-active.c fetch-control.c \
+ drop-transbox.c translated.c \
+ delegate.c \
+ exec-reauth.c \
+ set-options.c \
+ get-identity.c \
+ perms-isowner.c perms-access.c perms-checkdirmod.c \
+ touch.c
+LCLHDRS = fshelp.h locks.h trans.h
+installhdrs = fshelp.h
+
+HURDLIBS=shouldbeinlibc threads
+OBJS = $(subst .c,.o,$(SRCS))
+
+include ../Makeconf
diff --git a/libfshelp/delegate.c b/libfshelp/delegate.c
new file mode 100644
index 00000000..b695a47d
--- /dev/null
+++ b/libfshelp/delegate.c
@@ -0,0 +1,65 @@
+/* fshelp_delegate_translation
+
+ Copyright (C) 1995,96,99 Free Software Foundation, Inc.
+
+ Written by Miles Bader <miles@gnu.org>
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ This program is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include <errno.h>
+#include <string.h>
+#include <argz.h>
+#include <hurd.h>
+#include <hurd/fsys.h>
+#include <hurd/paths.h>
+
+/* Try to hand off responsibility from a translator to the server located on
+ the node SERVER_NAME. REQUESTOR is the translator's bootstrap port, and
+ ARGV is the command line. If SERVER_NAME is NULL, then a name is
+ concocted by appending ARGV[0] to _SERVERS. */
+error_t
+fshelp_delegate_translation (char *server_name,
+ mach_port_t requestor, char **argv)
+{
+ error_t err;
+ file_t server;
+
+ if (! server_name)
+ {
+ char *buf = alloca (strlen (argv[0]) + sizeof (_SERVERS));
+ strcpy (buf, _SERVERS);
+ strcat (buf, argv[0]);
+ server_name = buf;
+ }
+
+ server = file_name_lookup (server_name, 0, 0);
+ if (server != MACH_PORT_NULL)
+ {
+ char *argz;
+ int argz_len;
+ err = argz_create (argv, &argz, &argz_len);
+ if (!err)
+ {
+ err = fsys_forward (server,
+ requestor, MACH_MSG_TYPE_COPY_SEND,
+ argz, argz_len);
+ free (argz);
+ }
+ }
+ else
+ err = errno;
+
+ return err;
+}
diff --git a/libfshelp/drop-transbox.c b/libfshelp/drop-transbox.c
new file mode 100644
index 00000000..d9087488
--- /dev/null
+++ b/libfshelp/drop-transbox.c
@@ -0,0 +1,28 @@
+/*
+ Copyright (C) 1995 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "fshelp.h"
+
+void
+fshelp_drop_transbox (struct transbox *box)
+{
+ if (box->active != MACH_PORT_NULL)
+ mach_port_deallocate (mach_task_self (), box->active);
+}
diff --git a/libfshelp/exec-reauth.c b/libfshelp/exec-reauth.c
new file mode 100644
index 00000000..f0600a1c
--- /dev/null
+++ b/libfshelp/exec-reauth.c
@@ -0,0 +1,152 @@
+/* Setuid reauthentication for exec
+
+ Copyright (C) 1995, 1996, 1997 Free Software Foundation, Inc.
+
+ Written by Miles Bader <miles@gnu.ai.mit.edu>,
+ from the original by Michael I. Bushnell p/BSG <mib@gnu.ai.mit.edu>
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ This program is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include <hurd/io.h>
+#include <hurd/process.h>
+#include <hurd/auth.h>
+#include <idvec.h>
+
+#include "fshelp.h"
+
+extern error_t
+exec_reauth (auth_t auth, int secure, int must_reauth,
+ mach_port_t *ports, unsigned num_ports,
+ mach_port_t *fds, unsigned num_fds);
+
+/* If SUID or SGID is true, adds UID and/or GID respectively to the
+ authentication in PORTS[INIT_PORT_AUTH], and replaces it with the result.
+ All the other ports in PORTS and FDS are then reauthenticated, using any
+ privileges available through AUTH. If GET_FILE_IDS is non-NULL, and the
+ auth port in PORTS[INIT_PORT_AUTH] is bogus, it is called to get a list of
+ uids and gids from the file to use as a replacement. If SECURE is
+ non-NULL, whether not the added ids are new is returned in it. If either
+ the uid or gid case fails, then the other may still be applied. */
+error_t
+fshelp_exec_reauth (int suid, uid_t uid, int sgid, gid_t gid,
+ auth_t auth,
+ error_t
+ (*get_file_ids)(struct idvec *uids, struct idvec *gids),
+ mach_port_t *ports, mach_msg_type_number_t num_ports,
+ mach_port_t *fds, mach_msg_type_number_t num_fds,
+ int *secure)
+{
+ error_t err = 0;
+ int _secure = 0;
+
+ if (suid || sgid)
+ {
+ int already_root = 0;
+ auth_t newauth;
+ /* These variables describe the auth port that the user gave us. */
+ struct idvec *eff_uids = make_idvec (), *avail_uids = make_idvec ();
+ struct idvec *eff_gids = make_idvec (), *avail_gids = make_idvec ();
+
+ if (!eff_uids || !avail_uids || !eff_gids || !avail_gids)
+ goto abandon_suid; /* Allocation error; probably toast, but... */
+
+ /* STEP 0: Fetch the user's current id's. */
+ err = idvec_merge_auth (eff_uids, avail_uids, eff_gids, avail_gids,
+ ports[INIT_PORT_AUTH]);
+ if (err)
+ goto abandon_suid;
+
+ already_root =
+ idvec_contains (eff_uids, 0) || idvec_contains (avail_uids, 0);
+
+ /* If the user's auth port is fraudulent, then these values will be
+ wrong. No matter; we will repeat these checks using secure id sets
+ later if the port turns out to be bogus. */
+ if (suid)
+ err = idvec_setid (eff_uids, avail_uids, uid, &_secure);
+ if (sgid && !err)
+ err = idvec_setid (eff_gids, avail_gids, gid, &_secure);
+ if (err)
+ goto abandon_suid;
+
+ /* STEP 3: Attempt to create this new auth handle. */
+ err = auth_makeauth (auth, &ports[INIT_PORT_AUTH],
+ MACH_MSG_TYPE_COPY_SEND, 1,
+ eff_uids->ids, eff_uids->num,
+ avail_uids->ids, avail_uids->num,
+ eff_gids->ids, eff_gids->num,
+ avail_gids->ids, avail_gids->num,
+ &newauth);
+ if (err == EINVAL && get_file_ids)
+ /* The user's auth port was bogus. As we can't trust what the user
+ has told us about ids, we use the authentication on the file being
+ execed (which we know is good), as the effective ids, and assume
+ no aux ids. */
+ {
+ /* Get rid of all ids from the bogus auth port. */
+ idvec_clear (eff_uids);
+ idvec_clear (avail_uids);
+ idvec_clear (eff_gids);
+ idvec_clear (avail_gids);
+
+ /* Now add some from a source we trust. */
+ err = (*get_file_ids)(eff_uids, eff_gids);
+
+ already_root = idvec_contains (eff_uids, 0);
+ if (suid && !err)
+ err = idvec_setid (eff_uids, avail_uids, uid, &_secure);
+ if (sgid && !err)
+ err = idvec_setid (eff_uids, avail_uids, gid, &_secure);
+ if (err)
+ goto abandon_suid;
+
+ /* Trrrry again... */
+ err = auth_makeauth (auth, 0, MACH_MSG_TYPE_COPY_SEND, 1,
+ eff_uids->ids, eff_uids->num,
+ avail_uids->ids, avail_uids->num,
+ eff_gids->ids, eff_gids->num,
+ avail_gids->ids, avail_gids->num,
+ &newauth);
+ }
+
+ if (err)
+ goto abandon_suid;
+
+ if (already_root)
+ _secure = 0; /* executive privilege */
+
+ /* Re-authenticate the exec parameters. */
+ exec_reauth (newauth, _secure, 0, ports, num_ports, fds, num_fds);
+
+ proc_setowner (ports[INIT_PORT_PROC],
+ eff_uids->num > 0 ? eff_uids->ids[0] : 0,
+ !eff_uids->num);
+
+ abandon_suid:
+ if (eff_uids)
+ idvec_free (eff_uids);
+ if (avail_uids)
+ idvec_free (avail_uids);
+ if (eff_gids)
+ idvec_free (eff_gids);
+ if (avail_gids)
+ idvec_free (avail_gids);
+ }
+
+ if (_secure && secure)
+ *secure = _secure;
+
+ return err;
+}
diff --git a/libfshelp/fetch-control.c b/libfshelp/fetch-control.c
new file mode 100644
index 00000000..26c12d88
--- /dev/null
+++ b/libfshelp/fetch-control.c
@@ -0,0 +1,31 @@
+/*
+ Copyright (C) 1995 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "fshelp.h"
+
+error_t
+fshelp_fetch_control (struct transbox *box,
+ mach_port_t *control)
+{
+ *control = box->active;
+ if (*control != MACH_PORT_NULL)
+ mach_port_mod_refs (mach_task_self (), *control, MACH_PORT_RIGHT_SEND, 1);
+ return 0;
+}
diff --git a/libfshelp/fetch-root.c b/libfshelp/fetch-root.c
new file mode 100644
index 00000000..c712286f
--- /dev/null
+++ b/libfshelp/fetch-root.c
@@ -0,0 +1,193 @@
+/*
+ Copyright (C) 1995, 1996, 1999 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "trans.h"
+#include <unistd.h>
+#include <assert.h>
+#include <string.h>
+#include <hurd/fsys.h>
+
+error_t
+fshelp_fetch_root (struct transbox *box, void *cookie,
+ file_t dotdot,
+ struct iouser *user,
+ int flags,
+ fshelp_fetch_root_callback1_t callback1,
+ fshelp_fetch_root_callback2_t callback2,
+ retry_type *retry, char *retryname,
+ file_t *root)
+{
+ error_t err;
+ mach_port_t control;
+ int cancel;
+ int i;
+
+ start_over:
+
+ if (box->active != MACH_PORT_NULL)
+ assert ((box->flags & TRANSBOX_STARTING) == 0);
+ else
+ {
+ uid_t uid, gid;
+ char *argz;
+ int argz_len;
+ error_t err;
+ mach_port_t ports[INIT_PORT_MAX];
+ int ints[INIT_INT_MAX];
+ mach_port_t fds[STDERR_FILENO + 1];
+ auth_t ourauth, newauth;
+
+ mach_port_t reauth (mach_port_t port) /* Consumes PORT. */
+ {
+ mach_port_t rend, ret;
+ error_t err;
+
+ if (port == MACH_PORT_NULL)
+ return port;
+
+ if (ourauth == MACH_PORT_NULL)
+ /* We have no auth server, so we aren't doing reauthentications.
+ Just pass on our own ports directly. */
+ return port;
+
+ rend = mach_reply_port ();
+
+ err = io_reauthenticate (port, rend,
+ MACH_MSG_TYPE_MAKE_SEND);
+ mach_port_deallocate (mach_task_self (), port);
+ if (! err)
+ err = auth_user_authenticate (newauth, rend,
+ MACH_MSG_TYPE_MAKE_SEND, &ret);
+ if (err)
+ ret = MACH_PORT_NULL;
+
+ mach_port_destroy (mach_task_self (), rend);
+
+ return ret;
+ }
+ error_t fetch_underlying (int flags, mach_port_t *underlying,
+ mach_msg_type_name_t *underlying_type)
+ {
+ return
+ (*callback2) (box->cookie, cookie, flags,
+ underlying, underlying_type);
+ }
+
+ if (box->flags & TRANSBOX_STARTING)
+ {
+ box->flags |= TRANSBOX_WANTED;
+ cancel = hurd_condition_wait (&box->wakeup, box->lock);
+ if (cancel)
+ return EINTR;
+ goto start_over;
+ }
+ box->flags |= TRANSBOX_STARTING;
+ mutex_unlock (box->lock);
+
+ err = (*callback1) (box->cookie, cookie, &uid, &gid, &argz, &argz_len);
+ if (err)
+ goto return_error;
+
+ ourauth = getauth ();
+ if (ourauth == MACH_PORT_NULL)
+ newauth = ourauth;
+ else
+ {
+ uid_t uidarray[2] = { uid, uid };
+ gid_t gidarray[2] = { gid, gid };
+ err = auth_makeauth (ourauth, 0, MACH_MSG_TYPE_MAKE_SEND, 0,
+ uidarray, 1, uidarray, 2,
+ gidarray, 1, gidarray, 2, &newauth);
+ if (err)
+ goto return_error;
+ }
+
+ bzero (ports, INIT_PORT_MAX * sizeof (mach_port_t));
+ bzero (fds, (STDERR_FILENO + 1) * sizeof (mach_port_t));
+ bzero (ints, INIT_INT_MAX * sizeof (int));
+
+ ports[INIT_PORT_CWDIR] = dotdot;
+ ports[INIT_PORT_CRDIR] = reauth (getcrdir ());
+ ports[INIT_PORT_AUTH] = newauth;
+
+ fds[STDERR_FILENO] = reauth (getdport (STDERR_FILENO));
+
+ err = fshelp_start_translator_long (fetch_underlying,
+ argz, argz, argz_len,
+ fds, MACH_MSG_TYPE_COPY_SEND,
+ STDERR_FILENO + 1,
+ ports, MACH_MSG_TYPE_COPY_SEND,
+ INIT_PORT_MAX,
+ ints, INIT_INT_MAX,
+ uid,
+ 0, &control);
+ for (i = 0; i <= STDERR_FILENO; i++)
+ mach_port_deallocate (mach_task_self (), fds[i]);
+
+ for (i = 0; i < INIT_PORT_MAX; i++)
+ if (i != INIT_PORT_CWDIR)
+ mach_port_deallocate (mach_task_self (), ports[i]);
+
+ mutex_lock (box->lock);
+
+ free (argz);
+
+ return_error:
+
+ box->flags &= ~TRANSBOX_STARTING;
+ if (box->flags & TRANSBOX_WANTED)
+ {
+ box->flags &= ~TRANSBOX_WANTED;
+ condition_broadcast (&box->wakeup);
+ }
+
+ if (err)
+ return err;
+
+ if (! MACH_PORT_VALID (control))
+ /* The start translator succeeded, but it returned a bogus port. */
+ return EDIED;
+
+ box->active = control;
+ }
+
+ control = box->active;
+ mach_port_mod_refs (mach_task_self (), control,
+ MACH_PORT_RIGHT_SEND, 1);
+ mutex_unlock (box->lock);
+
+ /* Cancellation point XXX */
+ err = fsys_getroot (control, dotdot, MACH_MSG_TYPE_COPY_SEND,
+ user->uids->ids, user->uids->num,
+ user->gids->ids, user->gids->num,
+ flags, retry, retryname, root);
+
+ mutex_lock (box->lock);
+
+ if ((err == MACH_SEND_INVALID_DEST || err == MIG_SERVER_DIED)
+ && control == box->active)
+ fshelp_set_active (box, MACH_PORT_NULL, 0);
+ mach_port_deallocate (mach_task_self (), control);
+
+ if (err == MACH_SEND_INVALID_DEST || err == MIG_SERVER_DIED)
+ goto start_over;
+
+ return err;
+}
diff --git a/libfshelp/fshelp.h b/libfshelp/fshelp.h
new file mode 100644
index 00000000..08622725
--- /dev/null
+++ b/libfshelp/fshelp.h
@@ -0,0 +1,263 @@
+/* FS helper library definitions
+ Copyright (C) 1994, 95, 96, 97, 98, 1999 Free Software Foundation, Inc.
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ This program is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#ifndef _HURD_FSHELP_
+#define _HURD_FSHELP_
+
+/* This library implements various things that are generic to
+ all or most implementors of the filesystem protocol. It
+ presumes that you are using the iohelp library as well. It
+ is divided into separate facilities which may be used independently. */
+
+#include <errno.h>
+#include <mach.h>
+#include <hurd/hurd_types.h>
+#include <cthreads.h>
+#include <hurd/iohelp.h>
+#include <sys/stat.h>
+#include <maptime.h>
+
+
+/* Passive translator linkage */
+/* These routines are self-contained and start passive translators,
+ returning the control port. They do not require multi threading
+ or the ports library. */
+
+/* A callback used by the translator starting functions, which should be a
+ function that given some open flags, opens the appropiate file, and
+ returns the node port. */
+typedef error_t (*fshelp_open_fn_t) (int flags,
+ file_t *node,
+ mach_msg_type_name_t *node_type);
+
+/* Start a passive translator NAME with arguments ARGZ (length
+ ARGZ_LEN). Initialize the initports to PORTS (length PORTS_LEN),
+ the initints to INTS (length INTS_LEN), and the file descriptor
+ table to FDS (length FDS_LEN). Return the control port in
+ *CONTROL. If the translator doesn't respond or die in TIMEOUT
+ milliseconds (if TIMEOUT > 0), return an appropriate error. If the
+ translator dies before responding, return EDIED. Set the new
+ task's owner to OWNER_UID (or, if OWNER_UID is -1, then clear the
+ new task's owner. */
+error_t
+fshelp_start_translator_long (fshelp_open_fn_t underlying_open_fn,
+ char *name, char *argz, int argz_len,
+ mach_port_t *fds,
+ mach_msg_type_name_t fds_type, int fds_len,
+ mach_port_t *ports,
+ mach_msg_type_name_t ports_type, int ports_len,
+ int *ints, int ints_len,
+ uid_t owner_uid,
+ int timeout, fsys_t *control);
+
+
+/* Same as fshelp_start_translator_long, except the initports and ints
+ are copied from our own state, fd[2] is copied from our own stderr,
+ and the other fds are cleared. */
+error_t
+fshelp_start_translator (fshelp_open_fn_t underlying_open_fn,
+ char *name, char *argz, int argz_len,
+ int timeout, fsys_t *control);
+
+
+/* Active translator linkage */
+
+/* These routines implement the linkage to active translators needed
+ by any filesystem which supports them. They require cthreads and
+ use the passive translator routines above, but they don't require
+ the ports library at all. */
+
+struct transbox
+{
+ fsys_t active;
+ struct mutex *lock;
+ int flags;
+ struct condition wakeup;
+ void *cookie;
+};
+#define TRANSBOX_STARTING 1
+#define TRANSBOX_WANTED 2
+
+/* This interface is complex, because creating the ports and state
+ necessary for start_translator_long is expensive. The caller to
+ fshelp_fetch_root should not need to create them on every call, since
+ usually there will be an existing active translator. */
+
+/* This routine is called by fshelp_fetch_root to fetch more information.
+ Return the owner and group of the underlying translated file in *UID and
+ *GID; point *ARGZ at the entire passive translator spec for the file
+ (setting *ARGZ_LEN to the length.) If there is no passive translator,
+ then return ENOENT. COOKIE1 is the cookie passed in fshelp_transbox_init.
+ COOKIE2 is the cookie passed in the call to fshelp_fetch_root. */
+typedef error_t (*fshelp_fetch_root_callback1_t) (void *cookie1, void *cookie2,
+ uid_t *uid, gid_t *gid,
+ char **argz, size_t *argz_len);
+
+/* This routine is called by fshelp_fetch_root to fetch more information.
+ Return an unauthenticated node for the file itself in *UNDERLYING and
+ *UNDERLYING_TYPE (opened with FLAGS). COOKIE1 is the cookie passed in
+ fshelp_transbox_init. COOKIE2 is the cookie passed in the call to
+ fshelp_fetch_root. */
+typedef error_t (*fshelp_fetch_root_callback2_t) (void *cookie1, void *cookie2,
+ int flags,
+ mach_port_t *underlying,
+ mach_msg_type_name_t
+ *underlying_type);
+
+/* Fetch the root from TRANSBOX. DOTDOT is an unauthenticated port
+ for the directory in which we are looking; USER specifies the ids
+ of the user responsible for the call. FLAGS are as for
+ dir_pathtrans (but O_CREAT and O_EXCL are not meaningful and are
+ ignored). The trasnbox lock (as set by fshelp_transbox_init) must
+ be held before the call, and will be held upon return, but may be
+ released during the operation of the call. */
+error_t
+fshelp_fetch_root (struct transbox *transbox, void *cookie,
+ file_t dotdot,
+ struct iouser *user,
+ int flags,
+ fshelp_fetch_root_callback1_t callback1,
+ fshelp_fetch_root_callback2_t callback2,
+ retry_type *retry, char *retryname, mach_port_t *root);
+
+void
+fshelp_transbox_init (struct transbox *transbox,
+ struct mutex *lock,
+ void *cookie);
+
+/* Return true iff there is an active translator on this box */
+int fshelp_translated (struct transbox *box);
+
+/* Atomically replace the existing active translator port for this box
+ with NEWACTIVE. If EXCL is non-zero then don't frob an existing
+ active; return EBUSY instead. */
+error_t fshelp_set_active (struct transbox *box,
+ fsys_t newactive, int excl);
+
+/* Fetch the control port to make a request on it. It's a bad idea
+ to do fsys_getroot with the result; use fetch_root instead. */
+error_t fshelp_fetch_control (struct transbox *box,
+ mach_port_t *control);
+
+/* A transbox is being deallocated, clean associated state. */
+void fshelp_drop_transbox (struct transbox *box);
+
+
+
+/* Flock handling. */
+struct lock_box
+{
+ int type;
+ struct condition wait;
+ int waiting;
+ int shcount;
+};
+
+/* Call when a user makes a request to acquire an lock via file_lock.
+ There should be one lock box per object and one int per open; these
+ are passed as arguments BOX and USER respectively. FLAGS are as
+ per file_lock. MUT is a mutex which will be held whenever this
+ routine is called, to lock BOX->wait. */
+error_t fshelp_acquire_lock (struct lock_box *box, int *user,
+ struct mutex *mut, int flags);
+
+
+/* Initialize lock_box BOX. (The user int passed to fshelp_acquire_lock
+ should be initialized with LOCK_UN.). */
+void fshelp_lock_init (struct lock_box *box);
+
+
+
+struct port_bucket; /* shut up C compiler */
+/* Return an identity port in *PT for the node numbered FILENO,
+ suitable for returning from io_identity; exactly one send right
+ must be created from the returned value. FILENO should be the same
+ value returned as the `fileno' out-parameter in io_identity, and in
+ the enclosing directory (except for mount points), and in the
+ st_ino stat field. BUCKET should be a ports port bucket; fshelp
+ requires the caller to make sure port operations (for no-senders
+ notifications) are used.
+ */
+error_t fshelp_get_identity (struct port_bucket *bucket,
+ ino_t fileno, mach_port_t *pt);
+
+
+
+/* Try to hand off responsibility from a translator to the server located on
+ the node SERVER_NAME. REQUESTOR is the translator's bootstrap port, and
+ ARGV is the command line. If SERVER_NAME is NULL, then a name is
+ concocted by appending ARGV[0] to _SERVERS. */
+error_t fshelp_delegate_translation (char *server_name,
+ mach_port_t requestor, char **argv);
+
+struct idvec; /* Include <idvec.h> to get the real thing. */
+
+/* If SUID or SGID is true, adds UID and/or GID respectively to the
+ authentication in PORTS[INIT_PORT_AUTH], and replaces it with the result.
+ All the other ports in PORTS and FDS are then reauthenticated, using any
+ privileges available through AUTH. If GET_FILE_IDS is non-NULL, and the
+ auth port in PORTS[INIT_PORT_AUTH] is bogus, it is called to get a list of
+ uids and gids from the file to use as a replacement. If SECURE is
+ non-NULL, whether not the added ids are new is returned in it. If either
+ the uid or gid case fails, then the other may still be applied. */
+error_t
+fshelp_exec_reauth (int suid, uid_t uid, int sgid, gid_t gid,
+ auth_t auth,
+ error_t
+ (*get_file_ids)(struct idvec *uids, struct idvec *gids),
+ mach_port_t *ports, mach_msg_type_number_t num_ports,
+ mach_port_t *fds, mach_msg_type_number_t num_fds,
+ int *secure);
+
+struct argp; /* Include <argp.h> to get the real thing. */
+
+/* Invoke ARGP with data from DATA & LEN, in the standard way. */
+error_t fshelp_set_options (struct argp *argp, int flags,
+ const char *argz, size_t argz_len, void *input);
+
+
+/* Standardized filesystem permission checking */
+
+/* Check to see whether USER should be considered the owner of the
+ file identified by ST. If so, return zero; otherwise return an
+ appropriate error code. */
+error_t fshelp_isowner (struct stat *st, struct iouser *user);
+
+/* Check to see whether the user USER can operate on a file identified
+ by ST. OP is one of S_IREAD, S_IWRITE, and S_IEXEC. If the access
+ is permitted, return zero; otherwise return an appropriate error
+ code. */
+error_t fshelp_access (struct stat *st, int op, struct iouser *user);
+
+/* Check to see whether USER is allowed to modify DIR with respect to
+ existing file ST. (If there is no existing file, pass 0 for ST.)
+ If the access is permissable return 0; otherwise return an
+ appropriate error code. */
+error_t fshelp_checkdirmod (struct stat *dir, struct stat *st,
+ struct iouser *user);
+
+
+/* Timestamps to change. */
+#define TOUCH_ATIME 0x1
+#define TOUCH_MTIME 0x2
+#define TOUCH_CTIME 0x4
+
+/* Change the stat times of NODE as indicated by WHAT (from the set TOUCH_*)
+ to the current time. */
+void fshelp_touch (struct stat *st, unsigned what,
+ volatile struct mapped_time_value *maptime);
+#endif
diff --git a/libfshelp/get-identity.c b/libfshelp/get-identity.c
new file mode 100644
index 00000000..51c5fb29
--- /dev/null
+++ b/libfshelp/get-identity.c
@@ -0,0 +1,88 @@
+/* Helper function for io_identity
+ Copyright (C) 1996, 1999 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell, p/BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+
+#include <fshelp.h>
+#include <hurd/ports.h>
+#include <assert.h>
+
+static struct port_class *idclass = 0;
+static struct mutex idlock = MUTEX_INITIALIZER;
+
+struct idspec
+{
+ struct port_info pi;
+ ino_t fileno;
+};
+
+static void
+id_initialize ()
+{
+ assert (!idclass);
+ idclass = ports_create_class (0, 0);
+}
+
+error_t
+fshelp_get_identity (struct port_bucket *bucket,
+ ino_t fileno,
+ mach_port_t *pt)
+{
+ struct idspec *i;
+ error_t err = 0;
+
+ error_t check_port (void *arg)
+ {
+ struct idspec *i = arg;
+ if (i->fileno == fileno)
+ {
+ *pt = ports_get_right (i);
+ return 1;
+ }
+ else
+ return 0;
+ }
+
+ mutex_lock (&idlock);
+ if (!idclass)
+ id_initialize ();
+
+ *pt = MACH_PORT_NULL;
+
+ ports_class_iterate (idclass, check_port);
+
+ if (*pt != MACH_PORT_NULL)
+ {
+ mutex_unlock (&idlock);
+ return 0;
+ }
+
+ err = ports_create_port (idclass, bucket, sizeof (struct idspec), &i);
+ if (err)
+ {
+ mutex_unlock (&idlock);
+ return err;
+ }
+ i->fileno = fileno;
+
+ *pt = ports_get_right (i);
+ ports_port_deref (i);
+ mutex_unlock (&idlock);
+ return 0;
+}
diff --git a/libfshelp/lock-acquire.c b/libfshelp/lock-acquire.c
new file mode 100644
index 00000000..3d8df550
--- /dev/null
+++ b/libfshelp/lock-acquire.c
@@ -0,0 +1,134 @@
+/*
+ Copyright (C) 1993, 1994, 1996 Free Software Foundation
+
+This file is part of the GNU Hurd.
+
+The GNU Hurd is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+The GNU Hurd is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with the GNU Hurd; see the file COPYING. If not, write to
+the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+/* Written by Michael I. Bushnell. */
+
+#include "locks.h"
+
+#define EWOULDBLOCK EAGAIN /* XXX */
+
+error_t
+fshelp_acquire_lock (struct lock_box *box, int *user, struct mutex *mut,
+ int flags)
+{
+ if (!(flags & (LOCK_UN | LOCK_EX | LOCK_SH)))
+ return 0;
+
+ if ((flags & LOCK_UN)
+ && (flags & (LOCK_SH | LOCK_EX)))
+ return EINVAL;
+
+ if (flags & LOCK_EX)
+ flags &= ~LOCK_SH;
+
+ /* flags now contains exactly one of LOCK_UN, LOCK_SH, or LOCK_EX. */
+
+ if (flags & LOCK_UN)
+ {
+ if (*user & LOCK_UN)
+ return 0;
+
+ assert (*user == box->type);
+ assert (*user == LOCK_SH || *user == LOCK_EX);
+
+ if (*user == LOCK_SH)
+ {
+ if (!--box->shcount)
+ box->type = LOCK_UN;
+ }
+ else if (*user == LOCK_EX)
+ box->type = LOCK_UN;
+
+ if (box->type == LOCK_UN && box->waiting)
+ {
+ box->waiting = 0;
+ condition_broadcast (&box->wait);
+ }
+ *user = LOCK_UN;
+ }
+ else
+ {
+ /* If we have an exclusive lock, release it. */
+ if (*user == LOCK_EX)
+ {
+ *user = LOCK_UN;
+ box->type = LOCK_UN;
+ if (box->waiting)
+ {
+ box->waiting = 0;
+ condition_broadcast (&box->wait);
+ }
+ }
+
+ /* If there is an exclusive lock, wait for it to end. */
+ while (box->type == LOCK_EX)
+ {
+ if (flags & LOCK_NB)
+ return EWOULDBLOCK;
+ box->waiting = 1;
+ if (hurd_condition_wait (&box->wait, mut))
+ return EINTR;
+ }
+
+ /* If we have a shared lock, release it. */
+ if (*user == LOCK_SH)
+ {
+ *user = LOCK_UN;
+ if (!--box->shcount)
+ {
+ box->type = LOCK_UN;
+ if (box->waiting)
+ {
+ box->waiting = 0;
+ condition_broadcast (&box->wait);
+ }
+ }
+ }
+
+ assert ((flags & LOCK_SH) || (flags & LOCK_EX));
+ if (flags & LOCK_SH)
+ {
+ assert (box->type != LOCK_EX);
+ *user = LOCK_SH;
+ box->type = LOCK_SH;
+ box->shcount++;
+ }
+ else if (flags & LOCK_EX)
+ {
+ /* Wait for any shared locks to finish. */
+ while (box->type == LOCK_SH)
+ {
+ if (flags & LOCK_NB)
+ return EWOULDBLOCK;
+ else
+ {
+ box->waiting = 1;
+ if (hurd_condition_wait (&box->wait, mut))
+ return EINTR;
+ }
+ }
+ box->type = LOCK_EX;
+ *user = LOCK_EX;
+ }
+ }
+ return 0;
+}
+
+
+
diff --git a/libfshelp/lock-init.c b/libfshelp/lock-init.c
new file mode 100644
index 00000000..4b1da97e
--- /dev/null
+++ b/libfshelp/lock-init.c
@@ -0,0 +1,32 @@
+/*
+ Copyright (C) 1993, 1994 Free Software Foundation
+
+This file is part of the GNU Hurd.
+
+The GNU Hurd is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+The GNU Hurd is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with the GNU Hurd; see the file COPYING. If not, write to
+the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+/* Written by Michael I. Bushnell. */
+
+#include "locks.h"
+
+/* Initialize a lock box. */
+void
+fshelp_lock_init (struct lock_box *box)
+{
+ box->type = LOCK_UN;
+ condition_init (&box->wait);
+ box->waiting = 0;
+ box->shcount = 0;
+}
diff --git a/libfshelp/locks.h b/libfshelp/locks.h
new file mode 100644
index 00000000..dcecf5d9
--- /dev/null
+++ b/libfshelp/locks.h
@@ -0,0 +1,28 @@
+/*
+ Copyright (C) 1994 Free Software Foundation
+
+This file is part of the GNU Hurd.
+
+The GNU Hurd is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+The GNU Hurd is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with the GNU Hurd; see the file COPYING. If not, write to
+the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+/* Written by Michael I. Bushnell. */
+
+#include <mach.h>
+#include <hurd.h>
+#include <cthreads.h>
+#include <hurd/ports.h>
+#include "fshelp.h"
+#include <sys/file.h>
+#include <assert.h>
diff --git a/libfshelp/perms-access.c b/libfshelp/perms-access.c
new file mode 100644
index 00000000..91ad9da8
--- /dev/null
+++ b/libfshelp/perms-access.c
@@ -0,0 +1,43 @@
+/*
+ Copyright (C) 1999 Free Software Foundation, Inc.
+ Written by Thomas Bushnell, BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+
+#include "fshelp.h"
+
+/* Check to see whether the user USER can operate on a file identified
+ by ST. OP is one of S_IREAD, S_IWRITE, and S_IEXEC. If the access
+ is permitted, return zero; otherwise return an appropriate error
+ code. */
+error_t
+fshelp_access (struct stat *st, int op, struct iouser *user)
+{
+ int gotit;
+ if (idvec_contains (user->uids, 0))
+ gotit = 1;
+ else if (user->uids->num == 0 && (st->st_mode & S_IUSEUNK))
+ gotit = st->st_mode & (op << S_IUNKSHIFT);
+ else if (!fshelp_isowner (st, user))
+ gotit = st->st_mode & op;
+ else if (idvec_contains (user->gids, st->st_gid))
+ gotit = st->st_mode & (op >> 3);
+ else
+ gotit = st->st_mode & (op >> 6);
+ return gotit ? 0 : EACCES;
+}
diff --git a/libfshelp/perms-checkdirmod.c b/libfshelp/perms-checkdirmod.c
new file mode 100644
index 00000000..db4b2e43
--- /dev/null
+++ b/libfshelp/perms-checkdirmod.c
@@ -0,0 +1,44 @@
+/*
+ Copyright (C) 1999 Free Software Foundation, Inc.
+ Written by Thomas Bushnell, BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+
+#include "fshelp.h"
+
+/* Check to see whether USER is allowed to modify DIR with respect to
+ existing file ST. (If there is no existing file, pass 0 for ST.)
+ If the access is permissable return 0; otherwise return an
+ appropriate error code. */
+error_t
+fshelp_checkdirmod (struct stat *dir, struct stat *st, struct iouser *user)
+{
+ error_t err;
+
+ /* The user must be able to write the directory. */
+ err = fshelp_access (dir, S_IWRITE, user);
+ if (err)
+ return err;
+
+ /* If the directory is sticky, the user must own either it or the file. */
+ if ((dir->st_mode & S_ISVTX) && st
+ && fshelp_isowner (dir, user) && fshelp_isowner (st, user))
+ return EACCES;
+
+ return 0;
+}
diff --git a/libfshelp/perms-isowner.c b/libfshelp/perms-isowner.c
new file mode 100644
index 00000000..d1975993
--- /dev/null
+++ b/libfshelp/perms-isowner.c
@@ -0,0 +1,39 @@
+/*
+ Copyright (C) 1999 Free Software Foundation, Inc.
+ Written by Thomas Bushnell, BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+#include "fshelp.h"
+
+/* Check to see whether USER should be considered the owner of the
+ file identified by ST. If so, return zero; otherwise return an
+ appropriate error code. */
+error_t
+fshelp_isowner (struct stat *st, struct iouser *user)
+{
+ /* Permitted if the user has the owner UID, the superuser UID, or if
+ the user is in the group of the file and has the group ID as
+ their user ID. */
+ if (idvec_contains (user->uids, st->st_uid)
+ || idvec_contains (user->uids, 0)
+ || (idvec_contains (user->gids, st->st_gid)
+ && idvec_contains (user->uids, st->st_gid)))
+ return 0;
+ else
+ return EPERM;
+}
diff --git a/libfshelp/set-active.c b/libfshelp/set-active.c
new file mode 100644
index 00000000..4f25a50e
--- /dev/null
+++ b/libfshelp/set-active.c
@@ -0,0 +1,63 @@
+/*
+ Copyright (C) 1995, 1996 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "fshelp.h"
+#include <hurd/fsys.h>
+
+error_t
+fshelp_set_active (struct transbox *box,
+ mach_port_t active,
+ int excl)
+{
+ int cancel;
+
+ if (excl)
+ {
+ if (box->flags & TRANSBOX_STARTING)
+ return EBUSY;
+ if (box->active != MACH_PORT_NULL)
+ /* It looks like there's an existing translator, but make sure. */
+ {
+ mach_port_urefs_t dead_refs;
+ error_t err =
+ mach_port_get_refs (mach_task_self (),
+ box->active, MACH_PORT_RIGHT_DEAD_NAME,
+ &dead_refs);
+ if (!err && dead_refs == 0)
+ /* Still active, we lose. */
+ return EBUSY;
+ }
+ }
+
+ while (box->flags & TRANSBOX_STARTING)
+ {
+ box->flags |= TRANSBOX_WANTED;
+ cancel = hurd_condition_wait (&box->wakeup, box->lock);
+ if (cancel)
+ return EINTR;
+ }
+
+ if (box->active != MACH_PORT_NULL)
+ mach_port_deallocate (mach_task_self (), box->active);
+
+ box->active = active;
+ return 0;
+}
+
diff --git a/libfshelp/set-options.c b/libfshelp/set-options.c
new file mode 100644
index 00000000..13e4001f
--- /dev/null
+++ b/libfshelp/set-options.c
@@ -0,0 +1,46 @@
+/* Standard filesystem runtime option parsing
+
+ Copyright (C) 1996, 1998, 1999 Free Software Foundation, Inc.
+
+ Written by Miles Bader <miles@gnu.ai.mit.edu>
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License along
+ with this program; if not, write to the Free Software Foundation, Inc.,
+ 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include <mach.h>
+#include <argp.h>
+#include <argz.h>
+
+#include "fshelp.h"
+
+/* XXX this is not currently so useful, but the new fsys_set_options will
+ have more commonly used code that can be put here. */
+
+/* Invoke ARGP with data from DATA & LEN, in the standard way. */
+error_t
+fshelp_set_options (struct argp *argp, int flags,
+ const char *argz, size_t argz_len, void *input)
+{
+ int argc = argz_count (argz, argz_len);
+ char **argv = alloca (sizeof (char *) * (argc + 1));
+
+ argz_extract ((char *) argz, argz_len, argv);
+
+ return
+ argp_parse (argp, argc, argv,
+ flags | ARGP_NO_ERRS | ARGP_NO_HELP | ARGP_PARSE_ARGV0,
+ 0, input);
+}
diff --git a/libfshelp/start-translator-long.c b/libfshelp/start-translator-long.c
new file mode 100644
index 00000000..bf576035
--- /dev/null
+++ b/libfshelp/start-translator-long.c
@@ -0,0 +1,296 @@
+/*
+ Copyright (C) 1995, 1996, 1999 Free Software Foundation, Inc.
+ Written by Miles Bader and Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include <hurd.h>
+#include <mach/notify.h>
+#include <mach.h>
+#include <errno.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <string.h>
+#include <assert.h>
+#include "fshelp.h"
+
+
+/* The data passed in the various messages we're interested in. */
+struct fsys_startup_request
+{
+ mach_msg_header_t head;
+ mach_msg_type_t flagsType;
+ int flags;
+ mach_msg_type_t control_portType;
+ mach_port_t control_port;
+};
+
+struct fsys_startup_reply
+{
+ mach_msg_header_t head;
+ mach_msg_type_t RetCodeType;
+ kern_return_t RetCode;
+ mach_msg_type_t realnodeType;
+ mach_port_t realnode;
+};
+
+static const mach_msg_type_t flagsCheck = {
+ MACH_MSG_TYPE_INTEGER_32, /* msgt_name = */
+ 32, /* msgt_size = */
+ 1, /* msgt_number = */
+ TRUE, /* msgt_inline = */
+ FALSE, /* msgt_longform = */
+ FALSE, /* msgt_deallocate = */
+ 0 /* msgt_unused = */
+};
+
+static const mach_msg_type_t control_portCheck =
+{
+ 17, /* msgt_name = */
+ 32, /* msgt_size = */
+ 1, /* msgt_number = */
+ TRUE, /* msgt_inline = */
+ FALSE, /* msgt_longform = */
+ FALSE, /* msgt_deallocate = */
+ 0 /* msgt_unused = */
+};
+
+static const mach_msg_type_t RetCodeType = {
+ MACH_MSG_TYPE_INTEGER_32, /* msgt_name = */
+ 32, /* msgt_size = */
+ 1, /* msgt_number = */
+ TRUE, /* msgt_inline = */
+ FALSE, /* msgt_longform = */
+ FALSE, /* msgt_deallocate = */
+ 0 /* msgt_unused = */
+};
+
+static const mach_msg_type_t realnodeType =
+{
+ -1, /* msgt_name = */
+ 32, /* msgt_size = */
+ 1, /* msgt_number = */
+ TRUE, /* msgt_inline = */
+ FALSE, /* msgt_longform = */
+ FALSE, /* msgt_deallocate = */
+ 0 /* msgt_unused = */
+};
+
+
+/* Wait around for an fsys_startup message on the port PORT from the
+ translator on NODE (timing out after TIMEOUT milliseconds), and return a
+ send right for the resulting fsys control port in CONTROL. If a no-senders
+ notification is received on PORT, then it will be assumed that the
+ translator died, and EDIED will be returned. If an error occurs, the
+ error code is returned, otherwise 0. */
+static error_t
+service_fsys_startup (fshelp_open_fn_t underlying_open_fn,
+ mach_port_t port, long timeout,
+ fsys_t *control)
+{
+ error_t err;
+ union
+ {
+ mach_msg_header_t head;
+ struct fsys_startup_request startup;
+ }
+ request;
+ struct fsys_startup_reply reply;
+
+ /* Wait for the fsys_startup message... */
+ err = mach_msg (&request.head, (MACH_RCV_MSG | MACH_RCV_INTERRUPT
+ | (timeout ? MACH_RCV_TIMEOUT : 0)),
+ 0, sizeof(request), port, timeout, MACH_PORT_NULL);
+ if (err)
+ return err;
+
+ /* Check whether we actually got a no-senders notification instead. */
+ if (request.head.msgh_id == MACH_NOTIFY_NO_SENDERS)
+ return EDIED;
+
+ /* Construct our reply to the fsys_startup rpc. */
+ reply.head.msgh_size = sizeof(reply);
+ reply.head.msgh_bits =
+ MACH_MSGH_BITS(MACH_MSGH_BITS_REMOTE(request.head.msgh_bits), 0);
+ reply.head.msgh_remote_port = request.head.msgh_remote_port;
+ reply.head.msgh_local_port = MACH_PORT_NULL;
+ reply.head.msgh_seqno = 0;
+ reply.head.msgh_id = request.head.msgh_id + 100;
+ reply.RetCodeType = RetCodeType;
+
+ if (request.head.msgh_id != 22000)
+ reply.RetCode = MIG_BAD_ID;
+ else if ((*(int *)&request.startup.control_portType
+ != *(int *)&control_portCheck)
+ || (*(int *)&request.startup.flagsType != *(int *)&flagsCheck))
+ reply.RetCode = MIG_BAD_ARGUMENTS;
+ else
+ {
+ mach_msg_type_name_t realnode_type;
+
+ *control = request.startup.control_port;
+
+ reply.RetCode =
+ (*underlying_open_fn) (request.startup.flags,
+ &reply.realnode, &realnode_type);
+
+ reply.realnodeType = realnodeType;
+ reply.realnodeType.msgt_name = realnode_type;
+
+ if (!reply.RetCode && reply.realnode != MACH_PORT_NULL)
+ /* The message can't be simple because of the port. */
+ reply.head.msgh_bits |= MACH_MSGH_BITS_COMPLEX;
+ }
+
+ err = mach_msg (&reply.head, MACH_SEND_MSG | MACH_SEND_INTERRUPT,
+ sizeof(reply), 0,
+ request.head.msgh_remote_port,
+ MACH_MSG_TIMEOUT_NONE, MACH_PORT_NULL);
+
+ if (reply.RetCode)
+ /* Make our error return be the earlier one. */
+ err = reply.RetCode;
+
+ return err;
+}
+
+
+error_t
+fshelp_start_translator_long (fshelp_open_fn_t underlying_open_fn,
+ char *name, char *argz, int argz_len,
+ mach_port_t *fds,
+ mach_msg_type_name_t fds_type, int fds_len,
+ mach_port_t *ports,
+ mach_msg_type_name_t ports_type, int ports_len,
+ int *ints, int ints_len,
+ uid_t owner_uid,
+ int timeout, fsys_t *control)
+{
+ error_t err;
+ file_t executable;
+ mach_port_t bootstrap = MACH_PORT_NULL;
+ mach_port_t task = MACH_PORT_NULL;
+ mach_port_t prev_notify, proc, saveport, childproc;
+ int ports_moved = 0;
+
+ /* Find the translator itself. Since argz has zero-separated elements, we
+ can use it as a normal string representing the first element. */
+ executable = file_name_lookup(name, O_EXEC, 0);
+ if (executable == MACH_PORT_NULL)
+ return errno;
+
+ /* Create a bootstrap port for the translator. */
+ err =
+ mach_port_allocate(mach_task_self(), MACH_PORT_RIGHT_RECEIVE, &bootstrap);
+ if (err)
+ goto lose;
+
+ /* Create the task for the translator. */
+ err = task_create (mach_task_self (), 0, &task);
+ if (err)
+ goto lose;
+
+ /* Designate TASK as our child and set it's owner accordingly. */
+ proc = getproc ();
+ proc_child (proc, task);
+ err = proc_task2proc (proc, task, &childproc);
+ mach_port_deallocate (mach_task_self (), proc);
+ if (err)
+ goto lose;
+ err = proc_setowner (childproc, owner_uid, owner_uid == (uid_t) -1);
+ mach_port_deallocate (mach_task_self (), childproc);
+ if (err)
+ goto lose;
+
+ assert (ports_len > INIT_PORT_BOOTSTRAP);
+ switch (ports_type)
+ {
+ case MACH_MSG_TYPE_MAKE_SEND:
+ case MACH_MSG_TYPE_MAKE_SEND_ONCE:
+ break;
+
+ case MACH_MSG_TYPE_MOVE_SEND:
+ if (ports[INIT_PORT_BOOTSTRAP] != MACH_PORT_NULL)
+ mach_port_deallocate (mach_task_self (), ports[INIT_PORT_BOOTSTRAP]);
+ mach_port_insert_right (mach_task_self (), bootstrap, bootstrap,
+ MACH_MSG_TYPE_MAKE_SEND);
+ break;
+
+ case MACH_MSG_TYPE_COPY_SEND:
+ mach_port_insert_right (mach_task_self (), bootstrap, bootstrap,
+ MACH_MSG_TYPE_MAKE_SEND);
+ break;
+
+ default:
+ abort ();
+ }
+
+ saveport = ports[INIT_PORT_BOOTSTRAP];
+ ports[INIT_PORT_BOOTSTRAP] = bootstrap;
+
+ /* Try and exec the translator in TASK... */
+ err = file_exec (executable, task, EXEC_DEFAULTS,
+ argz, argz_len, 0, 0,
+ fds, fds_type, fds_len,
+ ports, ports_type, ports_len,
+ ints, ints_len, 0, 0, 0, 0);
+ ports_moved = 1;
+
+ if (ports_type == MACH_MSG_TYPE_COPY_SEND)
+ mach_port_deallocate (mach_task_self (), bootstrap);
+ ports[INIT_PORT_BOOTSTRAP] = saveport;
+
+ if (err)
+ {
+ task_terminate (task);
+ goto lose;
+ }
+
+ /* Ask to be told if TASK dies. */
+ err =
+ mach_port_request_notification(mach_task_self(),
+ bootstrap, MACH_NOTIFY_NO_SENDERS, 0,
+ bootstrap, MACH_MSG_TYPE_MAKE_SEND_ONCE,
+ &prev_notify);
+ if (err)
+ return err;
+
+ /* Ok, cool, we've got a running(?) program, now rendezvous with it if
+ possible using the startup protocol on the bootstrap port... */
+ err = service_fsys_startup(underlying_open_fn, bootstrap, timeout, control);
+
+ lose:
+ if (!ports_moved)
+ {
+ int i;
+
+ if (fds_type == MACH_MSG_TYPE_MOVE_SEND)
+ for (i = 0; i < fds_len; i++)
+ mach_port_deallocate (mach_task_self (), fds[i]);
+ if (ports_type == MACH_MSG_TYPE_MOVE_SEND)
+ for (i = 0; i < ports_len; i++)
+ mach_port_deallocate (mach_task_self (), ports[i]);
+ }
+ if (bootstrap != MACH_PORT_NULL)
+ mach_port_destroy(mach_task_self(), bootstrap);
+ if (executable != MACH_PORT_NULL)
+ mach_port_deallocate(mach_task_self(), executable);
+ if (task != MACH_PORT_NULL)
+ mach_port_deallocate(mach_task_self(), task);
+
+ return err;
+}
diff --git a/libfshelp/start-translator.c b/libfshelp/start-translator.c
new file mode 100644
index 00000000..5996ac74
--- /dev/null
+++ b/libfshelp/start-translator.c
@@ -0,0 +1,63 @@
+/*
+ Copyright (C) 1995, 1996, 1999 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "fshelp.h"
+#include <unistd.h>
+#include <string.h>
+#include <hurd.h>
+
+error_t
+fshelp_start_translator (fshelp_open_fn_t underlying_open_fn,
+ char *name, char *argz, int argz_len,
+ int timeout, fsys_t *control)
+{
+ mach_port_t ports[INIT_PORT_MAX];
+ mach_port_t fds[STDERR_FILENO + 1];
+ int ints[INIT_INT_MAX];
+ int i;
+ error_t err;
+
+ for (i = 0; i < INIT_PORT_MAX; i++)
+ ports[i] = MACH_PORT_NULL;
+ for (i = 0; i < STDERR_FILENO + 1; i++)
+ fds[i] = MACH_PORT_NULL;
+ bzero (ints, INIT_INT_MAX * sizeof (int));
+
+ ports[INIT_PORT_CWDIR] = getcwdir ();
+ ports[INIT_PORT_CRDIR] = getcrdir ();
+ ports[INIT_PORT_AUTH] = getauth ();
+ fds[STDERR_FILENO] = getdport (STDERR_FILENO);
+
+ err = fshelp_start_translator_long (underlying_open_fn,
+ name, argz, argz_len,
+ fds, MACH_MSG_TYPE_COPY_SEND,
+ STDERR_FILENO + 1,
+ ports, MACH_MSG_TYPE_COPY_SEND,
+ INIT_PORT_MAX,
+ ints, INIT_INT_MAX,
+ geteuid (),
+ timeout, control);
+ for (i = 0; i < INIT_PORT_MAX; i++)
+ mach_port_deallocate (mach_task_self (), ports[i]);
+ for (i = 0; i <= STDERR_FILENO; i++)
+ mach_port_deallocate (mach_task_self (), fds[i]);
+
+ return err;
+}
diff --git a/libfshelp/touch.c b/libfshelp/touch.c
new file mode 100644
index 00000000..c254bfbf
--- /dev/null
+++ b/libfshelp/touch.c
@@ -0,0 +1,48 @@
+/*
+ Copyright (C) 1999 Free Software Foundation, Inc.
+ Written by Thomas Bushnell, BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+#include "fshelp.h"
+
+/* Change the stat times of NODE as indicated by WHAT (from the set TOUCH_*)
+ to the current time. */
+void
+fshelp_touch (struct stat *st, unsigned what,
+ volatile struct mapped_time_value *maptime)
+{
+ struct timeval tv;
+
+ maptime_read (maptime, &tv);
+
+ if (what & TOUCH_ATIME)
+ {
+ st->st_atime = tv.tv_sec;
+ st->st_atime_usec = tv.tv_usec;
+ }
+ if (what & TOUCH_CTIME)
+ {
+ st->st_ctime = tv.tv_sec;
+ st->st_ctime_usec = tv.tv_usec;
+ }
+ if (what & TOUCH_MTIME)
+ {
+ st->st_mtime = tv.tv_sec;
+ st->st_mtime_usec = tv.tv_usec;
+ }
+}
diff --git a/libfshelp/trans.h b/libfshelp/trans.h
new file mode 100644
index 00000000..b2416453
--- /dev/null
+++ b/libfshelp/trans.h
@@ -0,0 +1,32 @@
+/*
+ Copyright (C) 1994 Free Software Foundation
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ This program is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include <mach.h>
+#include <hurd.h>
+#include <cthreads.h>
+#include <hurd/ports.h>
+#include "fshelp.h"
+
+struct transboot
+{
+ struct port_info pi;
+ file_t node;
+ struct trans_link *link;
+};
+
+spin_lock_t _fshelp_translistlock;
+struct trans_link *_fshelp_translist;
diff --git a/libfshelp/transbox-init.c b/libfshelp/transbox-init.c
new file mode 100644
index 00000000..1945a57d
--- /dev/null
+++ b/libfshelp/transbox-init.c
@@ -0,0 +1,35 @@
+/*
+ Copyright (C) 1995 Free Software Foundation, Inc.
+ Written by Michael I. Bushnell.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+#include "fshelp.h"
+#include <cthreads.h>
+
+void
+fshelp_transbox_init (struct transbox *transbox,
+ struct mutex *lock,
+ void *cookie)
+{
+ transbox->active = MACH_PORT_NULL;
+ transbox->flags = 0;
+ transbox->lock = lock;
+ condition_init (&transbox->wakeup);
+ transbox->cookie = cookie;
+}
+
diff --git a/libfshelp/translated.c b/libfshelp/translated.c
new file mode 100644
index 00000000..2dc724b6
--- /dev/null
+++ b/libfshelp/translated.c
@@ -0,0 +1,28 @@
+/*
+ Copyright (C) 1999 Free Software Foundation, Inc.
+ Written by Thomas Bushnell, BSG.
+
+ This file is part of the GNU Hurd.
+
+ The GNU Hurd is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License as
+ published by the Free Software Foundation; either version 2, or (at
+ your option) any later version.
+
+ The GNU Hurd is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. */
+
+#include "fshelp.h"
+
+/* Return true iff there is an active translator on this box */
+int
+fshelp_translated (struct transbox *box)
+{
+ return (box->active != MACH_PORT_NULL);
+}