Whamcloud - gitweb
new upstream libsysio snapshot (20041101)
authorphil <phil>
Fri, 7 Jan 2005 13:46:45 +0000 (13:46 +0000)
committerphil <phil>
Fri, 7 Jan 2005 13:46:45 +0000 (13:46 +0000)
63 files changed:
libsysio/.cvsignore
libsysio/INSTALL [new file with mode: 0644]
libsysio/Rules.make
libsysio/compile [new file with mode: 0755]
libsysio/config.guess [new file with mode: 0755]
libsysio/config.sub [new file with mode: 0755]
libsysio/configure.in
libsysio/depcomp [new file with mode: 0755]
libsysio/dev/stdfd/stdfd.c
libsysio/drivers/incore/fs_incore.c
libsysio/drivers/native/fs_native.c
libsysio/drivers/sockets/sockets.c
libsysio/drivers/yod/fs_yod.c
libsysio/include/inode.h
libsysio/include/module.mk
libsysio/include/native.h [new file with mode: 0644]
libsysio/include/stddir.h [new file with mode: 0644]
libsysio/include/sysio-cmn.h [new file with mode: 0644]
libsysio/include/sysio.h
libsysio/install-sh [new file with mode: 0755]
libsysio/misc/init-env.sh
libsysio/missing [new file with mode: 0755]
libsysio/mkinstalldirs [new file with mode: 0755]
libsysio/src/access.c
libsysio/src/chdir.c
libsysio/src/fcntl.c
libsysio/src/file.c
libsysio/src/file_hack.c
libsysio/src/fs.c
libsysio/src/fsync.c
libsysio/src/getdirentries.c
libsysio/src/init.c
libsysio/src/inode.c
libsysio/src/ioctl.c
libsysio/src/ioctx.c
libsysio/src/iowait.c
libsysio/src/link.c
libsysio/src/lseek.c
libsysio/src/mkdir.c
libsysio/src/mknod.c
libsysio/src/module.mk
libsysio/src/mount.c
libsysio/src/namei.c
libsysio/src/readdir.c [new file with mode: 0644]
libsysio/src/readdir64.c [new file with mode: 0644]
libsysio/src/readlink.c
libsysio/src/reconcile.c [new file with mode: 0644]
libsysio/src/rename.c
libsysio/src/rmdir.c
libsysio/src/rw.c
libsysio/src/stat.c
libsysio/src/stat64.c
libsysio/src/stddir.c [new file with mode: 0644]
libsysio/src/stdlib.c
libsysio/src/symlink.c
libsysio/src/truncate.c
libsysio/src/unlink.c
libsysio/src/utime.c
libsysio/tests/Makefile.am
libsysio/tests/startup.c
libsysio/tests/sysio-run-start.c [new file with mode: 0644]
libsysio/tests/test_all.pl
libsysio/tests/test_stddir.c [new file with mode: 0644]

index 098c549..e02a81f 100644 (file)
@@ -1,9 +1,10 @@
-.deps
-aclocal.m4
 autom4te.cache
+cnos64
+snos64
+cnos32
+snos32
+.deps
+Makefile
 config.log
-config.status
-configure
 lib
-Makefile
-Makefile.in
+libsysio.test.make.log
diff --git a/libsysio/INSTALL b/libsysio/INSTALL
new file mode 100644 (file)
index 0000000..54caf7c
--- /dev/null
@@ -0,0 +1,229 @@
+Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002 Free Software
+Foundation, Inc.
+
+   This file is free documentation; the Free Software Foundation gives
+unlimited permission to copy, distribute and modify it.
+
+Basic Installation
+==================
+
+   These are generic installation instructions.
+
+   The `configure' shell script attempts to guess correct values for
+various system-dependent variables used during compilation.  It uses
+those values to create a `Makefile' in each directory of the package.
+It may also create one or more `.h' files containing system-dependent
+definitions.  Finally, it creates a shell script `config.status' that
+you can run in the future to recreate the current configuration, and a
+file `config.log' containing compiler output (useful mainly for
+debugging `configure').
+
+   It can also use an optional file (typically called `config.cache'
+and enabled with `--cache-file=config.cache' or simply `-C') that saves
+the results of its tests to speed up reconfiguring.  (Caching is
+disabled by default to prevent problems with accidental use of stale
+cache files.)
+
+   If you need to do unusual things to compile the package, please try
+to figure out how `configure' could check whether to do them, and mail
+diffs or instructions to the address given in the `README' so they can
+be considered for the next release.  If you are using the cache, and at
+some point `config.cache' contains results you don't want to keep, you
+may remove or edit it.
+
+   The file `configure.ac' (or `configure.in') is used to create
+`configure' by a program called `autoconf'.  You only need
+`configure.ac' if you want to change it or regenerate `configure' using
+a newer version of `autoconf'.
+
+The simplest way to compile this package is:
+
+  1. `cd' to the directory containing the package's source code and type
+     `./configure' to configure the package for your system.  If you're
+     using `csh' on an old version of System V, you might need to type
+     `sh ./configure' instead to prevent `csh' from trying to execute
+     `configure' itself.
+
+     Running `configure' takes awhile.  While running, it prints some
+     messages telling which features it is checking for.
+
+  2. Type `make' to compile the package.
+
+  3. Optionally, type `make check' to run any self-tests that come with
+     the package.
+
+  4. Type `make install' to install the programs and any data files and
+     documentation.
+
+  5. You can remove the program binaries and object files from the
+     source code directory by typing `make clean'.  To also remove the
+     files that `configure' created (so you can compile the package for
+     a different kind of computer), type `make distclean'.  There is
+     also a `make maintainer-clean' target, but that is intended mainly
+     for the package's developers.  If you use it, you may have to get
+     all sorts of other programs in order to regenerate files that came
+     with the distribution.
+
+Compilers and Options
+=====================
+
+   Some systems require unusual options for compilation or linking that
+the `configure' script does not know about.  Run `./configure --help'
+for details on some of the pertinent environment variables.
+
+   You can give `configure' initial values for configuration parameters
+by setting variables in the command line or in the environment.  Here
+is an example:
+
+     ./configure CC=c89 CFLAGS=-O2 LIBS=-lposix
+
+   *Note Defining Variables::, for more details.
+
+Compiling For Multiple Architectures
+====================================
+
+   You can compile the package for more than one kind of computer at the
+same time, by placing the object files for each architecture in their
+own directory.  To do this, you must use a version of `make' that
+supports the `VPATH' variable, such as GNU `make'.  `cd' to the
+directory where you want the object files and executables to go and run
+the `configure' script.  `configure' automatically checks for the
+source code in the directory that `configure' is in and in `..'.
+
+   If you have to use a `make' that does not support the `VPATH'
+variable, you have to compile the package for one architecture at a
+time in the source code directory.  After you have installed the
+package for one architecture, use `make distclean' before reconfiguring
+for another architecture.
+
+Installation Names
+==================
+
+   By default, `make install' will install the package's files in
+`/usr/local/bin', `/usr/local/man', etc.  You can specify an
+installation prefix other than `/usr/local' by giving `configure' the
+option `--prefix=PATH'.
+
+   You can specify separate installation prefixes for
+architecture-specific files and architecture-independent files.  If you
+give `configure' the option `--exec-prefix=PATH', the package will use
+PATH as the prefix for installing programs and libraries.
+Documentation and other data files will still use the regular prefix.
+
+   In addition, if you use an unusual directory layout you can give
+options like `--bindir=PATH' to specify different values for particular
+kinds of files.  Run `configure --help' for a list of the directories
+you can set and what kinds of files go in them.
+
+   If the package supports it, you can cause programs to be installed
+with an extra prefix or suffix on their names by giving `configure' the
+option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'.
+
+Optional Features
+=================
+
+   Some packages pay attention to `--enable-FEATURE' options to
+`configure', where FEATURE indicates an optional part of the package.
+They may also pay attention to `--with-PACKAGE' options, where PACKAGE
+is something like `gnu-as' or `x' (for the X Window System).  The
+`README' should mention any `--enable-' and `--with-' options that the
+package recognizes.
+
+   For packages that use the X Window System, `configure' can usually
+find the X include and library files automatically, but if it doesn't,
+you can use the `configure' options `--x-includes=DIR' and
+`--x-libraries=DIR' to specify their locations.
+
+Specifying the System Type
+==========================
+
+   There may be some features `configure' cannot figure out
+automatically, but needs to determine by the type of machine the package
+will run on.  Usually, assuming the package is built to be run on the
+_same_ architectures, `configure' can figure that out, but if it prints
+a message saying it cannot guess the machine type, give it the
+`--build=TYPE' option.  TYPE can either be a short name for the system
+type, such as `sun4', or a canonical name which has the form:
+
+     CPU-COMPANY-SYSTEM
+
+where SYSTEM can have one of these forms:
+
+     OS KERNEL-OS
+
+   See the file `config.sub' for the possible values of each field.  If
+`config.sub' isn't included in this package, then this package doesn't
+need to know the machine type.
+
+   If you are _building_ compiler tools for cross-compiling, you should
+use the `--target=TYPE' option to select the type of system they will
+produce code for.
+
+   If you want to _use_ a cross compiler, that generates code for a
+platform different from the build platform, you should specify the
+"host" platform (i.e., that on which the generated programs will
+eventually be run) with `--host=TYPE'.
+
+Sharing Defaults
+================
+
+   If you want to set default values for `configure' scripts to share,
+you can create a site shell script called `config.site' that gives
+default values for variables like `CC', `cache_file', and `prefix'.
+`configure' looks for `PREFIX/share/config.site' if it exists, then
+`PREFIX/etc/config.site' if it exists.  Or, you can set the
+`CONFIG_SITE' environment variable to the location of the site script.
+A warning: not all `configure' scripts look for a site script.
+
+Defining Variables
+==================
+
+   Variables not defined in a site shell script can be set in the
+environment passed to `configure'.  However, some packages may run
+configure again during the build, and the customized values of these
+variables may be lost.  In order to avoid this problem, you should set
+them in the `configure' command line, using `VAR=value'.  For example:
+
+     ./configure CC=/usr/local2/bin/gcc
+
+will cause the specified gcc to be used as the C compiler (unless it is
+overridden in the site shell script).
+
+`configure' Invocation
+======================
+
+   `configure' recognizes the following options to control how it
+operates.
+
+`--help'
+`-h'
+     Print a summary of the options to `configure', and exit.
+
+`--version'
+`-V'
+     Print the version of Autoconf used to generate the `configure'
+     script, and exit.
+
+`--cache-file=FILE'
+     Enable the cache: use and save the results of the tests in FILE,
+     traditionally `config.cache'.  FILE defaults to `/dev/null' to
+     disable caching.
+
+`--config-cache'
+`-C'
+     Alias for `--cache-file=config.cache'.
+
+`--quiet'
+`--silent'
+`-q'
+     Do not print messages saying which checks are being made.  To
+     suppress all normal output, redirect it to `/dev/null' (any error
+     messages will still be shown).
+
+`--srcdir=DIR'
+     Look for the package's source code in directory DIR.  Usually
+     `configure' can determine that directory automatically.
+
+`configure' also accepts some other, not widely useful, options.  Run
+`configure --help' for more details.
+
index 057611b..e2558c9 100644 (file)
@@ -16,4 +16,4 @@ DEV_CPPFLAGS = $(STDFD_DEV_CPPFLAGS)
 AM_CPPFLAGS = \
        -D_POSIX_C_SOURCE=199506L -D_XOPEN_SOURCE=600 \
        $(AUTOMOUNT) $(ZERO_SUM_MEMORY) $(DEV_CPPFLAGS) $(SOCKETS_CPPFLAGS) \
-       -I$(top_srcdir)/include 
+       $(DEFER_INIT_CWD) -I$(top_srcdir)/include 
diff --git a/libsysio/compile b/libsysio/compile
new file mode 100755 (executable)
index 0000000..9bb997a
--- /dev/null
@@ -0,0 +1,99 @@
+#! /bin/sh
+
+# Wrapper for compilers which do not understand `-c -o'.
+
+# Copyright 1999, 2000 Free Software Foundation, Inc.
+# Written by Tom Tromey <tromey@cygnus.com>.
+#
+# 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Usage:
+# compile PROGRAM [ARGS]...
+# `-o FOO.o' is removed from the args passed to the actual compile.
+
+prog=$1
+shift
+
+ofile=
+cfile=
+args=
+while test $# -gt 0; do
+   case "$1" in
+    -o)
+       # configure might choose to run compile as `compile cc -o foo foo.c'.
+       # So we do something ugly here.
+       ofile=$2
+       shift
+       case "$ofile" in
+       *.o | *.obj)
+          ;;
+       *)
+          args="$args -o $ofile"
+          ofile=
+          ;;
+       esac
+       ;;
+    *.c)
+       cfile=$1
+       args="$args $1"
+       ;;
+    *)
+       args="$args $1"
+       ;;
+   esac
+   shift
+done
+
+if test -z "$ofile" || test -z "$cfile"; then
+   # If no `-o' option was seen then we might have been invoked from a
+   # pattern rule where we don't need one.  That is ok -- this is a
+   # normal compilation that the losing compiler can handle.  If no
+   # `.c' file was seen then we are probably linking.  That is also
+   # ok.
+   exec "$prog" $args
+fi
+
+# Name of file we expect compiler to create.
+cofile=`echo $cfile | sed -e 's|^.*/||' -e 's/\.c$/.o/'`
+
+# Create the lock directory.
+# Note: use `[/.-]' here to ensure that we don't use the same name
+# that we are using for the .o file.  Also, base the name on the expected
+# object file name, since that is what matters with a parallel build.
+lockdir=`echo $cofile | sed -e 's|[/.-]|_|g'`.d
+while true; do
+   if mkdir $lockdir > /dev/null 2>&1; then
+      break
+   fi
+   sleep 1
+done
+# FIXME: race condition here if user kills between mkdir and trap.
+trap "rmdir $lockdir; exit 1" 1 2 15
+
+# Run the compile.
+"$prog" $args
+status=$?
+
+if test -f "$cofile"; then
+   mv "$cofile" "$ofile"
+fi
+
+rmdir $lockdir
+exit $status
diff --git a/libsysio/config.guess b/libsysio/config.guess
new file mode 100755 (executable)
index 0000000..c8fc683
--- /dev/null
@@ -0,0 +1,1417 @@
+#! /bin/sh
+# Attempt to guess a canonical system name.
+#   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
+#   2000, 2001, 2002, 2003 Free Software Foundation, Inc.
+
+timestamp='2003-07-02'
+
+# This file 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 of the License, 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+#
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Originally written by Per Bothner <per@bothner.com>.
+# Please send patches to <config-patches@gnu.org>.  Submit a context
+# diff and a properly formatted ChangeLog entry.
+#
+# This script attempts to guess a canonical system name similar to
+# config.sub.  If it succeeds, it prints the system name on stdout, and
+# exits with 0.  Otherwise, it exits with 1.
+#
+# The plan is that this can be called by configure scripts if you
+# don't specify an explicit build system type.
+
+me=`echo "$0" | sed -e 's,.*/,,'`
+
+usage="\
+Usage: $0 [OPTION]
+
+Output the configuration name of the system \`$me' is run on.
+
+Operation modes:
+  -h, --help         print this help, then exit
+  -t, --time-stamp   print date of last modification, then exit
+  -v, --version      print version number, then exit
+
+Report bugs and patches to <config-patches@gnu.org>."
+
+version="\
+GNU config.guess ($timestamp)
+
+Originally written by Per Bothner.
+Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
+Free Software Foundation, Inc.
+
+This is free software; see the source for copying conditions.  There is NO
+warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
+
+help="
+Try \`$me --help' for more information."
+
+# Parse command line
+while test $# -gt 0 ; do
+  case $1 in
+    --time-stamp | --time* | -t )
+       echo "$timestamp" ; exit 0 ;;
+    --version | -v )
+       echo "$version" ; exit 0 ;;
+    --help | --h* | -h )
+       echo "$usage"; exit 0 ;;
+    -- )     # Stop option processing
+       shift; break ;;
+    - )        # Use stdin as input.
+       break ;;
+    -* )
+       echo "$me: invalid option $1$help" >&2
+       exit 1 ;;
+    * )
+       break ;;
+  esac
+done
+
+if test $# != 0; then
+  echo "$me: too many arguments$help" >&2
+  exit 1
+fi
+
+trap 'exit 1' 1 2 15
+
+# CC_FOR_BUILD -- compiler used by this script. Note that the use of a
+# compiler to aid in system detection is discouraged as it requires
+# temporary files to be created and, as you can see below, it is a
+# headache to deal with in a portable fashion.
+
+# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still
+# use `HOST_CC' if defined, but it is deprecated.
+
+# Portable tmp directory creation inspired by the Autoconf team.
+
+set_cc_for_build='
+trap "exitcode=\$?; (rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null) && exit \$exitcode" 0 ;
+trap "rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null; exit 1" 1 2 13 15 ;
+: ${TMPDIR=/tmp} ;
+ { tmp=`(umask 077 && mktemp -d -q "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } ||
+ { test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } ||
+ { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo "Warning: creating insecure temp directory" >&2 ; } ||
+ { echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } ;
+dummy=$tmp/dummy ;
+tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ;
+case $CC_FOR_BUILD,$HOST_CC,$CC in
+ ,,)    echo "int x;" > $dummy.c ;
+       for c in cc gcc c89 c99 ; do
+         if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then
+            CC_FOR_BUILD="$c"; break ;
+         fi ;
+       done ;
+       if test x"$CC_FOR_BUILD" = x ; then
+         CC_FOR_BUILD=no_compiler_found ;
+       fi
+       ;;
+ ,,*)   CC_FOR_BUILD=$CC ;;
+ ,*,*)  CC_FOR_BUILD=$HOST_CC ;;
+esac ;'
+
+# This is needed to find uname on a Pyramid OSx when run in the BSD universe.
+# (ghazi@noc.rutgers.edu 1994-08-24)
+if (test -f /.attbin/uname) >/dev/null 2>&1 ; then
+       PATH=$PATH:/.attbin ; export PATH
+fi
+
+UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown
+UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown
+UNAME_SYSTEM=`(uname -s) 2>/dev/null`  || UNAME_SYSTEM=unknown
+UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
+
+case "${UNAME_MACHINE}" in
+    i?86)
+       test -z "$VENDOR" && VENDOR=pc
+       ;;
+    *)
+       test -z "$VENDOR" && VENDOR=unknown
+       ;;
+esac
+test -f /etc/SuSE-release -o -f /.buildenv && VENDOR=suse
+
+# Note: order is significant - the case branches are not exclusive.
+
+case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
+    *:NetBSD:*:*)
+       # NetBSD (nbsd) targets should (where applicable) match one or
+       # more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*,
+       # *-*-netbsdecoff* and *-*-netbsd*.  For targets that recently
+       # switched to ELF, *-*-netbsd* would select the old
+       # object file format.  This provides both forward
+       # compatibility and a consistent mechanism for selecting the
+       # object file format.
+       #
+       # Note: NetBSD doesn't particularly care about the vendor
+       # portion of the name.  We always set it to "unknown".
+       sysctl="sysctl -n hw.machine_arch"
+       UNAME_MACHINE_ARCH=`(/sbin/$sysctl 2>/dev/null || \
+           /usr/sbin/$sysctl 2>/dev/null || echo unknown)`
+       case "${UNAME_MACHINE_ARCH}" in
+           armeb) machine=armeb-unknown ;;
+           arm*) machine=arm-unknown ;;
+           sh3el) machine=shl-unknown ;;
+           sh3eb) machine=sh-unknown ;;
+           *) machine=${UNAME_MACHINE_ARCH}-unknown ;;
+       esac
+       # The Operating System including object format, if it has switched
+       # to ELF recently, or will in the future.
+       case "${UNAME_MACHINE_ARCH}" in
+           arm*|i386|m68k|ns32k|sh3*|sparc|vax)
+               eval $set_cc_for_build
+               if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \
+                       | grep __ELF__ >/dev/null
+               then
+                   # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout).
+                   # Return netbsd for either.  FIX?
+                   os=netbsd
+               else
+                   os=netbsdelf
+               fi
+               ;;
+           *)
+               os=netbsd
+               ;;
+       esac
+       # The OS release
+       # Debian GNU/NetBSD machines have a different userland, and
+       # thus, need a distinct triplet. However, they do not need
+       # kernel version information, so it can be replaced with a
+       # suitable tag, in the style of linux-gnu.
+       case "${UNAME_VERSION}" in
+           Debian*)
+               release='-gnu'
+               ;;
+           *)
+               release=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'`
+               ;;
+       esac
+       # Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:
+       # contains redundant information, the shorter form:
+       # CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
+       echo "${machine}-${os}${release}"
+       exit 0 ;;
+    amiga:OpenBSD:*:*)
+       echo m68k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    arc:OpenBSD:*:*)
+       echo mipsel-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    hp300:OpenBSD:*:*)
+       echo m68k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    mac68k:OpenBSD:*:*)
+       echo m68k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    macppc:OpenBSD:*:*)
+       echo powerpc-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    mvme68k:OpenBSD:*:*)
+       echo m68k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    mvme88k:OpenBSD:*:*)
+       echo m88k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    mvmeppc:OpenBSD:*:*)
+       echo powerpc-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    pmax:OpenBSD:*:*)
+       echo mipsel-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    sgi:OpenBSD:*:*)
+       echo mipseb-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    sun3:OpenBSD:*:*)
+       echo m68k-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    wgrisc:OpenBSD:*:*)
+       echo mipsel-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    *:OpenBSD:*:*)
+       echo ${UNAME_MACHINE}-unknown-openbsd${UNAME_RELEASE}
+       exit 0 ;;
+    alpha:OSF1:*:*)
+       if test $UNAME_RELEASE = "V4.0"; then
+               UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`
+       fi
+       # According to Compaq, /usr/sbin/psrinfo has been available on
+       # OSF/1 and Tru64 systems produced since 1995.  I hope that
+       # covers most systems running today.  This code pipes the CPU
+       # types through head -n 1, so we only detect the type of CPU 0.
+       ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^  The alpha \(.*\) processor.*$/\1/p' | head -n 1`
+       case "$ALPHA_CPU_TYPE" in
+           "EV4 (21064)")
+               UNAME_MACHINE="alpha" ;;
+           "EV4.5 (21064)")
+               UNAME_MACHINE="alpha" ;;
+           "LCA4 (21066/21068)")
+               UNAME_MACHINE="alpha" ;;
+           "EV5 (21164)")
+               UNAME_MACHINE="alphaev5" ;;
+           "EV5.6 (21164A)")
+               UNAME_MACHINE="alphaev56" ;;
+           "EV5.6 (21164PC)")
+               UNAME_MACHINE="alphapca56" ;;
+           "EV5.7 (21164PC)")
+               UNAME_MACHINE="alphapca57" ;;
+           "EV6 (21264)")
+               UNAME_MACHINE="alphaev6" ;;
+           "EV6.7 (21264A)")
+               UNAME_MACHINE="alphaev67" ;;
+           "EV6.8CB (21264C)")
+               UNAME_MACHINE="alphaev68" ;;
+           "EV6.8AL (21264B)")
+               UNAME_MACHINE="alphaev68" ;;
+           "EV6.8CX (21264D)")
+               UNAME_MACHINE="alphaev68" ;;
+           "EV6.9A (21264/EV69A)")
+               UNAME_MACHINE="alphaev69" ;;
+           "EV7 (21364)")
+               UNAME_MACHINE="alphaev7" ;;
+           "EV7.9 (21364A)")
+               UNAME_MACHINE="alphaev79" ;;
+       esac
+       # A Vn.n version is a released version.
+       # A Tn.n version is a released field test version.
+       # A Xn.n version is an unreleased experimental baselevel.
+       # 1.2 uses "1.2" for uname -r.
+       echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[VTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
+       exit 0 ;;
+    Alpha*:OpenVMS:*:*)
+       echo alpha-hp-vms
+       exit 0 ;;
+    Alpha\ *:Windows_NT*:*)
+       # How do we know it's Interix rather than the generic POSIX subsystem?
+       # Should we change UNAME_MACHINE based on the output of uname instead
+       # of the specific Alpha model?
+       echo alpha-pc-interix
+       exit 0 ;;
+    21064:Windows_NT:50:3)
+       echo alpha-dec-winnt3.5
+       exit 0 ;;
+    Amiga*:UNIX_System_V:4.0:*)
+       echo m68k-unknown-sysv4
+       exit 0;;
+    *:[Aa]miga[Oo][Ss]:*:*)
+       echo ${UNAME_MACHINE}-unknown-amigaos
+       exit 0 ;;
+    *:[Mm]orph[Oo][Ss]:*:*)
+       echo ${UNAME_MACHINE}-unknown-morphos
+       exit 0 ;;
+    *:OS/390:*:*)
+       echo i370-ibm-openedition
+       exit 0 ;;
+    arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
+       echo arm-acorn-riscix${UNAME_RELEASE}
+       exit 0;;
+    SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)
+       echo hppa1.1-hitachi-hiuxmpp
+       exit 0;;
+    Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*)
+       # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE.
+       if test "`(/bin/universe) 2>/dev/null`" = att ; then
+               echo pyramid-pyramid-sysv3
+       else
+               echo pyramid-pyramid-bsd
+       fi
+       exit 0 ;;
+    NILE*:*:*:dcosx)
+       echo pyramid-pyramid-svr4
+       exit 0 ;;
+    DRS?6000:unix:4.0:6*)
+       echo sparc-icl-nx6
+       exit 0 ;;
+    DRS?6000:UNIX_SV:4.2*:7*)
+       case `/usr/bin/uname -p` in
+           sparc) echo sparc-icl-nx7 && exit 0 ;;
+       esac ;;
+    sun4H:SunOS:5.*:*)
+       echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+       exit 0 ;;
+    sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)
+       echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+       exit 0 ;;
+    i86pc:SunOS:5.*:*)
+       echo i386-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+       exit 0 ;;
+    sun4*:SunOS:6*:*)
+       # According to config.sub, this is the proper way to canonicalize
+       # SunOS6.  Hard to guess exactly what SunOS6 will be like, but
+       # it's likely to be more like Solaris than SunOS4.
+       echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+       exit 0 ;;
+    sun4*:SunOS:*:*)
+       case "`/usr/bin/arch -k`" in
+           Series*|S4*)
+               UNAME_RELEASE=`uname -v`
+               ;;
+       esac
+       # Japanese Language versions have a version number like `4.1.3-JL'.
+       echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'`
+       exit 0 ;;
+    sun3*:SunOS:*:*)
+       echo m68k-sun-sunos${UNAME_RELEASE}
+       exit 0 ;;
+    sun*:*:4.2BSD:*)
+       UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
+       test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3
+       case "`/bin/arch`" in
+           sun3)
+               echo m68k-sun-sunos${UNAME_RELEASE}
+               ;;
+           sun4)
+               echo sparc-sun-sunos${UNAME_RELEASE}
+               ;;
+       esac
+       exit 0 ;;
+    aushp:SunOS:*:*)
+       echo sparc-auspex-sunos${UNAME_RELEASE}
+       exit 0 ;;
+    # The situation for MiNT is a little confusing.  The machine name
+    # can be virtually everything (everything which is not
+    # "atarist" or "atariste" at least should have a processor
+    # > m68000).  The system name ranges from "MiNT" over "FreeMiNT"
+    # to the lowercase version "mint" (or "freemint").  Finally
+    # the system name "TOS" denotes a system which is actually not
+    # MiNT.  But MiNT is downward compatible to TOS, so this should
+    # be no problem.
+    atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)
+        echo m68k-atari-mint${UNAME_RELEASE}
+       exit 0 ;;
+    atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)
+       echo m68k-atari-mint${UNAME_RELEASE}
+        exit 0 ;;
+    *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)
+        echo m68k-atari-mint${UNAME_RELEASE}
+       exit 0 ;;
+    milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)
+        echo m68k-milan-mint${UNAME_RELEASE}
+        exit 0 ;;
+    hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)
+        echo m68k-hades-mint${UNAME_RELEASE}
+        exit 0 ;;
+    *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
+        echo m68k-unknown-mint${UNAME_RELEASE}
+        exit 0 ;;
+    powerpc:machten:*:*)
+       echo powerpc-apple-machten${UNAME_RELEASE}
+       exit 0 ;;
+    RISC*:Mach:*:*)
+       echo mips-dec-mach_bsd4.3
+       exit 0 ;;
+    RISC*:ULTRIX:*:*)
+       echo mips-dec-ultrix${UNAME_RELEASE}
+       exit 0 ;;
+    VAX*:ULTRIX*:*:*)
+       echo vax-dec-ultrix${UNAME_RELEASE}
+       exit 0 ;;
+    2020:CLIX:*:* | 2430:CLIX:*:*)
+       echo clipper-intergraph-clix${UNAME_RELEASE}
+       exit 0 ;;
+    mips:*:*:UMIPS | mips:*:*:RISCos)
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+#ifdef __cplusplus
+#include <stdio.h>  /* for printf() prototype */
+       int main (int argc, char *argv[]) {
+#else
+       int main (argc, argv) int argc; char *argv[]; {
+#endif
+       #if defined (host_mips) && defined (MIPSEB)
+       #if defined (SYSTYPE_SYSV)
+         printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0);
+       #endif
+       #if defined (SYSTYPE_SVR4)
+         printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0);
+       #endif
+       #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD)
+         printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0);
+       #endif
+       #endif
+         exit (-1);
+       }
+EOF
+       $CC_FOR_BUILD -o $dummy $dummy.c \
+         && $dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \
+         && exit 0
+       echo mips-mips-riscos${UNAME_RELEASE}
+       exit 0 ;;
+    Motorola:PowerMAX_OS:*:*)
+       echo powerpc-motorola-powermax
+       exit 0 ;;
+    Motorola:*:4.3:PL8-*)
+       echo powerpc-harris-powermax
+       exit 0 ;;
+    Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*)
+       echo powerpc-harris-powermax
+       exit 0 ;;
+    Night_Hawk:Power_UNIX:*:*)
+       echo powerpc-harris-powerunix
+       exit 0 ;;
+    m88k:CX/UX:7*:*)
+       echo m88k-harris-cxux7
+       exit 0 ;;
+    m88k:*:4*:R4*)
+       echo m88k-motorola-sysv4
+       exit 0 ;;
+    m88k:*:3*:R3*)
+       echo m88k-motorola-sysv3
+       exit 0 ;;
+    AViiON:dgux:*:*)
+        # DG/UX returns AViiON for all architectures
+        UNAME_PROCESSOR=`/usr/bin/uname -p`
+       if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]
+       then
+           if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \
+              [ ${TARGET_BINARY_INTERFACE}x = x ]
+           then
+               echo m88k-dg-dgux${UNAME_RELEASE}
+           else
+               echo m88k-dg-dguxbcs${UNAME_RELEASE}
+           fi
+       else
+           echo i586-dg-dgux${UNAME_RELEASE}
+       fi
+       exit 0 ;;
+    M88*:DolphinOS:*:*)        # DolphinOS (SVR3)
+       echo m88k-dolphin-sysv3
+       exit 0 ;;
+    M88*:*:R3*:*)
+       # Delta 88k system running SVR3
+       echo m88k-motorola-sysv3
+       exit 0 ;;
+    XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3)
+       echo m88k-tektronix-sysv3
+       exit 0 ;;
+    Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD)
+       echo m68k-tektronix-bsd
+       exit 0 ;;
+    *:IRIX*:*:*)
+       echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'`
+       exit 0 ;;
+    ????????:AIX?:[12].1:2)   # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.
+       echo romp-ibm-aix      # uname -m gives an 8 hex-code CPU id
+       exit 0 ;;              # Note that: echo "'`uname -s`'" gives 'AIX '
+    i*86:AIX:*:*)
+       echo i386-ibm-aix
+       exit 0 ;;
+    ia64:AIX:*:*)
+       if [ -x /usr/bin/oslevel ] ; then
+               IBM_REV=`/usr/bin/oslevel`
+       else
+               IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+       fi
+       echo ${UNAME_MACHINE}-ibm-aix${IBM_REV}
+       exit 0 ;;
+    *:AIX:2:3)
+       if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then
+               eval $set_cc_for_build
+               sed 's/^                //' << EOF >$dummy.c
+               #include <sys/systemcfg.h>
+
+               main()
+                       {
+                       if (!__power_pc())
+                               exit(1);
+                       puts("powerpc-ibm-aix3.2.5");
+                       exit(0);
+                       }
+EOF
+               $CC_FOR_BUILD -o $dummy $dummy.c && $dummy && exit 0
+               echo rs6000-ibm-aix3.2.5
+       elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then
+               echo rs6000-ibm-aix3.2.4
+       else
+               echo rs6000-ibm-aix3.2
+       fi
+       exit 0 ;;
+    *:AIX:*:[45])
+       IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
+       if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
+               IBM_ARCH=rs6000
+       else
+               IBM_ARCH=powerpc
+       fi
+       if [ -x /usr/bin/oslevel ] ; then
+               IBM_REV=`/usr/bin/oslevel`
+       else
+               IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+       fi
+       echo ${IBM_ARCH}-ibm-aix${IBM_REV}
+       exit 0 ;;
+    *:AIX:*:*)
+       echo rs6000-ibm-aix
+       exit 0 ;;
+    ibmrt:4.4BSD:*|romp-ibm:BSD:*)
+       echo romp-ibm-bsd4.4
+       exit 0 ;;
+    ibmrt:*BSD:*|romp-ibm:BSD:*)            # covers RT/PC BSD and
+       echo romp-ibm-bsd${UNAME_RELEASE}   # 4.3 with uname added to
+       exit 0 ;;                           # report: romp-ibm BSD 4.3
+    *:BOSX:*:*)
+       echo rs6000-bull-bosx
+       exit 0 ;;
+    DPX/2?00:B.O.S.:*:*)
+       echo m68k-bull-sysv3
+       exit 0 ;;
+    9000/[34]??:4.3bsd:1.*:*)
+       echo m68k-hp-bsd
+       exit 0 ;;
+    hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*)
+       echo m68k-hp-bsd4.4
+       exit 0 ;;
+    9000/[34678]??:HP-UX:*:*)
+       HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
+       case "${UNAME_MACHINE}" in
+           9000/31? )            HP_ARCH=m68000 ;;
+           9000/[34]?? )         HP_ARCH=m68k ;;
+           9000/[678][0-9][0-9])
+               if [ -x /usr/bin/getconf ]; then
+                   sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
+                    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
+                    case "${sc_cpu_version}" in
+                      523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
+                      528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1
+                      532)                      # CPU_PA_RISC2_0
+                        case "${sc_kernel_bits}" in
+                          32) HP_ARCH="hppa2.0n" ;;
+                          64) HP_ARCH="hppa2.0w" ;;
+                         '') HP_ARCH="hppa2.0" ;;   # HP-UX 10.20
+                        esac ;;
+                    esac
+               fi
+               if [ "${HP_ARCH}" = "" ]; then
+                   eval $set_cc_for_build
+                   sed 's/^              //' << EOF >$dummy.c
+
+              #define _HPUX_SOURCE
+              #include <stdlib.h>
+              #include <unistd.h>
+
+              int main ()
+              {
+              #if defined(_SC_KERNEL_BITS)
+                  long bits = sysconf(_SC_KERNEL_BITS);
+              #endif
+                  long cpu  = sysconf (_SC_CPU_VERSION);
+
+                  switch (cpu)
+               {
+               case CPU_PA_RISC1_0: puts ("hppa1.0"); break;
+               case CPU_PA_RISC1_1: puts ("hppa1.1"); break;
+               case CPU_PA_RISC2_0:
+              #if defined(_SC_KERNEL_BITS)
+                   switch (bits)
+                       {
+                       case 64: puts ("hppa2.0w"); break;
+                       case 32: puts ("hppa2.0n"); break;
+                       default: puts ("hppa2.0"); break;
+                       } break;
+              #else  /* !defined(_SC_KERNEL_BITS) */
+                   puts ("hppa2.0"); break;
+              #endif
+               default: puts ("hppa1.0"); break;
+               }
+                  exit (0);
+              }
+EOF
+                   (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
+                   test -z "$HP_ARCH" && HP_ARCH=hppa
+               fi ;;
+       esac
+       if [ ${HP_ARCH} = "hppa2.0w" ]
+       then
+           # avoid double evaluation of $set_cc_for_build
+           test -n "$CC_FOR_BUILD" || eval $set_cc_for_build
+           if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E -) | grep __LP64__ >/dev/null
+           then
+               HP_ARCH="hppa2.0w"
+           else
+               HP_ARCH="hppa64"
+           fi
+       fi
+       echo ${HP_ARCH}-hp-hpux${HPUX_REV}
+       exit 0 ;;
+    ia64:HP-UX:*:*)
+       HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
+       echo ia64-hp-hpux${HPUX_REV}
+       exit 0 ;;
+    3050*:HI-UX:*:*)
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+       #include <unistd.h>
+       int
+       main ()
+       {
+         long cpu = sysconf (_SC_CPU_VERSION);
+         /* The order matters, because CPU_IS_HP_MC68K erroneously returns
+            true for CPU_PA_RISC1_0.  CPU_IS_PA_RISC returns correct
+            results, however.  */
+         if (CPU_IS_PA_RISC (cpu))
+           {
+             switch (cpu)
+               {
+                 case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break;
+                 case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break;
+                 case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break;
+                 default: puts ("hppa-hitachi-hiuxwe2"); break;
+               }
+           }
+         else if (CPU_IS_HP_MC68K (cpu))
+           puts ("m68k-hitachi-hiuxwe2");
+         else puts ("unknown-hitachi-hiuxwe2");
+         exit (0);
+       }
+EOF
+       $CC_FOR_BUILD -o $dummy $dummy.c && $dummy && exit 0
+       echo unknown-hitachi-hiuxwe2
+       exit 0 ;;
+    9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )
+       echo hppa1.1-hp-bsd
+       exit 0 ;;
+    9000/8??:4.3bsd:*:*)
+       echo hppa1.0-hp-bsd
+       exit 0 ;;
+    *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*)
+       echo hppa1.0-hp-mpeix
+       exit 0 ;;
+    hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* )
+       echo hppa1.1-hp-osf
+       exit 0 ;;
+    hp8??:OSF1:*:*)
+       echo hppa1.0-hp-osf
+       exit 0 ;;
+    i*86:OSF1:*:*)
+       if [ -x /usr/sbin/sysversion ] ; then
+           echo ${UNAME_MACHINE}-unknown-osf1mk
+       else
+           echo ${UNAME_MACHINE}-unknown-osf1
+       fi
+       exit 0 ;;
+    parisc*:Lites*:*:*)
+       echo hppa1.1-hp-lites
+       exit 0 ;;
+    C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)
+       echo c1-convex-bsd
+        exit 0 ;;
+    C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*)
+       if getsysinfo -f scalar_acc
+       then echo c32-convex-bsd
+       else echo c2-convex-bsd
+       fi
+        exit 0 ;;
+    C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*)
+       echo c34-convex-bsd
+        exit 0 ;;
+    C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*)
+       echo c38-convex-bsd
+        exit 0 ;;
+    C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)
+       echo c4-convex-bsd
+        exit 0 ;;
+    CRAY*Y-MP:*:*:*)
+       echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+       exit 0 ;;
+    CRAY*[A-Z]90:*:*:*)
+       echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \
+       | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \
+             -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \
+             -e 's/\.[^.]*$/.X/'
+       exit 0 ;;
+    CRAY*TS:*:*:*)
+       echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+       exit 0 ;;
+    CRAY*T3E:*:*:*)
+       echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+       exit 0 ;;
+    CRAY*SV1:*:*:*)
+       echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+       exit 0 ;;
+    *:UNICOS/mp:*:*)
+       echo nv1-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' 
+       exit 0 ;;
+    F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
+       FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
+        FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
+        FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
+        echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+        exit 0 ;;
+    i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
+       echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
+       exit 0 ;;
+    sparc*:BSD/OS:*:*)
+       echo sparc-unknown-bsdi${UNAME_RELEASE}
+       exit 0 ;;
+    *:BSD/OS:*:*)
+       echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
+       exit 0 ;;
+    *:FreeBSD:*:*|*:GNU/FreeBSD:*:*)
+       # Determine whether the default compiler uses glibc.
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+       #include <features.h>
+       #if __GLIBC__ >= 2
+       LIBC=gnu
+       #else
+       LIBC=
+       #endif
+EOF
+       eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^LIBC=`
+       # GNU/FreeBSD systems have a "k" prefix to indicate we are using
+       # FreeBSD's kernel, but not the complete OS.
+       case ${LIBC} in gnu) kernel_only='k' ;; esac
+       echo ${UNAME_MACHINE}-unknown-${kernel_only}freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`${LIBC:+-$LIBC}
+       exit 0 ;;
+    i*:CYGWIN*:*)
+       echo ${UNAME_MACHINE}-pc-cygwin
+       exit 0 ;;
+    i*:MINGW*:*)
+       echo ${UNAME_MACHINE}-pc-mingw32
+       exit 0 ;;
+    i*:PW*:*)
+       echo ${UNAME_MACHINE}-pc-pw32
+       exit 0 ;;
+    x86:Interix*:[34]*)
+       echo i586-pc-interix${UNAME_RELEASE}|sed -e 's/\..*//'
+       exit 0 ;;
+    [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)
+       echo i${UNAME_MACHINE}-pc-mks
+       exit 0 ;;
+    i*:Windows_NT*:* | Pentium*:Windows_NT*:*)
+       # How do we know it's Interix rather than the generic POSIX subsystem?
+       # It also conflicts with pre-2.0 versions of AT&T UWIN. Should we
+       # UNAME_MACHINE based on the output of uname instead of i386?
+       echo i586-pc-interix
+       exit 0 ;;
+    i*:UWIN*:*)
+       echo ${UNAME_MACHINE}-pc-uwin
+       exit 0 ;;
+    p*:CYGWIN*:*)
+       echo powerpcle-unknown-cygwin
+       exit 0 ;;
+    prep*:SunOS:5.*:*)
+       echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+       exit 0 ;;
+    *:GNU:*:*)
+       echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
+       exit 0 ;;
+    i*86:Minix:*:*)
+       echo ${UNAME_MACHINE}-pc-minix
+       exit 0 ;;
+    arm*:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    cris:Linux:*:*)
+       echo cris-axis-linux
+       exit 0 ;;
+    ia64:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    m68*:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    mips:Linux:*:*)
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+       #undef CPU
+       #undef mips
+       #undef mipsel
+       #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
+       CPU=mipsel
+       #else
+       #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
+       CPU=mips
+       #else
+       CPU=
+       #endif
+       #endif
+EOF
+       eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^CPU=`
+       test x"${CPU}" != x && echo "${CPU}-${VENDOR}-linux" && exit 0
+       ;;
+    mips64:Linux:*:*)
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+       #undef CPU
+       #undef mips64
+       #undef mips64el
+       #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
+       CPU=mips64el
+       #else
+       #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
+       CPU=mips64
+       #else
+       CPU=
+       #endif
+       #endif
+EOF
+       eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^CPU=`
+       test x"${CPU}" != x && echo "${CPU}-${VENDOR}-linux" && exit 0
+       ;;
+    ppc:Linux:*:*)
+       echo powerpc-${VENDOR}-linux
+       exit 0 ;;
+    ppc64:Linux:*:*)
+       echo powerpc64-${VENDOR}-linux
+       exit 0 ;;
+    alpha:Linux:*:*)
+       case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
+         EV5)   UNAME_MACHINE=alphaev5 ;;
+         EV56)  UNAME_MACHINE=alphaev56 ;;
+         PCA56) UNAME_MACHINE=alphapca56 ;;
+         PCA57) UNAME_MACHINE=alphapca56 ;;
+         EV6)   UNAME_MACHINE=alphaev6 ;;
+         EV67)  UNAME_MACHINE=alphaev67 ;;
+         EV68*) UNAME_MACHINE=alphaev68 ;;
+        esac
+       objdump --private-headers /bin/sh | grep ld.so.1 >/dev/null
+       if test "$?" = 0 ; then LIBC="-libc1" ; else LIBC="" ; fi
+       echo ${UNAME_MACHINE}-${VENDOR}-linux${LIBC}
+       exit 0 ;;
+    parisc:Linux:*:* | hppa:Linux:*:*)
+       # Look for CPU level
+       case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
+         PA7*) echo hppa1.1-${VENDOR}-linux ;;
+         PA8*) echo hppa2.0-${VENDOR}-linux ;;
+         *)    echo hppa-${VENDOR}-linux ;;
+       esac
+       exit 0 ;;
+    parisc64:Linux:*:* | hppa64:Linux:*:*)
+       echo hppa64-${VENDOR}-linux
+       exit 0 ;;
+    s390:Linux:*:* | s390x:Linux:*:*)
+       echo ${UNAME_MACHINE}-ibm-linux
+       exit 0 ;;
+    sh64*:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    sh*:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    sparc:Linux:*:* | sparc64:Linux:*:*)
+       echo ${UNAME_MACHINE}-${VENDOR}-linux
+       exit 0 ;;
+    x86_64:Linux:*:*)
+       echo x86_64-${VENDOR}-linux
+       exit 0 ;;
+    i*86:Linux:*:*)
+       # The BFD linker knows what the default object file format is, so
+       # first see if it will tell us. cd to the root directory to prevent
+       # problems with other programs or directories called `ld' in the path.
+       # Set LC_ALL=C to ensure ld outputs messages in English.
+       ld_supported_targets=`cd /; LC_ALL=C ld --help 2>&1 \
+                        | sed -ne '/supported targets:/!d
+                                   s/[         ][      ]*/ /g
+                                   s/.*supported targets: *//
+                                   s/ .*//
+                                   p'`
+        case "$ld_supported_targets" in
+         elf32-i386)
+               TENTATIVE="${UNAME_MACHINE}-${VENDOR}-linux"
+               ;;
+         a.out-i386-linux)
+               echo "${UNAME_MACHINE}-${VENDOR}-linuxaout"
+               exit 0 ;;
+         coff-i386)
+               echo "${UNAME_MACHINE}-${VENDOR}-linuxcoff"
+               exit 0 ;;
+         "")
+               # Either a pre-BFD a.out linker (linuxoldld) or
+               # one that does not give us useful --help.
+               echo "${UNAME_MACHINE}-${VENDOR}-linuxoldld"
+               exit 0 ;;
+       esac
+       # Determine whether the default compiler is a.out or elf
+       eval $set_cc_for_build
+       sed 's/^        //' << EOF >$dummy.c
+       #include <features.h>
+       #ifdef __ELF__
+       # ifdef __GLIBC__
+       #  if __GLIBC__ >= 2
+       LIBC=gnu
+       #  else
+       LIBC=gnulibc1
+       #  endif
+       # else
+       LIBC=gnulibc1
+       # endif
+       #else
+       #ifdef __INTEL_COMPILER
+       LIBC=gnu
+       #else
+       LIBC=gnuaout
+       #endif
+       #endif
+EOF
+       eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^LIBC=`
+       test x"${LIBC}" != x && echo "${UNAME_MACHINE}-${VENDOR}-linux-${LIBC}" | sed 's/linux-gnu/linux/' && exit 0
+       test x"${TENTATIVE}" != x && echo "${TENTATIVE}" && exit 0
+       ;;
+    i*86:DYNIX/ptx:4*:*)
+       # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
+       # earlier versions are messed up and put the nodename in both
+       # sysname and nodename.
+       echo i386-sequent-sysv4
+       exit 0 ;;
+    i*86:UNIX_SV:4.2MP:2.*)
+        # Unixware is an offshoot of SVR4, but it has its own version
+        # number series starting with 2...
+        # I am not positive that other SVR4 systems won't match this,
+       # I just have to hope.  -- rms.
+        # Use sysv4.2uw... so that sysv4* matches it.
+       echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
+       exit 0 ;;
+    i*86:OS/2:*:*)
+       # If we were able to find `uname', then EMX Unix compatibility
+       # is probably installed.
+       echo ${UNAME_MACHINE}-pc-os2-emx
+       exit 0 ;;
+    i*86:XTS-300:*:STOP)
+       echo ${UNAME_MACHINE}-unknown-stop
+       exit 0 ;;
+    i*86:atheos:*:*)
+       echo ${UNAME_MACHINE}-unknown-atheos
+       exit 0 ;;
+    i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*)
+       echo i386-unknown-lynxos${UNAME_RELEASE}
+       exit 0 ;;
+    i*86:*DOS:*:*)
+       echo ${UNAME_MACHINE}-pc-msdosdjgpp
+       exit 0 ;;
+    i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
+       UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
+       if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
+               echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}
+       else
+               echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}
+       fi
+       exit 0 ;;
+    i*86:*:5:[78]*)
+       case `/bin/uname -X | grep "^Machine"` in
+           *486*)           UNAME_MACHINE=i486 ;;
+           *Pentium)        UNAME_MACHINE=i586 ;;
+           *Pent*|*Celeron) UNAME_MACHINE=i686 ;;
+       esac
+       echo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION}
+       exit 0 ;;
+    i*86:*:3.2:*)
+       if test -f /usr/options/cb.name; then
+               UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
+               echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
+       elif /bin/uname -X 2>/dev/null >/dev/null ; then
+               UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`
+               (/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486
+               (/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \
+                       && UNAME_MACHINE=i586
+               (/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \
+                       && UNAME_MACHINE=i686
+               (/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \
+                       && UNAME_MACHINE=i686
+               echo ${UNAME_MACHINE}-pc-sco$UNAME_REL
+       else
+               echo ${UNAME_MACHINE}-pc-sysv32
+       fi
+       exit 0 ;;
+    pc:*:*:*)
+       # Left here for compatibility:
+        # uname -m prints for DJGPP always 'pc', but it prints nothing about
+        # the processor, so we play safe by assuming i386.
+       echo i386-pc-msdosdjgpp
+        exit 0 ;;
+    Intel:Mach:3*:*)
+       echo i386-pc-mach3
+       exit 0 ;;
+    paragon:*:*:*)
+       echo i860-intel-osf1
+       exit 0 ;;
+    i860:*:4.*:*) # i860-SVR4
+       if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then
+         echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4
+       else # Add other i860-SVR4 vendors below as they are discovered.
+         echo i860-unknown-sysv${UNAME_RELEASE}  # Unknown i860-SVR4
+       fi
+       exit 0 ;;
+    mini*:CTIX:SYS*5:*)
+       # "miniframe"
+       echo m68010-convergent-sysv
+       exit 0 ;;
+    mc68k:UNIX:SYSTEM5:3.51m)
+       echo m68k-convergent-sysv
+       exit 0 ;;
+    M680?0:D-NIX:5.3:*)
+       echo m68k-diab-dnix
+       exit 0 ;;
+    M68*:*:R3V[567]*:*)
+       test -r /sysV68 && echo 'm68k-motorola-sysv' && exit 0 ;;
+    3[34]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0)
+       OS_REL=''
+       test -r /etc/.relid \
+       && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
+       /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+         && echo i486-ncr-sysv4.3${OS_REL} && exit 0
+       /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
+         && echo i586-ncr-sysv4.3${OS_REL} && exit 0 ;;
+    3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
+        /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+          && echo i486-ncr-sysv4 && exit 0 ;;
+    m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)
+       echo m68k-unknown-lynxos${UNAME_RELEASE}
+       exit 0 ;;
+    mc68030:UNIX_System_V:4.*:*)
+       echo m68k-atari-sysv4
+       exit 0 ;;
+    TSUNAMI:LynxOS:2.*:*)
+       echo sparc-unknown-lynxos${UNAME_RELEASE}
+       exit 0 ;;
+    rs6000:LynxOS:2.*:*)
+       echo rs6000-unknown-lynxos${UNAME_RELEASE}
+       exit 0 ;;
+    PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.0*:*)
+       echo powerpc-unknown-lynxos${UNAME_RELEASE}
+       exit 0 ;;
+    SM[BE]S:UNIX_SV:*:*)
+       echo mips-dde-sysv${UNAME_RELEASE}
+       exit 0 ;;
+    RM*:ReliantUNIX-*:*:*)
+       echo mips-sni-sysv4
+       exit 0 ;;
+    RM*:SINIX-*:*:*)
+       echo mips-sni-sysv4
+       exit 0 ;;
+    *:SINIX-*:*:*)
+       if uname -p 2>/dev/null >/dev/null ; then
+               UNAME_MACHINE=`(uname -p) 2>/dev/null`
+               echo ${UNAME_MACHINE}-sni-sysv4
+       else
+               echo ns32k-sni-sysv
+       fi
+       exit 0 ;;
+    PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort
+                      # says <Richard.M.Bartel@ccMail.Census.GOV>
+        echo i586-unisys-sysv4
+        exit 0 ;;
+    *:UNIX_System_V:4*:FTX*)
+       # From Gerald Hewes <hewes@openmarket.com>.
+       # How about differentiating between stratus architectures? -djm
+       echo hppa1.1-stratus-sysv4
+       exit 0 ;;
+    *:*:*:FTX*)
+       # From seanf@swdc.stratus.com.
+       echo i860-stratus-sysv4
+       exit 0 ;;
+    *:VOS:*:*)
+       # From Paul.Green@stratus.com.
+       echo hppa1.1-stratus-vos
+       exit 0 ;;
+    mc68*:A/UX:*:*)
+       echo m68k-apple-aux${UNAME_RELEASE}
+       exit 0 ;;
+    news*:NEWS-OS:6*:*)
+       echo mips-sony-newsos6
+       exit 0 ;;
+    R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)
+       if [ -d /usr/nec ]; then
+               echo mips-nec-sysv${UNAME_RELEASE}
+       else
+               echo mips-unknown-sysv${UNAME_RELEASE}
+       fi
+        exit 0 ;;
+    BeBox:BeOS:*:*)    # BeOS running on hardware made by Be, PPC only.
+       echo powerpc-be-beos
+       exit 0 ;;
+    BeMac:BeOS:*:*)    # BeOS running on Mac or Mac clone, PPC only.
+       echo powerpc-apple-beos
+       exit 0 ;;
+    BePC:BeOS:*:*)     # BeOS running on Intel PC compatible.
+       echo i586-pc-beos
+       exit 0 ;;
+    SX-4:SUPER-UX:*:*)
+       echo sx4-nec-superux${UNAME_RELEASE}
+       exit 0 ;;
+    SX-5:SUPER-UX:*:*)
+       echo sx5-nec-superux${UNAME_RELEASE}
+       exit 0 ;;
+    SX-6:SUPER-UX:*:*)
+       echo sx6-nec-superux${UNAME_RELEASE}
+       exit 0 ;;
+    Power*:Rhapsody:*:*)
+       echo powerpc-apple-rhapsody${UNAME_RELEASE}
+       exit 0 ;;
+    *:Rhapsody:*:*)
+       echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}
+       exit 0 ;;
+    *:Darwin:*:*)
+       case `uname -p` in
+           *86) UNAME_PROCESSOR=i686 ;;
+           powerpc) UNAME_PROCESSOR=powerpc ;;
+       esac
+       echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
+       exit 0 ;;
+    *:procnto*:*:* | *:QNX:[0123456789]*:*)
+       UNAME_PROCESSOR=`uname -p`
+       if test "$UNAME_PROCESSOR" = "x86"; then
+               UNAME_PROCESSOR=i386
+               UNAME_MACHINE=pc
+       fi
+       echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}
+       exit 0 ;;
+    *:QNX:*:4*)
+       echo i386-pc-qnx
+       exit 0 ;;
+    NSR-[DGKLNPTVW]:NONSTOP_KERNEL:*:*)
+       echo nsr-tandem-nsk${UNAME_RELEASE}
+       exit 0 ;;
+    *:NonStop-UX:*:*)
+       echo mips-compaq-nonstopux
+       exit 0 ;;
+    BS2000:POSIX*:*:*)
+       echo bs2000-siemens-sysv
+       exit 0 ;;
+    DS/*:UNIX_System_V:*:*)
+       echo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE}
+       exit 0 ;;
+    *:Plan9:*:*)
+       # "uname -m" is not consistent, so use $cputype instead. 386
+       # is converted to i386 for consistency with other x86
+       # operating systems.
+       if test "$cputype" = "386"; then
+           UNAME_MACHINE=i386
+       else
+           UNAME_MACHINE="$cputype"
+       fi
+       echo ${UNAME_MACHINE}-unknown-plan9
+       exit 0 ;;
+    *:TOPS-10:*:*)
+       echo pdp10-unknown-tops10
+       exit 0 ;;
+    *:TENEX:*:*)
+       echo pdp10-unknown-tenex
+       exit 0 ;;
+    KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*)
+       echo pdp10-dec-tops20
+       exit 0 ;;
+    XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*)
+       echo pdp10-xkl-tops20
+       exit 0 ;;
+    *:TOPS-20:*:*)
+       echo pdp10-unknown-tops20
+       exit 0 ;;
+    *:ITS:*:*)
+       echo pdp10-unknown-its
+       exit 0 ;;
+    SEI:*:*:SEIUX)
+        echo mips-sei-seiux${UNAME_RELEASE}
+       exit 0 ;;
+esac
+
+#echo '(No uname command or uname output not recognized.)' 1>&2
+#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2
+
+eval $set_cc_for_build
+cat >$dummy.c <<EOF
+#ifdef _SEQUENT_
+# include <sys/types.h>
+# include <sys/utsname.h>
+#endif
+main ()
+{
+#if defined (sony)
+#if defined (MIPSEB)
+  /* BFD wants "bsd" instead of "newsos".  Perhaps BFD should be changed,
+     I don't know....  */
+  printf ("mips-sony-bsd\n"); exit (0);
+#else
+#include <sys/param.h>
+  printf ("m68k-sony-newsos%s\n",
+#ifdef NEWSOS4
+          "4"
+#else
+         ""
+#endif
+         ); exit (0);
+#endif
+#endif
+
+#if defined (__arm) && defined (__acorn) && defined (__unix)
+  printf ("arm-acorn-riscix"); exit (0);
+#endif
+
+#if defined (hp300) && !defined (hpux)
+  printf ("m68k-hp-bsd\n"); exit (0);
+#endif
+
+#if defined (NeXT)
+#if !defined (__ARCHITECTURE__)
+#define __ARCHITECTURE__ "m68k"
+#endif
+  int version;
+  version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`;
+  if (version < 4)
+    printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version);
+  else
+    printf ("%s-next-openstep%d\n", __ARCHITECTURE__, version);
+  exit (0);
+#endif
+
+#if defined (MULTIMAX) || defined (n16)
+#if defined (UMAXV)
+  printf ("ns32k-encore-sysv\n"); exit (0);
+#else
+#if defined (CMU)
+  printf ("ns32k-encore-mach\n"); exit (0);
+#else
+  printf ("ns32k-encore-bsd\n"); exit (0);
+#endif
+#endif
+#endif
+
+#if defined (__386BSD__)
+  printf ("i386-pc-bsd\n"); exit (0);
+#endif
+
+#if defined (sequent)
+#if defined (i386)
+  printf ("i386-sequent-dynix\n"); exit (0);
+#endif
+#if defined (ns32000)
+  printf ("ns32k-sequent-dynix\n"); exit (0);
+#endif
+#endif
+
+#if defined (_SEQUENT_)
+    struct utsname un;
+
+    uname(&un);
+
+    if (strncmp(un.version, "V2", 2) == 0) {
+       printf ("i386-sequent-ptx2\n"); exit (0);
+    }
+    if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */
+       printf ("i386-sequent-ptx1\n"); exit (0);
+    }
+    printf ("i386-sequent-ptx\n"); exit (0);
+
+#endif
+
+#if defined (vax)
+# if !defined (ultrix)
+#  include <sys/param.h>
+#  if defined (BSD)
+#   if BSD == 43
+      printf ("vax-dec-bsd4.3\n"); exit (0);
+#   else
+#    if BSD == 199006
+      printf ("vax-dec-bsd4.3reno\n"); exit (0);
+#    else
+      printf ("vax-dec-bsd\n"); exit (0);
+#    endif
+#   endif
+#  else
+    printf ("vax-dec-bsd\n"); exit (0);
+#  endif
+# else
+    printf ("vax-dec-ultrix\n"); exit (0);
+# endif
+#endif
+
+#if defined (alliant) && defined (i860)
+  printf ("i860-alliant-bsd\n"); exit (0);
+#endif
+
+  exit (1);
+}
+EOF
+
+$CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null && $dummy && exit 0
+
+# Apollos put the system type in the environment.
+
+test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit 0; }
+
+# Convex versions that predate uname can use getsysinfo(1)
+
+if [ -x /usr/convex/getsysinfo ]
+then
+    case `getsysinfo -f cpu_type` in
+    c1*)
+       echo c1-convex-bsd
+       exit 0 ;;
+    c2*)
+       if getsysinfo -f scalar_acc
+       then echo c32-convex-bsd
+       else echo c2-convex-bsd
+       fi
+       exit 0 ;;
+    c34*)
+       echo c34-convex-bsd
+       exit 0 ;;
+    c38*)
+       echo c38-convex-bsd
+       exit 0 ;;
+    c4*)
+       echo c4-convex-bsd
+       exit 0 ;;
+    esac
+fi
+
+cat >&2 <<EOF
+$0: unable to guess system type
+
+This script, last modified $timestamp, has failed to recognize
+the operating system you are using. It is advised that you
+download the most up to date version of the config scripts from
+
+    ftp://ftp.gnu.org/pub/gnu/config/
+
+If the version you run ($0) is already up to date, please
+send the following data and any information you think might be
+pertinent to <config-patches@gnu.org> in order to provide the needed
+information to handle your system.
+
+config.guess timestamp = $timestamp
+
+uname -m = `(uname -m) 2>/dev/null || echo unknown`
+uname -r = `(uname -r) 2>/dev/null || echo unknown`
+uname -s = `(uname -s) 2>/dev/null || echo unknown`
+uname -v = `(uname -v) 2>/dev/null || echo unknown`
+
+/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null`
+/bin/uname -X     = `(/bin/uname -X) 2>/dev/null`
+
+hostinfo               = `(hostinfo) 2>/dev/null`
+/bin/universe          = `(/bin/universe) 2>/dev/null`
+/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null`
+/bin/arch              = `(/bin/arch) 2>/dev/null`
+/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null`
+/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null`
+
+UNAME_MACHINE = ${UNAME_MACHINE}
+UNAME_RELEASE = ${UNAME_RELEASE}
+UNAME_SYSTEM  = ${UNAME_SYSTEM}
+UNAME_VERSION = ${UNAME_VERSION}
+EOF
+
+exit 1
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "timestamp='"
+# time-stamp-format: "%:y-%02m-%02d"
+# time-stamp-end: "'"
+# End:
diff --git a/libsysio/config.sub b/libsysio/config.sub
new file mode 100755 (executable)
index 0000000..9952c14
--- /dev/null
@@ -0,0 +1,1501 @@
+#! /bin/sh
+# Configuration validation subroutine script.
+#   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
+#   2000, 2001, 2002, 2003 Free Software Foundation, Inc.
+
+timestamp='2003-07-04'
+
+# This file is (in principle) common to ALL GNU software.
+# The presence of a machine in this file suggests that SOME GNU software
+# can handle that machine.  It does not imply ALL GNU software can.
+#
+# This file 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 of the License, 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., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Please send patches to <config-patches@gnu.org>.  Submit a context
+# diff and a properly formatted ChangeLog entry.
+#
+# Configuration subroutine to validate and canonicalize a configuration type.
+# Supply the specified configuration type as an argument.
+# If it is invalid, we print an error message on stderr and exit with code 1.
+# Otherwise, we print the canonical config type on stdout and succeed.
+
+# This file is supposed to be the same for all GNU packages
+# and recognize all the CPU types, system types and aliases
+# that are meaningful with *any* GNU software.
+# Each package is responsible for reporting which valid configurations
+# it does not support.  The user should be able to distinguish
+# a failure to support a valid configuration from a meaningless
+# configuration.
+
+# The goal of this file is to map all the various variations of a given
+# machine specification into a single specification in the form:
+#      CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM
+# or in some cases, the newer four-part form:
+#      CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM
+# It is wrong to echo any other type of specification.
+
+me=`echo "$0" | sed -e 's,.*/,,'`
+
+usage="\
+Usage: $0 [OPTION] CPU-MFR-OPSYS
+       $0 [OPTION] ALIAS
+
+Canonicalize a configuration name.
+
+Operation modes:
+  -h, --help         print this help, then exit
+  -t, --time-stamp   print date of last modification, then exit
+  -v, --version      print version number, then exit
+
+Report bugs and patches to <config-patches@gnu.org>."
+
+version="\
+GNU config.sub ($timestamp)
+
+Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
+Free Software Foundation, Inc.
+
+This is free software; see the source for copying conditions.  There is NO
+warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
+
+help="
+Try \`$me --help' for more information."
+
+# Parse command line
+while test $# -gt 0 ; do
+  case $1 in
+    --time-stamp | --time* | -t )
+       echo "$timestamp" ; exit 0 ;;
+    --version | -v )
+       echo "$version" ; exit 0 ;;
+    --help | --h* | -h )
+       echo "$usage"; exit 0 ;;
+    -- )     # Stop option processing
+       shift; break ;;
+    - )        # Use stdin as input.
+       break ;;
+    -* )
+       echo "$me: invalid option $1$help"
+       exit 1 ;;
+
+    *local*)
+       # First pass through any local machine types.
+       echo $1
+       exit 0;;
+
+    * )
+       break ;;
+  esac
+done
+
+case $# in
+ 0) echo "$me: missing argument$help" >&2
+    exit 1;;
+ 1) ;;
+ *) echo "$me: too many arguments$help" >&2
+    exit 1;;
+esac
+
+# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any).
+# Here we must recognize all the valid KERNEL-OS combinations.
+maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
+case $maybe_os in
+  nto-qnx* | linux-gnu* | kfreebsd*-gnu* | netbsd*-gnu* | storm-chaos* | os2-emx* | rtmk-nova*)
+    os=-$maybe_os
+    basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
+    ;;
+  *)
+    basic_machine=`echo $1 | sed 's/-[^-]*$//'`
+    if [ $basic_machine != $1 ]
+    then os=`echo $1 | sed 's/.*-/-/'`
+    else os=; fi
+    ;;
+esac
+
+### Let's recognize common machines as not being operating systems so
+### that things like config.sub decstation-3100 work.  We also
+### recognize some manufacturers as not being operating systems, so we
+### can provide default operating systems below.
+case $os in
+       -sun*os*)
+               # Prevent following clause from handling this invalid input.
+               ;;
+       -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \
+       -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \
+       -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \
+       -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\
+       -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \
+       -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \
+       -apple | -axis)
+               os=
+               basic_machine=$1
+               ;;
+       -sim | -cisco | -oki | -wec | -winbond)
+               os=
+               basic_machine=$1
+               ;;
+       -scout)
+               ;;
+       -wrs)
+               os=-vxworks
+               basic_machine=$1
+               ;;
+       -chorusos*)
+               os=-chorusos
+               basic_machine=$1
+               ;;
+       -chorusrdb)
+               os=-chorusrdb
+               basic_machine=$1
+               ;;
+       -hiux*)
+               os=-hiuxwe2
+               ;;
+       -sco5)
+               os=-sco3.2v5
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -sco4)
+               os=-sco3.2v4
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -sco3.2.[4-9]*)
+               os=`echo $os | sed -e 's/sco3.2./sco3.2v/'`
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -sco3.2v[4-9]*)
+               # Don't forget version if it is 3.2v4 or newer.
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -sco*)
+               os=-sco3.2v2
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -udk*)
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -isc)
+               os=-isc2.2
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -clix*)
+               basic_machine=clipper-intergraph
+               ;;
+       -isc*)
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+               ;;
+       -lynx*)
+               os=-lynxos
+               ;;
+       -ptx*)
+               basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'`
+               ;;
+       -windowsnt*)
+               os=`echo $os | sed -e 's/windowsnt/winnt/'`
+               ;;
+       -psos*)
+               os=-psos
+               ;;
+       -mint | -mint[0-9]*)
+               basic_machine=m68k-atari
+               os=-mint
+               ;;
+esac
+
+# Decode aliases for certain CPU-COMPANY combinations.
+case $basic_machine in
+       # Recognize the basic CPU types without company name.
+       # Some are omitted here because they have special meanings below.
+       1750a | 580 \
+       | a29k \
+       | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
+       | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
+       | arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr \
+       | c4x | clipper \
+       | d10v | d30v | dlx | dsp16xx \
+       | fr30 | frv \
+       | h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
+       | i370 | i860 | i960 | ia64 \
+       | ip2k \
+       | m32r | m68000 | m68k | m88k | mcore \
+       | mips | mipsbe | mipseb | mipsel | mipsle \
+       | mips16 \
+       | mips64 | mips64el \
+       | mips64vr | mips64vrel \
+       | mips64orion | mips64orionel \
+       | mips64vr4100 | mips64vr4100el \
+       | mips64vr4300 | mips64vr4300el \
+       | mips64vr5000 | mips64vr5000el \
+       | mipsisa32 | mipsisa32el \
+       | mipsisa32r2 | mipsisa32r2el \
+       | mipsisa64 | mipsisa64el \
+       | mipsisa64sb1 | mipsisa64sb1el \
+       | mipsisa64sr71k | mipsisa64sr71kel \
+       | mipstx39 | mipstx39el \
+       | mn10200 | mn10300 \
+       | msp430 \
+       | ns16k | ns32k \
+       | openrisc | or32 \
+       | pdp10 | pdp11 | pj | pjl \
+       | powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \
+       | pyramid \
+       | sh | sh[1234] | sh[23]e | sh[34]eb | shbe | shle | sh[1234]le | sh3ele \
+       | sh64 | sh64le \
+       | sparc | sparc64 | sparc86x | sparclet | sparclite | sparcv9 | sparcv9b \
+       | strongarm \
+       | tahoe | thumb | tic4x | tic80 | tron \
+       | v850 | v850e \
+       | we32k \
+       | x86 | xscale | xstormy16 | xtensa \
+       | z8k)
+               basic_machine=$basic_machine-unknown
+               ;;
+       m6811 | m68hc11 | m6812 | m68hc12)
+               # Motorola 68HC11/12.
+               basic_machine=$basic_machine-unknown
+               os=-none
+               ;;
+       m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k)
+               ;;
+
+       # We use `pc' rather than `unknown'
+       # because (1) that's what they normally are, and
+       # (2) the word "unknown" tends to confuse beginning users.
+       i*86 | x86_64)
+         basic_machine=$basic_machine-pc
+         ;;
+       # Object if more than one company name word.
+       *-*-*)
+               echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+               exit 1
+               ;;
+       # Recognize the basic CPU types with company name.
+       580-* \
+       | a29k-* \
+       | alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
+       | alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
+       | alphapca5[67]-* | alpha64pca5[67]-* | arc-* \
+       | arm-*  | armbe-* | armle-* | armeb-* | armv*-* \
+       | avr-* \
+       | bs2000-* \
+       | c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \
+       | clipper-* | cydra-* \
+       | d10v-* | d30v-* | dlx-* \
+       | elxsi-* \
+       | f30[01]-* | f700-* | fr30-* | frv-* | fx80-* \
+       | h8300-* | h8500-* \
+       | hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
+       | i*86-* | i860-* | i960-* | ia64-* \
+       | ip2k-* \
+       | m32r-* \
+       | m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \
+       | m88110-* | m88k-* | mcore-* \
+       | mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \
+       | mips16-* \
+       | mips64-* | mips64el-* \
+       | mips64vr-* | mips64vrel-* \
+       | mips64orion-* | mips64orionel-* \
+       | mips64vr4100-* | mips64vr4100el-* \
+       | mips64vr4300-* | mips64vr4300el-* \
+       | mips64vr5000-* | mips64vr5000el-* \
+       | mipsisa32-* | mipsisa32el-* \
+       | mipsisa32r2-* | mipsisa32r2el-* \
+       | mipsisa64-* | mipsisa64el-* \
+       | mipsisa64sb1-* | mipsisa64sb1el-* \
+       | mipsisa64sr71k-* | mipsisa64sr71kel-* \
+       | mipstx39-* | mipstx39el-* \
+       | msp430-* \
+       | none-* | np1-* | nv1-* | ns16k-* | ns32k-* \
+       | orion-* \
+       | pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
+       | powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \
+       | pyramid-* \
+       | romp-* | rs6000-* \
+       | sh-* | sh[1234]-* | sh[23]e-* | sh[34]eb-* | shbe-* \
+       | shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \
+       | sparc-* | sparc64-* | sparc86x-* | sparclet-* | sparclite-* \
+       | sparcv9-* | sparcv9b-* | strongarm-* | sv1-* | sx?-* \
+       | tahoe-* | thumb-* \
+       | tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \
+       | tron-* \
+       | v850-* | v850e-* | vax-* \
+       | we32k-* \
+       | x86-* | x86_64-* | xps100-* | xscale-* | xstormy16-* \
+       | xtensa-* \
+       | ymp-* \
+       | z8k-*)
+               ;;
+       # Recognize the various machine names and aliases which stand
+       # for a CPU type and a company and sometimes even an OS.
+       386bsd)
+               basic_machine=i386-unknown
+               os=-bsd
+               ;;
+       3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc)
+               basic_machine=m68000-att
+               ;;
+       3b*)
+               basic_machine=we32k-att
+               ;;
+       a29khif)
+               basic_machine=a29k-amd
+               os=-udi
+               ;;
+       adobe68k)
+               basic_machine=m68010-adobe
+               os=-scout
+               ;;
+       alliant | fx80)
+               basic_machine=fx80-alliant
+               ;;
+       altos | altos3068)
+               basic_machine=m68k-altos
+               ;;
+       am29k)
+               basic_machine=a29k-none
+               os=-bsd
+               ;;
+       amd64)
+               basic_machine=x86_64-pc
+               ;;
+       amdahl)
+               basic_machine=580-amdahl
+               os=-sysv
+               ;;
+       amiga | amiga-*)
+               basic_machine=m68k-unknown
+               ;;
+       amigaos | amigados)
+               basic_machine=m68k-unknown
+               os=-amigaos
+               ;;
+       amigaunix | amix)
+               basic_machine=m68k-unknown
+               os=-sysv4
+               ;;
+       apollo68)
+               basic_machine=m68k-apollo
+               os=-sysv
+               ;;
+       apollo68bsd)
+               basic_machine=m68k-apollo
+               os=-bsd
+               ;;
+       aux)
+               basic_machine=m68k-apple
+               os=-aux
+               ;;
+       balance)
+               basic_machine=ns32k-sequent
+               os=-dynix
+               ;;
+       c90)
+               basic_machine=c90-cray
+               os=-unicos
+               ;;
+       convex-c1)
+               basic_machine=c1-convex
+               os=-bsd
+               ;;
+       convex-c2)
+               basic_machine=c2-convex
+               os=-bsd
+               ;;
+       convex-c32)
+               basic_machine=c32-convex
+               os=-bsd
+               ;;
+       convex-c34)
+               basic_machine=c34-convex
+               os=-bsd
+               ;;
+       convex-c38)
+               basic_machine=c38-convex
+               os=-bsd
+               ;;
+       cray | j90)
+               basic_machine=j90-cray
+               os=-unicos
+               ;;
+       crds | unos)
+               basic_machine=m68k-crds
+               ;;
+       cris | cris-* | etrax*)
+               basic_machine=cris-axis
+               ;;
+       da30 | da30-*)
+               basic_machine=m68k-da30
+               ;;
+       decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn)
+               basic_machine=mips-dec
+               ;;
+       decsystem10* | dec10*)
+               basic_machine=pdp10-dec
+               os=-tops10
+               ;;
+       decsystem20* | dec20*)
+               basic_machine=pdp10-dec
+               os=-tops20
+               ;;
+       delta | 3300 | motorola-3300 | motorola-delta \
+             | 3300-motorola | delta-motorola)
+               basic_machine=m68k-motorola
+               ;;
+       delta88)
+               basic_machine=m88k-motorola
+               os=-sysv3
+               ;;
+       dpx20 | dpx20-*)
+               basic_machine=rs6000-bull
+               os=-bosx
+               ;;
+       dpx2* | dpx2*-bull)
+               basic_machine=m68k-bull
+               os=-sysv3
+               ;;
+       ebmon29k)
+               basic_machine=a29k-amd
+               os=-ebmon
+               ;;
+       elxsi)
+               basic_machine=elxsi-elxsi
+               os=-bsd
+               ;;
+       encore | umax | mmax)
+               basic_machine=ns32k-encore
+               ;;
+       es1800 | OSE68k | ose68k | ose | OSE)
+               basic_machine=m68k-ericsson
+               os=-ose
+               ;;
+       fx2800)
+               basic_machine=i860-alliant
+               ;;
+       genix)
+               basic_machine=ns32k-ns
+               ;;
+       gmicro)
+               basic_machine=tron-gmicro
+               os=-sysv
+               ;;
+       go32)
+               basic_machine=i386-pc
+               os=-go32
+               ;;
+       h3050r* | hiux*)
+               basic_machine=hppa1.1-hitachi
+               os=-hiuxwe2
+               ;;
+       h8300hms)
+               basic_machine=h8300-hitachi
+               os=-hms
+               ;;
+       h8300xray)
+               basic_machine=h8300-hitachi
+               os=-xray
+               ;;
+       h8500hms)
+               basic_machine=h8500-hitachi
+               os=-hms
+               ;;
+       harris)
+               basic_machine=m88k-harris
+               os=-sysv3
+               ;;
+       hp300-*)
+               basic_machine=m68k-hp
+               ;;
+       hp300bsd)
+               basic_machine=m68k-hp
+               os=-bsd
+               ;;
+       hp300hpux)
+               basic_machine=m68k-hp
+               os=-hpux
+               ;;
+       hp3k9[0-9][0-9] | hp9[0-9][0-9])
+               basic_machine=hppa1.0-hp
+               ;;
+       hp9k2[0-9][0-9] | hp9k31[0-9])
+               basic_machine=m68000-hp
+               ;;
+       hp9k3[2-9][0-9])
+               basic_machine=m68k-hp
+               ;;
+       hp9k6[0-9][0-9] | hp6[0-9][0-9])
+               basic_machine=hppa1.0-hp
+               ;;
+       hp9k7[0-79][0-9] | hp7[0-79][0-9])
+               basic_machine=hppa1.1-hp
+               ;;
+       hp9k78[0-9] | hp78[0-9])
+               # FIXME: really hppa2.0-hp
+               basic_machine=hppa1.1-hp
+               ;;
+       hp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893)
+               # FIXME: really hppa2.0-hp
+               basic_machine=hppa1.1-hp
+               ;;
+       hp9k8[0-9][13679] | hp8[0-9][13679])
+               basic_machine=hppa1.1-hp
+               ;;
+       hp9k8[0-9][0-9] | hp8[0-9][0-9])
+               basic_machine=hppa1.0-hp
+               ;;
+       hppa-next)
+               os=-nextstep3
+               ;;
+       hppaosf)
+               basic_machine=hppa1.1-hp
+               os=-osf
+               ;;
+       hppro)
+               basic_machine=hppa1.1-hp
+               os=-proelf
+               ;;
+       i370-ibm* | ibm*)
+               basic_machine=i370-ibm
+               ;;
+# I'm not sure what "Sysv32" means.  Should this be sysv3.2?
+       i*86v32)
+               basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+               os=-sysv32
+               ;;
+       i*86v4*)
+               basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+               os=-sysv4
+               ;;
+       i*86v)
+               basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+               os=-sysv
+               ;;
+       i*86sol2)
+               basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+               os=-solaris2
+               ;;
+       i386mach)
+               basic_machine=i386-mach
+               os=-mach
+               ;;
+       i386-vsta | vsta)
+               basic_machine=i386-unknown
+               os=-vsta
+               ;;
+       iris | iris4d)
+               basic_machine=mips-sgi
+               case $os in
+                   -irix*)
+                       ;;
+                   *)
+                       os=-irix4
+                       ;;
+               esac
+               ;;
+       isi68 | isi)
+               basic_machine=m68k-isi
+               os=-sysv
+               ;;
+       m88k-omron*)
+               basic_machine=m88k-omron
+               ;;
+       magnum | m3230)
+               basic_machine=mips-mips
+               os=-sysv
+               ;;
+       merlin)
+               basic_machine=ns32k-utek
+               os=-sysv
+               ;;
+       mingw32)
+               basic_machine=i386-pc
+               os=-mingw32
+               ;;
+       miniframe)
+               basic_machine=m68000-convergent
+               ;;
+       *mint | -mint[0-9]* | *MiNT | *MiNT[0-9]*)
+               basic_machine=m68k-atari
+               os=-mint
+               ;;
+       mips3*-*)
+               basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`
+               ;;
+       mips3*)
+               basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown
+               ;;
+       mmix*)
+               basic_machine=mmix-knuth
+               os=-mmixware
+               ;;
+       monitor)
+               basic_machine=m68k-rom68k
+               os=-coff
+               ;;
+       morphos)
+               basic_machine=powerpc-unknown
+               os=-morphos
+               ;;
+       msdos)
+               basic_machine=i386-pc
+               os=-msdos
+               ;;
+       mvs)
+               basic_machine=i370-ibm
+               os=-mvs
+               ;;
+       ncr3000)
+               basic_machine=i486-ncr
+               os=-sysv4
+               ;;
+       netbsd386)
+               basic_machine=i386-unknown
+               os=-netbsd
+               ;;
+       netwinder)
+               basic_machine=armv4l-rebel
+               os=-linux
+               ;;
+       news | news700 | news800 | news900)
+               basic_machine=m68k-sony
+               os=-newsos
+               ;;
+       news1000)
+               basic_machine=m68030-sony
+               os=-newsos
+               ;;
+       news-3600 | risc-news)
+               basic_machine=mips-sony
+               os=-newsos
+               ;;
+       necv70)
+               basic_machine=v70-nec
+               os=-sysv
+               ;;
+       next | m*-next )
+               basic_machine=m68k-next
+               case $os in
+                   -nextstep* )
+                       ;;
+                   -ns2*)
+                     os=-nextstep2
+                       ;;
+                   *)
+                     os=-nextstep3
+                       ;;
+               esac
+               ;;
+       nh3000)
+               basic_machine=m68k-harris
+               os=-cxux
+               ;;
+       nh[45]000)
+               basic_machine=m88k-harris
+               os=-cxux
+               ;;
+       nindy960)
+               basic_machine=i960-intel
+               os=-nindy
+               ;;
+       mon960)
+               basic_machine=i960-intel
+               os=-mon960
+               ;;
+       nonstopux)
+               basic_machine=mips-compaq
+               os=-nonstopux
+               ;;
+       np1)
+               basic_machine=np1-gould
+               ;;
+       nv1)
+               basic_machine=nv1-cray
+               os=-unicosmp
+               ;;
+       nsr-tandem)
+               basic_machine=nsr-tandem
+               ;;
+       op50n-* | op60c-*)
+               basic_machine=hppa1.1-oki
+               os=-proelf
+               ;;
+       or32 | or32-*)
+               basic_machine=or32-unknown
+               os=-coff
+               ;;
+       OSE68000 | ose68000)
+               basic_machine=m68000-ericsson
+               os=-ose
+               ;;
+       os68k)
+               basic_machine=m68k-none
+               os=-os68k
+               ;;
+       pa-hitachi)
+               basic_machine=hppa1.1-hitachi
+               os=-hiuxwe2
+               ;;
+       paragon)
+               basic_machine=i860-intel
+               os=-osf
+               ;;
+       pbd)
+               basic_machine=sparc-tti
+               ;;
+       pbb)
+               basic_machine=m68k-tti
+               ;;
+       pc532 | pc532-*)
+               basic_machine=ns32k-pc532
+               ;;
+       pentium | p5 | k5 | k6 | nexgen | viac3)
+               basic_machine=i586-pc
+               ;;
+       pentiumpro | p6 | 6x86 | athlon | athlon_*)
+               basic_machine=i686-pc
+               ;;
+       pentiumii | pentium2 | pentiumiii | pentium3)
+               basic_machine=i686-pc
+               ;;
+       pentium4)
+               basic_machine=i786-pc
+               ;;
+       pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)
+               basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       pentiumpro-* | p6-* | 6x86-* | athlon-*)
+               basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)
+               basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       pentium4-*)
+               basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       pn)
+               basic_machine=pn-gould
+               ;;
+       power)  basic_machine=power-ibm
+               ;;
+       ppc)    basic_machine=powerpc-unknown
+               ;;
+       ppc-*)  basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       ppcle | powerpclittle | ppc-le | powerpc-little)
+               basic_machine=powerpcle-unknown
+               ;;
+       ppcle-* | powerpclittle-*)
+               basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       ppc64)  basic_machine=powerpc64-unknown
+               ;;
+       ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       ppc64le | powerpc64little | ppc64-le | powerpc64-little)
+               basic_machine=powerpc64le-unknown
+               ;;
+       ppc64le-* | powerpc64little-*)
+               basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`
+               ;;
+       ps2)
+               basic_machine=i386-ibm
+               ;;
+       pw32)
+               basic_machine=i586-unknown
+               os=-pw32
+               ;;
+       rom68k)
+               basic_machine=m68k-rom68k
+               os=-coff
+               ;;
+       rm[46]00)
+               basic_machine=mips-siemens
+               ;;
+       rtpc | rtpc-*)
+               basic_machine=romp-ibm
+               ;;
+       s390 | s390-*)
+               basic_machine=s390-ibm
+               ;;
+       s390x | s390x-*)
+               basic_machine=s390x-ibm
+               ;;
+       sa29200)
+               basic_machine=a29k-amd
+               os=-udi
+               ;;
+       sb1)
+               basic_machine=mipsisa64sb1-unknown
+               ;;
+       sb1el)
+               basic_machine=mipsisa64sb1el-unknown
+               ;;
+       sei)
+               basic_machine=mips-sei
+               os=-seiux
+               ;;
+       sequent)
+               basic_machine=i386-sequent
+               ;;
+       sh)
+               basic_machine=sh-hitachi
+               os=-hms
+               ;;
+       sh64)
+               basic_machine=sh64-unknown
+               ;;
+       sparclite-wrs | simso-wrs)
+               basic_machine=sparclite-wrs
+               os=-vxworks
+               ;;
+       sps7)
+               basic_machine=m68k-bull
+               os=-sysv2
+               ;;
+       spur)
+               basic_machine=spur-unknown
+               ;;
+       st2000)
+               basic_machine=m68k-tandem
+               ;;
+       stratus)
+               basic_machine=i860-stratus
+               os=-sysv4
+               ;;
+       sun2)
+               basic_machine=m68000-sun
+               ;;
+       sun2os3)
+               basic_machine=m68000-sun
+               os=-sunos3
+               ;;
+       sun2os4)
+               basic_machine=m68000-sun
+               os=-sunos4
+               ;;
+       sun3os3)
+               basic_machine=m68k-sun
+               os=-sunos3
+               ;;
+       sun3os4)
+               basic_machine=m68k-sun
+               os=-sunos4
+               ;;
+       sun4os3)
+               basic_machine=sparc-sun
+               os=-sunos3
+               ;;
+       sun4os4)
+               basic_machine=sparc-sun
+               os=-sunos4
+               ;;
+       sun4sol2)
+               basic_machine=sparc-sun
+               os=-solaris2
+               ;;
+       sun3 | sun3-*)
+               basic_machine=m68k-sun
+               ;;
+       sun4)
+               basic_machine=sparc-sun
+               ;;
+       sun386 | sun386i | roadrunner)
+               basic_machine=i386-sun
+               ;;
+       sv1)
+               basic_machine=sv1-cray
+               os=-unicos
+               ;;
+       symmetry)
+               basic_machine=i386-sequent
+               os=-dynix
+               ;;
+       t3e)
+               basic_machine=alphaev5-cray
+               os=-unicos
+               ;;
+       t90)
+               basic_machine=t90-cray
+               os=-unicos
+               ;;
+       tic54x | c54x*)
+               basic_machine=tic54x-unknown
+               os=-coff
+               ;;
+       tic55x | c55x*)
+               basic_machine=tic55x-unknown
+               os=-coff
+               ;;
+       tic6x | c6x*)
+               basic_machine=tic6x-unknown
+               os=-coff
+               ;;
+       tx39)
+               basic_machine=mipstx39-unknown
+               ;;
+       tx39el)
+               basic_machine=mipstx39el-unknown
+               ;;
+       toad1)
+               basic_machine=pdp10-xkl
+               os=-tops20
+               ;;
+       tower | tower-32)
+               basic_machine=m68k-ncr
+               ;;
+       udi29k)
+               basic_machine=a29k-amd
+               os=-udi
+               ;;
+       ultra3)
+               basic_machine=a29k-nyu
+               os=-sym1
+               ;;
+       v810 | necv810)
+               basic_machine=v810-nec
+               os=-none
+               ;;
+       vaxv)
+               basic_machine=vax-dec
+               os=-sysv
+               ;;
+       vms)
+               basic_machine=vax-dec
+               os=-vms
+               ;;
+       vpp*|vx|vx-*)
+               basic_machine=f301-fujitsu
+               ;;
+       vxworks960)
+               basic_machine=i960-wrs
+               os=-vxworks
+               ;;
+       vxworks68)
+               basic_machine=m68k-wrs
+               os=-vxworks
+               ;;
+       vxworks29k)
+               basic_machine=a29k-wrs
+               os=-vxworks
+               ;;
+       w65*)
+               basic_machine=w65-wdc
+               os=-none
+               ;;
+       w89k-*)
+               basic_machine=hppa1.1-winbond
+               os=-proelf
+               ;;
+       xps | xps100)
+               basic_machine=xps100-honeywell
+               ;;
+       ymp)
+               basic_machine=ymp-cray
+               os=-unicos
+               ;;
+       z8k-*-coff)
+               basic_machine=z8k-unknown
+               os=-sim
+               ;;
+       none)
+               basic_machine=none-none
+               os=-none
+               ;;
+
+# Here we handle the default manufacturer of certain CPU types.  It is in
+# some cases the only manufacturer, in others, it is the most popular.
+       w89k)
+               basic_machine=hppa1.1-winbond
+               ;;
+       op50n)
+               basic_machine=hppa1.1-oki
+               ;;
+       op60c)
+               basic_machine=hppa1.1-oki
+               ;;
+       romp)
+               basic_machine=romp-ibm
+               ;;
+       rs6000)
+               basic_machine=rs6000-ibm
+               ;;
+       vax)
+               basic_machine=vax-dec
+               ;;
+       pdp10)
+               # there are many clones, so DEC is not a safe bet
+               basic_machine=pdp10-unknown
+               ;;
+       pdp11)
+               basic_machine=pdp11-dec
+               ;;
+       we32k)
+               basic_machine=we32k-att
+               ;;
+       sh3 | sh4 | sh[34]eb | sh[1234]le | sh[23]ele)
+               basic_machine=sh-unknown
+               ;;
+       sh64)
+               basic_machine=sh64-unknown
+               ;;
+       sparc | sparcv9 | sparcv9b)
+               basic_machine=sparc-sun
+               ;;
+       cydra)
+               basic_machine=cydra-cydrome
+               ;;
+       orion)
+               basic_machine=orion-highlevel
+               ;;
+       orion105)
+               basic_machine=clipper-highlevel
+               ;;
+       mac | mpw | mac-mpw)
+               basic_machine=m68k-apple
+               ;;
+       pmac | pmac-mpw)
+               basic_machine=powerpc-apple
+               ;;
+       *-unknown)
+               # Make sure to match an already-canonicalized machine name.
+               ;;
+       *)
+               echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+               exit 1
+               ;;
+esac
+
+# Here we canonicalize certain aliases for manufacturers.
+case $basic_machine in
+       *-digital*)
+               basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'`
+               ;;
+       *-commodore*)
+               basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'`
+               ;;
+       *)
+               ;;
+esac
+
+# Decode manufacturer-specific aliases for certain operating systems.
+
+if [ x"$os" != x"" ]
+then
+case $os in
+        # First match some system type aliases
+        # that might get confused with valid system types.
+       # -solaris* is a basic system type, with this one exception.
+       -solaris1 | -solaris1.*)
+               os=`echo $os | sed -e 's|solaris1|sunos4|'`
+               ;;
+       -solaris)
+               os=-solaris2
+               ;;
+       -svr4*)
+               os=-sysv4
+               ;;
+       -unixware*)
+               os=-sysv4.2uw
+               ;;
+       -gnu/linux*)
+               os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'`
+               ;;
+       # First accept the basic system types.
+       # The portable systems comes first.
+       # Each alternative MUST END IN A *, to match a version number.
+       # -sysv* is not here because it comes later, after sysvr4.
+       -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \
+             | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\
+             | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \
+             | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \
+             | -aos* \
+             | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \
+             | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \
+             | -hiux* | -386bsd* | -netbsd* | -openbsd* | -kfreebsd* | -freebsd* | -riscix* \
+             | -lynxos* | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \
+             | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \
+             | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \
+             | -chorusos* | -chorusrdb* \
+             | -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
+             | -mingw32* | -linux* | -uxpv* | -beos* | -mpeix* | -udk* \
+             | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
+             | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
+             | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \
+             | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
+             | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
+             | -powermax* | -dnix* | -nx6 | -nx7 | -sei*)
+       # Remember, each alternative MUST END IN *, to match a version number.
+               ;;
+       -qnx*)
+               case $basic_machine in
+                   x86-* | i*86-*)
+                       ;;
+                   *)
+                       os=-nto$os
+                       ;;
+               esac
+               ;;
+       -nto-qnx*)
+               ;;
+       -nto*)
+               os=`echo $os | sed -e 's|nto|nto-qnx|'`
+               ;;
+       -sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \
+             | -windows* | -osx | -abug | -netware* | -os9* | -beos* \
+             | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*)
+               ;;
+       -mac*)
+               os=`echo $os | sed -e 's|mac|macos|'`
+               ;;
+       -sunos5*)
+               os=`echo $os | sed -e 's|sunos5|solaris2|'`
+               ;;
+       -sunos6*)
+               os=`echo $os | sed -e 's|sunos6|solaris3|'`
+               ;;
+       -opened*)
+               os=-openedition
+               ;;
+       -wince*)
+               os=-wince
+               ;;
+       -osfrose*)
+               os=-osfrose
+               ;;
+       -osf*)
+               os=-osf
+               ;;
+       -utek*)
+               os=-bsd
+               ;;
+       -dynix*)
+               os=-bsd
+               ;;
+       -acis*)
+               os=-aos
+               ;;
+       -atheos*)
+               os=-atheos
+               ;;
+       -386bsd)
+               os=-bsd
+               ;;
+       -ctix* | -uts*)
+               os=-sysv
+               ;;
+       -nova*)
+               os=-rtmk-nova
+               ;;
+       -ns2 )
+               os=-nextstep2
+               ;;
+       -nsk*)
+               os=-nsk
+               ;;
+       # Preserve the version number of sinix5.
+       -sinix5.*)
+               os=`echo $os | sed -e 's|sinix|sysv|'`
+               ;;
+       -sinix*)
+               os=-sysv4
+               ;;
+       -triton*)
+               os=-sysv3
+               ;;
+       -oss*)
+               os=-sysv3
+               ;;
+       -svr4)
+               os=-sysv4
+               ;;
+       -svr3)
+               os=-sysv3
+               ;;
+       -sysvr4)
+               os=-sysv4
+               ;;
+       # This must come after -sysvr4.
+       -sysv*)
+               ;;
+       -ose*)
+               os=-ose
+               ;;
+       -es1800*)
+               os=-ose
+               ;;
+       -xenix)
+               os=-xenix
+               ;;
+       -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
+               os=-mint
+               ;;
+       -aros*)
+               os=-aros
+               ;;
+       -kaos*)
+               os=-kaos
+               ;;
+       -none)
+               ;;
+       *)
+               # Get rid of the `-' at the beginning of $os.
+               os=`echo $os | sed 's/[^-]*-//'`
+               echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2
+               exit 1
+               ;;
+esac
+else
+
+# Here we handle the default operating systems that come with various machines.
+# The value should be what the vendor currently ships out the door with their
+# machine or put another way, the most popular os provided with the machine.
+
+# Note that if you're going to try to match "-MANUFACTURER" here (say,
+# "-sun"), then you have to tell the case statement up towards the top
+# that MANUFACTURER isn't an operating system.  Otherwise, code above
+# will signal an error saying that MANUFACTURER isn't an operating
+# system, and we'll never get to this point.
+
+case $basic_machine in
+       *-acorn)
+               os=-riscix1.2
+               ;;
+       arm*-rebel)
+               os=-linux
+               ;;
+       arm*-semi)
+               os=-aout
+               ;;
+    c4x-* | tic4x-*)
+        os=-coff
+        ;;
+       # This must come before the *-dec entry.
+       pdp10-*)
+               os=-tops20
+               ;;
+       pdp11-*)
+               os=-none
+               ;;
+       *-dec | vax-*)
+               os=-ultrix4.2
+               ;;
+       m68*-apollo)
+               os=-domain
+               ;;
+       i386-sun)
+               os=-sunos4.0.2
+               ;;
+       m68000-sun)
+               os=-sunos3
+               # This also exists in the configure program, but was not the
+               # default.
+               # os=-sunos4
+               ;;
+       m68*-cisco)
+               os=-aout
+               ;;
+       mips*-cisco)
+               os=-elf
+               ;;
+       mips*-*)
+               os=-elf
+               ;;
+       or32-*)
+               os=-coff
+               ;;
+       *-tti)  # must be before sparc entry or we get the wrong os.
+               os=-sysv3
+               ;;
+       sparc-* | *-sun)
+               os=-sunos4.1.1
+               ;;
+       *-be)
+               os=-beos
+               ;;
+       *-ibm)
+               os=-aix
+               ;;
+       *-wec)
+               os=-proelf
+               ;;
+       *-winbond)
+               os=-proelf
+               ;;
+       *-oki)
+               os=-proelf
+               ;;
+       *-hp)
+               os=-hpux
+               ;;
+       *-hitachi)
+               os=-hiux
+               ;;
+       i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent)
+               os=-sysv
+               ;;
+       *-cbm)
+               os=-amigaos
+               ;;
+       *-dg)
+               os=-dgux
+               ;;
+       *-dolphin)
+               os=-sysv3
+               ;;
+       m68k-ccur)
+               os=-rtu
+               ;;
+       m88k-omron*)
+               os=-luna
+               ;;
+       *-next )
+               os=-nextstep
+               ;;
+       *-sequent)
+               os=-ptx
+               ;;
+       *-crds)
+               os=-unos
+               ;;
+       *-ns)
+               os=-genix
+               ;;
+       i370-*)
+               os=-mvs
+               ;;
+       *-next)
+               os=-nextstep3
+               ;;
+       *-gould)
+               os=-sysv
+               ;;
+       *-highlevel)
+               os=-bsd
+               ;;
+       *-encore)
+               os=-bsd
+               ;;
+       *-sgi)
+               os=-irix
+               ;;
+       *-siemens)
+               os=-sysv4
+               ;;
+       *-masscomp)
+               os=-rtu
+               ;;
+       f30[01]-fujitsu | f700-fujitsu)
+               os=-uxpv
+               ;;
+       *-rom68k)
+               os=-coff
+               ;;
+       *-*bug)
+               os=-coff
+               ;;
+       *-apple)
+               os=-macos
+               ;;
+       *-atari*)
+               os=-mint
+               ;;
+       *)
+               os=-none
+               ;;
+esac
+fi
+
+# Here we handle the case where we know the os, and the CPU type, but not the
+# manufacturer.  We pick the logical manufacturer.
+vendor=unknown
+case $basic_machine in
+       *-unknown)
+               case $os in
+                       -riscix*)
+                               vendor=acorn
+                               ;;
+                       -sunos*)
+                               vendor=sun
+                               ;;
+                       -aix*)
+                               vendor=ibm
+                               ;;
+                       -beos*)
+                               vendor=be
+                               ;;
+                       -hpux*)
+                               vendor=hp
+                               ;;
+                       -mpeix*)
+                               vendor=hp
+                               ;;
+                       -hiux*)
+                               vendor=hitachi
+                               ;;
+                       -unos*)
+                               vendor=crds
+                               ;;
+                       -dgux*)
+                               vendor=dg
+                               ;;
+                       -luna*)
+                               vendor=omron
+                               ;;
+                       -genix*)
+                               vendor=ns
+                               ;;
+                       -mvs* | -opened*)
+                               vendor=ibm
+                               ;;
+                       -ptx*)
+                               vendor=sequent
+                               ;;
+                       -vxsim* | -vxworks* | -windiss*)
+                               vendor=wrs
+                               ;;
+                       -aux*)
+                               vendor=apple
+                               ;;
+                       -hms*)
+                               vendor=hitachi
+                               ;;
+                       -mpw* | -macos*)
+                               vendor=apple
+                               ;;
+                       -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
+                               vendor=atari
+                               ;;
+                       -vos*)
+                               vendor=stratus
+                               ;;
+               esac
+               basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"`
+               ;;
+esac
+
+echo $basic_machine$os
+exit 0
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "timestamp='"
+# time-stamp-format: "%:y-%02m-%02d"
+# time-stamp-end: "'"
+# End:
index 9f83269..c6b6e30 100644 (file)
@@ -101,6 +101,17 @@ AC_ARG_WITH(zero-sum-memory,
   [with_zero_sum_memory=no])
 AC_SUBST(ZERO_SUM_MEMORY)
 
+AC_ARG_WITH(defer-init-cwd,
+  AC_HELP_STRING([--with-defer-init-cwd],
+    [defer initialization of current working directory]),
+  [    case "${withval}" in
+        yes) DEFER_INIT_CWD=-DDEFER_INIT_CWD=1 ;;
+        no) ;;
+        *) AC_MSG_ERROR(bad value ${withval} for --with-defer-init-cwd) ;;
+       esac],
+  [with_defer_init_cwd=no])
+AC_SUBST(DEFER_INIT_CWD)
+
 AC_ARG_WITH(cplant_yod,
    AC_HELP_STRING([--with-cplant-yod],[build cplant yod I/O driver]),
    [   case "${withval}" in    
@@ -235,61 +246,6 @@ fi
 AC_MSG_RESULT($alpha_linux_env)
 AM_CONDITIONAL(TEST_ALPHA_ARG, test x$alpha_linux_env = xyes)
 
-# check for 64 bit stat, fstat, truncate, ftruncate syscalls
-# 
-AC_MSG_CHECKING(for 64 bit stat and truncate syscalls)
-AC_TRY_COMPILE([
-#include <sys/stat.h>
-#include <syscall.h>
-extern int syscall();],
-[char path[] = "/";
-int fd = 0;
-struct stat buf;
-syscall(SYS_stat64,path,&buf);
-syscall(SYS_fstat64,fd,&buf);
-syscall(SYS_truncate64, path, buf.st_size);
-syscall(SYS_ftruncate64, fd, buf.st_size);
-],
-       sysstat64_exists=yes,
-       sysstat64_exists=no)
-AC_MSG_RESULT($sysstat64_exists)
-if test x$sysstat64_exists = xno; then
-       AC_DEFINE(USE_NATIVE_STAT)
-fi
-
-# Check for fdatasync syscall
-#
-AC_MSG_CHECKING(for fdatasync system call)
-if test x$alpha_linux_env = xyes; then
-       _syscallnum=SYS_osf_fdatasync
-else
-       _syscallnum=SYS_fdatasync
-fi
-AC_TRY_COMPILE([
-#include <syscall.h>
-extern int syscall();],
-[int fd = 0;
-syscall(SYS_fdatasync, fd);],
-       syscall_fdatasync_exists=yes,
-       syscall_fdatasync_exists=no)
-AC_MSG_RESULT($syscall_fdatasync_exists)
-if test x$syscall_fdatasync_exists = xyes; then
-       AC_DEFINE_UNQUOTED(NATIVE_FDATASYNC, $_syscallnum)
-fi
-
-# Check for SYS_utime
-#
-AC_MSG_CHECKING(for utime system call)
-AC_TRY_COMPILE([
-#include <syscall.h>
-extern int syscall();],
-[syscall(SYS_utime);],
-       syscall_utime_exists=yes,
-       syscall_utime_exists=no)
-AC_MSG_RESULT($syscall_utime_exists)
-if test x$syscall_utime_exists = xno; then
-       AC_DEFINE(USE_NATIVE_UTIME)
-fi
 # Check for __st_ino 
 #
 AC_MSG_CHECKING(for __st_ino)
diff --git a/libsysio/depcomp b/libsysio/depcomp
new file mode 100755 (executable)
index 0000000..aea3d00
--- /dev/null
@@ -0,0 +1,472 @@
+#! /bin/sh
+
+# depcomp - compile a program generating dependencies as side-effects
+# Copyright 1999, 2000 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., 59 Temple Place - Suite 330, Boston, MA
+# 02111-1307, USA.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Originally written by Alexandre Oliva <oliva@dcc.unicamp.br>.
+
+if test -z "$depmode" || test -z "$source" || test -z "$object"; then
+  echo "depcomp: Variables source, object and depmode must be set" 1>&2
+  exit 1
+fi
+# `libtool' can also be set to `yes' or `no'.
+
+if test -z "$depfile"; then
+   base=`echo "$object" | sed -e 's,^.*/,,' -e 's,\.\([^.]*\)$,.P\1,'`
+   dir=`echo "$object" | sed 's,/.*$,/,'`
+   if test "$dir" = "$object"; then
+      dir=
+   fi
+   # FIXME: should be _deps on DOS.
+   depfile="$dir.deps/$base"
+fi
+
+tmpdepfile=${tmpdepfile-`echo "$depfile" | sed 's/\.\([^.]*\)$/.T\1/'`}
+
+rm -f "$tmpdepfile"
+
+# Some modes work just like other modes, but use different flags.  We
+# parameterize here, but still list the modes in the big case below,
+# to make depend.m4 easier to write.  Note that we *cannot* use a case
+# here, because this file can only contain one case statement.
+if test "$depmode" = hp; then
+  # HP compiler uses -M and no extra arg.
+  gccflag=-M
+  depmode=gcc
+fi
+
+if test "$depmode" = dashXmstdout; then
+   # This is just like dashmstdout with a different argument.
+   dashmflag=-xM
+   depmode=dashmstdout
+fi
+
+case "$depmode" in
+gcc3)
+## gcc 3 implements dependency tracking that does exactly what
+## we want.  Yay!  Note: for some reason libtool 1.4 doesn't like
+## it if -MD -MP comes after the -MF stuff.  Hmm.
+  "$@" -MT "$object" -MD -MP -MF "$tmpdepfile"
+  stat=$?
+  if test $stat -eq 0; then :
+  else
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  mv "$tmpdepfile" "$depfile"
+  ;;
+
+gcc)
+## There are various ways to get dependency output from gcc.  Here's
+## why we pick this rather obscure method:
+## - Don't want to use -MD because we'd like the dependencies to end
+##   up in a subdir.  Having to rename by hand is ugly.
+##   (We might end up doing this anyway to support other compilers.)
+## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like
+##   -MM, not -M (despite what the docs say).
+## - Using -M directly means running the compiler twice (even worse
+##   than renaming).
+  if test -z "$gccflag"; then
+    gccflag=-MD,
+  fi
+  "$@" -Wp,"$gccflag$tmpdepfile"
+  stat=$?
+  if test $stat -eq 0; then :
+  else
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  alpha=ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz
+## The second -e expression handles DOS-style file names with drive letters.
+  sed -e 's/^[^:]*: / /' \
+      -e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile"
+## This next piece of magic avoids the `deleted header file' problem.
+## The problem is that when a header file which appears in a .P file
+## is deleted, the dependency causes make to die (because there is
+## typically no way to rebuild the header).  We avoid this by adding
+## dummy dependencies for each header file.  Too bad gcc doesn't do
+## this for us directly.
+  tr ' ' '
+' < "$tmpdepfile" |
+## Some versions of gcc put a space before the `:'.  On the theory
+## that the space means something, we add a space to the output as
+## well.
+## Some versions of the HPUX 10.20 sed can't process this invocation
+## correctly.  Breaking it into two sed invocations is a workaround.
+    sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+hp)
+  # This case exists only to let depend.m4 do its work.  It works by
+  # looking at the text of this script.  This case will never be run,
+  # since it is checked for above.
+  exit 1
+  ;;
+
+sgi)
+  if test "$libtool" = yes; then
+    "$@" "-Wp,-MDupdate,$tmpdepfile"
+  else
+    "$@" -MDupdate "$tmpdepfile"
+  fi
+  stat=$?
+  if test $stat -eq 0; then :
+  else
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+
+  if test -f "$tmpdepfile"; then  # yes, the sourcefile depend on other files
+    echo "$object : \\" > "$depfile"
+
+    # Clip off the initial element (the dependent).  Don't try to be
+    # clever and replace this with sed code, as IRIX sed won't handle
+    # lines with more than a fixed number of characters (4096 in
+    # IRIX 6.2 sed, 8192 in IRIX 6.5).  We also remove comment lines;
+    # the IRIX cc adds comments like `#:fec' to the end of the
+    # dependency line.
+    tr ' ' '
+' < "$tmpdepfile" \
+    | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' | \
+    tr '
+' ' ' >> $depfile
+    echo >> $depfile
+
+    # The second pass generates a dummy entry for each header file.
+    tr ' ' '
+' < "$tmpdepfile" \
+   | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \
+   >> $depfile
+  else
+    # The sourcefile does not contain any dependencies, so just
+    # store a dummy comment line, to avoid errors with the Makefile
+    # "include basename.Plo" scheme.
+    echo "#dummy" > "$depfile"
+  fi
+  rm -f "$tmpdepfile"
+  ;;
+
+aix)
+  # The C for AIX Compiler uses -M and outputs the dependencies
+  # in a .u file.  This file always lives in the current directory.
+  # Also, the AIX compiler puts `$object:' at the start of each line;
+  # $object doesn't have directory information.
+  stripped=`echo "$object" | sed -e 's,^.*/,,' -e 's/\(.*\)\..*$/\1/'`
+  tmpdepfile="$stripped.u"
+  outname="$stripped.o"
+  if test "$libtool" = yes; then
+    "$@" -Wc,-M
+  else
+    "$@" -M
+  fi
+
+  stat=$?
+  if test $stat -eq 0; then :
+  else
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+
+  if test -f "$tmpdepfile"; then
+    # Each line is of the form `foo.o: dependent.h'.
+    # Do two passes, one to just change these to
+    # `$object: dependent.h' and one to simply `dependent.h:'.
+    sed -e "s,^$outname:,$object :," < "$tmpdepfile" > "$depfile"
+    sed -e "s,^$outname: \(.*\)$,\1:," < "$tmpdepfile" >> "$depfile"
+  else
+    # The sourcefile does not contain any dependencies, so just
+    # store a dummy comment line, to avoid errors with the Makefile
+    # "include basename.Plo" scheme.
+    echo "#dummy" > "$depfile"
+  fi
+  rm -f "$tmpdepfile"
+  ;;
+
+icc)
+  # Intel's C compiler understands `-MD -MF file'.  However on
+  #    icc -MD -MF foo.d -c -o sub/foo.o sub/foo.c
+  # ICC 7.0 will fill foo.d with something like
+  #    foo.o: sub/foo.c
+  #    foo.o: sub/foo.h
+  # which is wrong.  We want:
+  #    sub/foo.o: sub/foo.c
+  #    sub/foo.o: sub/foo.h
+  #    sub/foo.c:
+  #    sub/foo.h:
+  # ICC 7.1 will output
+  #    foo.o: sub/foo.c sub/foo.h
+  # and will wrap long lines using \ :
+  #    foo.o: sub/foo.c ... \
+  #     sub/foo.h ... \
+  #     ...
+
+  "$@" -MD -MF "$tmpdepfile"
+  stat=$?
+  if test $stat -eq 0; then :
+  else
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  # Each line is of the form `foo.o: dependent.h',
+  # or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'.
+  # Do two passes, one to just change these to
+  # `$object: dependent.h' and one to simply `dependent.h:'.
+  sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile"
+  # Some versions of the HPUX 10.20 sed can't process this invocation
+  # correctly.  Breaking it into two sed invocations is a workaround.
+  sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" |
+    sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+tru64)
+   # The Tru64 compiler uses -MD to generate dependencies as a side
+   # effect.  `cc -MD -o foo.o ...' puts the dependencies into `foo.o.d'.
+   # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put
+   # dependencies in `foo.d' instead, so we check for that too.
+   # Subdirectories are respected.
+   dir=`echo "$object" | sed -e 's|/[^/]*$|/|'`
+   test "x$dir" = "x$object" && dir=
+   base=`echo "$object" | sed -e 's|^.*/||' -e 's/\.o$//' -e 's/\.lo$//'`
+
+   if test "$libtool" = yes; then
+      tmpdepfile1="$dir.libs/$base.lo.d"
+      tmpdepfile2="$dir.libs/$base.d"
+      "$@" -Wc,-MD
+   else
+      tmpdepfile1="$dir$base.o.d"
+      tmpdepfile2="$dir$base.d"
+      "$@" -MD
+   fi
+
+   stat=$?
+   if test $stat -eq 0; then :
+   else
+      rm -f "$tmpdepfile1" "$tmpdepfile2"
+      exit $stat
+   fi
+
+   if test -f "$tmpdepfile1"; then
+      tmpdepfile="$tmpdepfile1"
+   else
+      tmpdepfile="$tmpdepfile2"
+   fi
+   if test -f "$tmpdepfile"; then
+      sed -e "s,^.*\.[a-z]*:,$object:," < "$tmpdepfile" > "$depfile"
+      # That's a space and a tab in the [].
+      sed -e 's,^.*\.[a-z]*:[  ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile"
+   else
+      echo "#dummy" > "$depfile"
+   fi
+   rm -f "$tmpdepfile"
+   ;;
+
+#nosideeffect)
+  # This comment above is used by automake to tell side-effect
+  # dependency tracking mechanisms from slower ones.
+
+dashmstdout)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the proprocessed file to stdout, regardless of -o.
+  "$@" || exit $?
+
+  # Remove the call to Libtool.
+  if test "$libtool" = yes; then
+    while test $1 != '--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+
+  # Remove `-o $object'.
+  IFS=" "
+  for arg
+  do
+    case $arg in
+    -o)
+      shift
+      ;;
+    $object)
+      shift
+      ;;
+    *)
+      set fnord "$@" "$arg"
+      shift # fnord
+      shift # $arg
+      ;;
+    esac
+  done
+
+  test -z "$dashmflag" && dashmflag=-M
+  # Require at least two characters before searching for `:'
+  # in the target name.  This is to cope with DOS-style filenames:
+  # a dependency such as `c:/foo/bar' could be seen as target `c' otherwise.
+  "$@" $dashmflag |
+    sed 's:^[  ]*[^: ][^:][^:]*\:[    ]*:'"$object"'\: :' > "$tmpdepfile"
+  rm -f "$depfile"
+  cat < "$tmpdepfile" > "$depfile"
+  tr ' ' '
+' < "$tmpdepfile" | \
+## Some versions of the HPUX 10.20 sed can't process this invocation
+## correctly.  Breaking it into two sed invocations is a workaround.
+    sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+dashXmstdout)
+  # This case only exists to satisfy depend.m4.  It is never actually
+  # run, as this mode is specially recognized in the preamble.
+  exit 1
+  ;;
+
+makedepend)
+  "$@" || exit $?
+  # Remove any Libtool call
+  if test "$libtool" = yes; then
+    while test $1 != '--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+  # X makedepend
+  shift
+  cleared=no
+  for arg in "$@"; do
+    case $cleared in
+    no)
+      set ""; shift
+      cleared=yes ;;
+    esac
+    case "$arg" in
+    -D*|-I*)
+      set fnord "$@" "$arg"; shift ;;
+    # Strip any option that makedepend may not understand.  Remove
+    # the object too, otherwise makedepend will parse it as a source file.
+    -*|$object)
+      ;;
+    *)
+      set fnord "$@" "$arg"; shift ;;
+    esac
+  done
+  obj_suffix="`echo $object | sed 's/^.*\././'`"
+  touch "$tmpdepfile"
+  ${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@"
+  rm -f "$depfile"
+  cat < "$tmpdepfile" > "$depfile"
+  sed '1,2d' "$tmpdepfile" | tr ' ' '
+' | \
+## Some versions of the HPUX 10.20 sed can't process this invocation
+## correctly.  Breaking it into two sed invocations is a workaround.
+    sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile" "$tmpdepfile".bak
+  ;;
+
+cpp)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the proprocessed file to stdout.
+  "$@" || exit $?
+
+  # Remove the call to Libtool.
+  if test "$libtool" = yes; then
+    while test $1 != '--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+
+  # Remove `-o $object'.
+  IFS=" "
+  for arg
+  do
+    case $arg in
+    -o)
+      shift
+      ;;
+    $object)
+      shift
+      ;;
+    *)
+      set fnord "$@" "$arg"
+      shift # fnord
+      shift # $arg
+      ;;
+    esac
+  done
+
+  "$@" -E |
+    sed -n '/^# [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' |
+    sed '$ s: \\$::' > "$tmpdepfile"
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  cat < "$tmpdepfile" >> "$depfile"
+  sed < "$tmpdepfile" '/^$/d;s/^ //;s/ \\$//;s/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+msvisualcpp)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the proprocessed file to stdout, regardless of -o,
+  # because we must use -o when running libtool.
+  "$@" || exit $?
+  IFS=" "
+  for arg
+  do
+    case "$arg" in
+    "-Gm"|"/Gm"|"-Gi"|"/Gi"|"-ZI"|"/ZI")
+       set fnord "$@"
+       shift
+       shift
+       ;;
+    *)
+       set fnord "$@" "$arg"
+       shift
+       shift
+       ;;
+    esac
+  done
+  "$@" -E |
+  sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::echo "`cygpath -u \\"\1\\"`":p' | sort | uniq > "$tmpdepfile"
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  . "$tmpdepfile" | sed 's% %\\ %g' | sed -n '/^\(.*\)$/ s::   \1 \\:p' >> "$depfile"
+  echo "       " >> "$depfile"
+  . "$tmpdepfile" | sed 's% %\\ %g' | sed -n '/^\(.*\)$/ s::\1\::p' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+none)
+  exec "$@"
+  ;;
+
+*)
+  echo "Unknown depmode $depmode" 1>&2
+  exit 1
+  ;;
+esac
+
+exit 0
index aa6bf85..26ade6c 100644 (file)
 #endif
 
 #include <errno.h>
+#include <stdarg.h>
 #include <sys/syscall.h>
 #include <unistd.h>
+#include <fcntl.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "xtio.h"
 #include "sysio.h"
+#include "native.h"
 #include "inode.h"
 #include "dev.h"
 
@@ -64,8 +68,8 @@
 #define dowrite(f, b, n) write_yod(f, b, n)
 #define doread(f, b, n) read_yod(f, b, n)
 #else
-#define dowrite(f, b, n) syscall(SYS_write, f, b, n)
-#define doread(f, b, n) syscall(SYS_read, f, b, n)
+#define dowrite(f, b, n) syscall(SYSIO_SYS_write, f, b, n)
+#define doread(f, b, n) syscall(SYSIO_SYS_read, f, b, n)
 #endif
 
 /*
@@ -78,6 +82,7 @@ static int stdfd_read(struct inode *ino, struct ioctx *ioctx);
 static int stdfd_write(struct inode *ino, struct ioctx *ioctx);
 static int stdfd_iodone(struct ioctx *ioctx);
 static int stdfd_datasync(struct inode *ino);
+static int stdfd_fcntl(struct inode *ino, int cmd, va_list ap, int *rtn);
 static int stdfd_ioctl(struct inode *ino,
                       unsigned long int request,
                       va_list ap);
@@ -93,6 +98,7 @@ _sysio_stdfd_init()
        stdfd_operations.inop_read = stdfd_read;
        stdfd_operations.inop_write = stdfd_write;
        stdfd_operations.inop_iodone = stdfd_iodone;
+       stdfd_operations.inop_fcntl = stdfd_fcntl;
        stdfd_operations.inop_datasync = stdfd_datasync;
        stdfd_operations.inop_ioctl = stdfd_ioctl;
 
@@ -148,10 +154,13 @@ stdfd_read_simple(void *buf,
                  _SYSIO_OFF_T off __IS_UNUSED,
                  struct inode *ino)
 {
+       int     fd = SYSIO_MINOR_DEV(ino->i_stbuf.st_rdev);
+       int     cc;
 
-       int     fd = SYSIO_MINOR_DEV(ino->i_rdev);
-
-       return doread(fd, buf, nbytes);
+       cc = doread(fd, buf, nbytes);
+       if (cc < 0)
+               cc = -errno;
+       return cc;
 }
 
 static int
@@ -167,9 +176,13 @@ stdfd_write_simple(const void *buf,
                   _SYSIO_OFF_T off __IS_UNUSED,
                   struct inode *ino)
 {
-       int     fd = SYSIO_MINOR_DEV(ino->i_rdev);
+       int     fd = SYSIO_MINOR_DEV(ino->i_stbuf.st_rdev);
+       int     cc;
 
-       return dowrite(fd, buf, nbytes);
+       cc = dowrite(fd, buf, nbytes);
+       if (cc < 0)
+               cc = -errno;
+       return cc;
 }
 
 static int
@@ -195,6 +208,37 @@ stdfd_iodone(struct ioctx *iocp __IS_UNUSED)
 }
 
 static int
+stdfd_fcntl(struct inode *ino,
+           int cmd,
+           va_list ap,
+           int *rtn)
+{
+       int     err;
+       int     fd = SYSIO_MINOR_DEV(ino->i_stbuf.st_rdev);
+       long    arg;
+
+       err = 0;
+       switch (cmd) {
+       case F_GETFL:
+               *rtn = syscall(SYS_fcntl, fd, cmd);
+               if (*rtn == -1)
+                       err = -errno;
+               break;
+       case F_SETFL:
+               arg = va_arg(ap, long);
+               *rtn = syscall(SYS_fcntl, fd, cmd, arg);
+               if (*rtn == -1)
+                       err = -errno;
+               va_end(ap);
+               break;
+       default:
+               *rtn = -1;
+               err = -EINVAL;
+       }
+       return err;
+}
+
+static int
 stdfd_datasync(struct inode *ino __IS_UNUSED)
 {
 
index ca10b4f..4d69821 100644 (file)
@@ -85,7 +85,6 @@
  */
 struct incore_inode {
        LIST_ENTRY(incore_inode) ici_link;              /* i-nodes list link */
-       unsigned ici_revalidate                 : 1;    /* synch sys inode? */
        struct intnl_stat ici_st;                       /* attrs */
        struct file_identifier ici_fileid;              /* file ID */
        void    *ici_data;                              /* file data */
@@ -165,7 +164,7 @@ static void _sysio_incore_inop_gone(struct inode *ino);
 #define _sysio_incore_dirop_symlink \
        (int (*)(struct pnode *, const char *))_sysio_do_enosys
 #define _sysio_incore_dirop_readlink \
-       (int (*)(struct pnode *, char *, size_t))_sysio_do_einval
+       (int (*)(struct pnode *, char *, size_t))_sysio_do_enosys
 #define _sysio_incore_dirop_read \
        (int (*)(struct inode *, \
                 struct ioctx *))_sysio_do_eisdir
@@ -419,7 +418,6 @@ incore_i_alloc(struct incore_filesys *icfs, struct intnl_stat *st)
        icino = malloc(sizeof(struct incore_inode));
        if (!icino)
                return NULL;
-       icino->ici_revalidate = 0;
        icino->ici_st = *st;
        icino->ici_fileid.fid_data = &icino->ici_st.st_ino;
        icino->ici_fileid.fid_len = sizeof(icino->ici_st.st_ino);
@@ -634,8 +632,7 @@ _sysio_incore_fsswop_mount(const char *source,
        rooti =
            _sysio_i_new(fs,
                         &icino->ici_fileid,
-                        icino->ici_st.st_mode,
-                        0,
+                        &icino->ici_st,
                         1,
                         &_sysio_incore_dir_ops,
                         icino);
@@ -809,10 +806,7 @@ _sysio_incore_dirop_lookup(struct pnode *pno,
        if (*inop) {
                icino = I2IC(*inop);
                assert(icino);
-               if (icino->ici_revalidate) {
-                       (*inop)->i_mode = icino->ici_st.st_mode;
-                       icino->ici_revalidate = 0;
-               }
+               (*inop)->i_stbuf = icino->ici_st;
                return 0;
        }
 
@@ -856,8 +850,7 @@ _sysio_incore_dirop_lookup(struct pnode *pno,
        ino =
            _sysio_i_new(ino->i_fs,
                         &icino->ici_fileid,
-                        icino->ici_st.st_mode,
-                        0,
+                        &icino->ici_st
                         1,
                         ops,
                         icino);
@@ -911,7 +904,6 @@ _sysio_incore_inop_setattr(struct pnode *pno,
        if (mask & SETATTR_MODE) {
                icino->ici_st.st_mode =
                    (icino->ici_st.st_mode & S_IFMT) | (stbuf->st_mode & 07777);
-               icino->ici_revalidate = 1;
        }
        if (mask & SETATTR_MTIME)
                icino->ici_st.st_mtime = stbuf->st_mtime;
@@ -923,6 +915,7 @@ _sysio_incore_inop_setattr(struct pnode *pno,
                icino->ici_st.st_gid = stbuf->st_gid;
        icino->ici_st.st_ctime = time(NULL);
 
+       ino->i_stbuf = icino->ici_st;
 out:
        return err;
 }
@@ -1167,8 +1160,7 @@ _sysio_incore_dirop_mkdir(struct pnode *pno, mode_t mode)
        ino =
            _sysio_i_new(pno->p_parent->p_base->pb_ino->i_fs,
                         &icino->ici_fileid,
-                        stat.st_mode,
-                        0,
+                        &stat,
                         1,
                         &_sysio_incore_dir_ops,
                         icino);
@@ -1274,7 +1266,7 @@ _sysio_incore_dirop_rmdir(struct pnode *pno)
 }
 
 static int
-incore_create(struct pnode *pno, struct intnl_stat *st)
+incore_create(struct pnode *pno, struct intnl_stat *stat)
 {
        struct inode *dino, *ino;
        struct incore_inode *icino;
@@ -1283,7 +1275,7 @@ incore_create(struct pnode *pno, struct intnl_stat *st)
        dino = pno->p_parent->p_base->pb_ino;
        assert(dino);
 
-       icino = incore_i_alloc(FS2ICFS(dino->i_fs), st);
+       icino = incore_i_alloc(FS2ICFS(dino->i_fs), stat);
        if (!icino)
                return -ENOSPC;
 
@@ -1293,10 +1285,9 @@ incore_create(struct pnode *pno, struct intnl_stat *st)
        ino =
            _sysio_i_new(dino->i_fs,
                         &icino->ici_fileid,
-                        st->st_mode,
-                        st->st_rdev,
+                        stat,
                         1,
-                        S_ISREG(st->st_mode)
+                        S_ISREG(stat->st_mode)
                           ? &_sysio_incore_file_ops
                           : &_sysio_incore_dev_ops,
                         icino);
@@ -1311,7 +1302,7 @@ incore_create(struct pnode *pno, struct intnl_stat *st)
        err =
            incore_directory_insert(I2IC(dino),
                                    &pno->p_base->pb_name,
-                                   st->st_ino,
+                                   stat->st_ino,
                                    INCORE_D_TYPEOF(icino->ici_st.st_mode));
        if (err) {
                I_RELE(ino);
@@ -1372,7 +1363,7 @@ _sysio_incore_dirop_link(struct pnode *old, struct pnode *new)
        int     err;
 
        assert(!new->p_base->pb_ino);
-       assert(!S_ISDIR(old->p_base->pb_ino->i_mode));
+       assert(!S_ISDIR(old->p_base->pb_ino->i_stbuf.st_mode));
 
        /*
         * Can bump the link count?
index 446d61e..65f10dc 100644 (file)
@@ -57,6 +57,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <syscall.h>
+#include <sys/time.h>
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <sys/fcntl.h>
@@ -73,6 +74,7 @@
 
 #include "xtio.h"
 #include "sysio.h"
+#include "native.h"
 #include "fs.h"
 #include "mount.h"
 #include "inode.h"
 #include <sys/uio.h>
 #endif
 
-#if defined(SYS_getdirentries)
+#if defined(SYSIO_SYS_getdirentries)
 #define DIR_STREAMED 0
 #define DIR_CVT_64 0
-#elif defined(SYS_getdents64)
+#elif defined(SYSIO_SYS_getdents64)
 #define DIR_STREAMED 1
 #define DIR_CVT_64 0
-#elif defined(SYS_getdents)
+#elif defined(SYSIO_SYS_getdents)
 #define DIR_STREAMED 1
 #if defined(_LARGEFILE64_SOURCE)
 #define DIR_CVT_64 1
@@ -111,80 +113,17 @@ struct linux_dirent {
 #endif
 
 /*
- * Local host file system driver.
+ * Native file system information we keep per FS.
  */
-
-#if defined(ALPHA_LINUX)
-
-/* stat struct from asm/stat.h, as returned 
- * by alpha linux kernel
- */
-struct __native_stat {
-       unsigned int    st_dev;
-       unsigned int    st_ino;
-       unsigned int    st_mode;
-       unsigned int    st_nlink;
-       unsigned int    st_uid;
-       unsigned int    st_gid;
-       unsigned int    st_rdev;
-       long            st_size;
-       unsigned long   st_atime;
-       unsigned long   st_mtime;
-       unsigned long   st_ctime;
-       unsigned int    st_blksize;
-       int             st_blocks;
-       unsigned int    st_flags;
-       unsigned int    st_gen;
+struct native_filesystem {
+       time_t  nfs_atimo;                              /* attr timeout (sec) */
 };
 
-#define COPY_STAT(src, dest)                    \
-do {                                            \
-       memset((dest), 0, sizeof((*dest)));     \
-       (dest)->st_dev     = (src)->st_dev;     \
-       (dest)->st_ino     = (src)->st_ino;     \
-       (dest)->st_mode    = (src)->st_mode;    \
-       (dest)->st_nlink   = (src)->st_nlink;   \
-       (dest)->st_uid     = (src)->st_uid;     \
-       (dest)->st_gid     = (src)->st_gid;     \
-       (dest)->st_rdev    = (src)->st_rdev;    \
-       (dest)->st_size    = (src)->st_size;    \
-       (dest)->st_atime   = (src)->st_atime;   \
-       (dest)->st_mtime   = (src)->st_mtime;   \
-       (dest)->st_ctime   = (src)->st_ctime;   \
-       (dest)->st_blksize = (src)->st_blksize; \
-       (dest)->st_blocks  = (src)->st_blocks;  \
-       (dest)->st_flags   = (src)->st_flags;   \
-       (dest)->st_gen     = (src)->st_gen;     \
-} while (0);
-
-#else 
-#define __native_stat intnl_stat
-#define COPY_STAT(src, dest) *(dest) = *(src) 
-#endif
-
-#if defined(USE_NATIVE_STAT)
-#define __SYS_STAT SYS_lstat
-#define __SYS_FSTAT SYS_fstat
-#define __SYS_TRUNCATE SYS_truncate
-#define __SYS_FTRUNCATE SYS_ftruncate
-#else
-#define __SYS_STAT SYS_lstat64
-#define __SYS_FSTAT SYS_fstat64
-#define __SYS_TRUNCATE SYS_truncate64
-#define __SYS_FTRUNCATE SYS_ftruncate64
-#endif
-
-#if defined(USE_NATIVE_FDATASYNC)
-#define __SYS_FDATASYNC SYS_osf_fdatasync
-#else
-#define __SYS_FDATASYNC SYS_fdatasync
-#endif
-
-#if defined(USE_NATIVE_UTIME)
-#define __SYS_UTIME SYS_utimes
-#else
-#define __SYS_UTIME SYS_utime
-#endif
+/*
+ * Given fs, return driver private part.
+ */
+#define FS2NFS(fs) \
+       ((struct native_filesystem *)(fs)->fs_private)
 
 /*
  * Native file identifiers format.
@@ -203,17 +142,24 @@ struct native_inode_identifier {
  */
 struct native_inode {
        unsigned
-               ni_seekok               : 1;            /* can seek? */
+               ni_seekok               : 1,            /* can seek? */
+               ni_attrvalid            : 1;            /* cached attrs ok? */
        struct native_inode_identifier ni_ident;        /* unique identifier */
        struct file_identifier ni_fileid;               /* ditto */
        int     ni_fd;                                  /* host fildes */
        int     ni_oflags;                              /* flags, from open */
        unsigned ni_nopens;                             /* soft ref count */
        _SYSIO_OFF_T ni_fpos;                           /* current pos */
-       struct intnl_stat ni_stat;                      /* cached attrs */
+       time_t  ni_attrtim;                             /* attrs expire time */
 };
 
 /*
+ * Cached attributes usable?
+ */
+#define NATIVE_ATTRS_VALID(nino, t) \
+       ((nino)->ni_attrtim && (t) < (nino)->ni_attrtim)
+
+/*
  * Native IO path arguments.
  */
 struct native_io {
@@ -329,59 +275,46 @@ static struct mount *native_internal_mount = NULL;
  * stat -- by path.
  */
 static int
-native_stat(const char *path, struct native_inode *nino, struct intnl_stat *buf)
+native_stat(const char *path,
+           struct inode *ino,
+           time_t t,
+           struct intnl_stat *buf)
 {
+       struct native_inode *nino;
        int     err;
-       struct __native_stat stbuf;
-
-       err = syscall(__SYS_STAT, path, &stbuf);
-       if (err) {
-               err = -errno;
-               goto out;
-       }
-       if (!nino) {
-               COPY_STAT(&stbuf, buf);
-               goto out;
-       }
-       COPY_STAT(&stbuf, &nino->ni_stat);
-       if (&nino->ni_stat != buf)
-               (void )memcpy(buf, &nino->ni_stat, sizeof(struct intnl_stat));
-
-out:
-       return err;
-}
+       struct _sysio_native_stat stbuf;
 
-/*
- * stat -- by fildes
- */
-static int
-native_fstat(int fd, struct native_inode *nino, struct intnl_stat *buf)
-{
-       int     err;
-       struct __native_stat stbuf;
+       nino = ino ? I2NI(ino) : NULL;
 
-       err = syscall(__SYS_FSTAT, fd, &stbuf);
+       if (path)
+               err = syscall(SYSIO_SYS_stat, path, &stbuf);
+       else if (nino && nino->ni_fd >= 0)
+               err = syscall(SYSIO_SYS_fstat, nino->ni_fd, &stbuf);
+       else
+               abort();
        if (err) {
-               err = -errno;
-               goto out;
+               if (nino)
+                       nino->ni_attrtim = 0;
+               return -errno;
        }
-       if (!nino) {
-               COPY_STAT(&stbuf, buf);
-               goto out;
+       if (nino) {
+               nino->ni_attrtim = t;
+               SYSIO_COPY_STAT(&stbuf, &ino->i_stbuf);
+               if (buf)
+                       *buf = ino->i_stbuf;
+               return 0;
        }
-       COPY_STAT(&stbuf, &nino->ni_stat);
-       if (&nino->ni_stat != buf)
-               (void )memcpy(buf, &nino->ni_stat, sizeof(struct intnl_stat));
-
-out:
-       return err;
+       if (!buf)
+               return 0;
+       SYSIO_COPY_STAT(&stbuf, buf);
+       return 0;
 }
 
 /*
  * Introduce an i-node to the system.
  */
 static struct inode *
-native_i_new(struct filesys *fs, struct intnl_stat *buf)
+native_i_new(struct filesys *fs, time_t expiration, struct intnl_stat *buf)
 {
        struct native_inode *nino;
        struct inode *ino;
@@ -390,6 +323,7 @@ native_i_new(struct filesys *fs, struct intnl_stat *buf)
        if (!nino)
                return NULL;
        bzero(&nino->ni_ident, sizeof(nino->ni_ident));
+       nino->ni_seekok = 0;
        nino->ni_ident.dev = buf->st_dev;
        nino->ni_ident.ino = buf->st_ino;
 #ifdef HAVE_GENERATION
@@ -401,16 +335,11 @@ native_i_new(struct filesys *fs, struct intnl_stat *buf)
        nino->ni_oflags = 0;
        nino->ni_nopens = 0;
        nino->ni_fpos = 0;
-       (void )memcpy(&nino->ni_stat, buf, sizeof(struct intnl_stat));
+       nino->ni_attrtim = expiration;
        ino =
            _sysio_i_new(fs,
                         &nino->ni_fileid,
-#ifndef AUTOMOUNT_FILE_NAME
-                        buf->st_mode & S_IFMT,
-#else
-                        buf->st_mode,                  /* all of the bits! */
-#endif
-                        buf->st_rdev,
+                        buf,
                         0,
                         &native_i_ops,
                         nino);
@@ -431,7 +360,7 @@ _sysio_native_init()
         * zero. All permission bits to open/creat/setattr are absolute --
         * They've already had a umask applied, when appropriate.
         */
-       _sysio_umask = syscall(SYS_umask, 0);
+       _sysio_umask = syscall(SYSIO_SYS_umask, 0);
 
        return _sysio_fssw_register("native", &native_fssw_ops);
 }
@@ -440,15 +369,25 @@ _sysio_native_init()
  * Create private, internal, view of the hosts name space.
  */
 static int
-create_internal_namespace()
+create_internal_namespace(const void *data)
 {
+       char    *opts;
+       ssize_t len;
+       char    *cp;
+       struct native_filesystem *nfs;
        int     err;
        struct mount *mnt;
        struct inode *rootino;
        struct pnode_base *rootpb;
        static struct qstr noname = { NULL, 0, 0 };
        struct filesys *fs;
+       time_t  t;
        struct intnl_stat stbuf;
+       unsigned long ul;
+       static struct option_value_info v[] = {
+               { "atimo",      "30" },
+               { NULL,         NULL }
+       };
 
        if (native_internal_mount) {
                /*
@@ -458,14 +397,53 @@ create_internal_namespace()
        }
 
        /*
+        * Get mount options.
+        */
+       opts = NULL;
+       if (data && (len = strlen((char *)data))) {
+               opts = malloc(len + 1);
+               if (!opts)
+                       return -ENOMEM;
+               (void )strcpy(opts, data);
+               if (_sysio_get_args(opts, v) - opts != (ssize_t )len)
+                       return -EINVAL;
+       }
+       ul = strtoul(v[0].ovi_value, &cp, 0);
+       if (*cp != '\0' || ul >= UINT_MAX)
+               return -EINVAL;
+       if (opts) {
+               free(opts);
+               opts = NULL;
+       }
+
+       /*
         * We maintain an artificial, internal, name space in order to
         * have access to fully qualified path names in the various routines.
         * Initialize that name space now.
         */
+       fs = NULL;
        mnt = NULL;
        rootino = NULL;
        rootpb = NULL;
-       fs = _sysio_fs_new(&native_inodesys_ops, 0, NULL);
+       /*
+        * This really should be per-mount. Hmm, but that's best done
+        * as proper sub-mounts in the core and not this driver. We reconcile
+        * now, here, by putting the mount options on the file system. That
+        * means they are global and only can be passed at the initial mount.
+        *
+        * Maybe do it right some day?
+        */
+       nfs = malloc(sizeof(struct native_filesystem));
+       if (!nfs) {
+               err = -ENOMEM;
+               goto error;
+       }
+       nfs->nfs_atimo = ul;
+       if ((unsigned long)nfs->nfs_atimo != ul) {
+               err = -EINVAL;
+               goto error;
+       }
+       fs = _sysio_fs_new(&native_inodesys_ops, 0, nfs);
        if (!fs) {
                err = -ENOMEM;
                goto error;
@@ -474,10 +452,11 @@ create_internal_namespace()
        /*
         * Get root i-node.
         */
-       err = native_stat("/", NULL, &stbuf);
+       t = _SYSIO_LOCAL_TIME();
+       err = native_stat("/", NULL, 0, &stbuf);
        if (err)
                goto error;
-       rootino = native_i_new(fs, &stbuf);
+       rootino = native_i_new(fs, t + FS2NFS(fs)->nfs_atimo, &stbuf);
        if (!rootino) {
                err = -ENOMEM;
                goto error;
@@ -506,6 +485,7 @@ error:
        if (mnt) {
                if (_sysio_do_unmount(mnt) != 0)
                        abort();
+               nfs = NULL;
                fs = NULL;
                rootpb = NULL;
                rootino = NULL;
@@ -515,7 +495,12 @@ error:
        if (fs) {
                FS_RELE(fs);
                _sysio_fs_gone(fs);
+               nfs = NULL;
        }
+       if (nfs)
+               free(nfs);
+       if (opts)
+               free(opts);
 
        return err;
 }
@@ -523,7 +508,7 @@ error:
 static int
 native_fsswop_mount(const char *source,
                    unsigned flags,
-                   const void *data __IS_UNUSED,
+                   const void *data,
                    struct pnode *tocover,
                    struct mount **mntp)
 {
@@ -539,10 +524,11 @@ native_fsswop_mount(const char *source,
                return -ENOENT;
 
        if (!native_internal_mount) {
-               err = create_internal_namespace();
+               err = create_internal_namespace(data);
                if (err)
                        return err;
-       }
+       } else if (data && *(char *)data)
+               return -EINVAL;
 
        /*
         * Lookup the source in the internally maintained name space.
@@ -578,130 +564,94 @@ native_fsswop_mount(const char *source,
 }
 
 static int
-native_i_invalid(struct inode *inop, struct intnl_stat stbuf)
+native_i_invalid(struct inode *inop, struct intnl_stat *stat)
 {
+       struct native_inode *nino;
+
        /*
         * Validate passed in inode against stat struct info
         */
-       struct native_inode *nino = I2NI(inop);
+       nino = I2NI(inop);
        
-       if ((nino->ni_ident.dev != stbuf.st_dev ||
-            nino->ni_ident.ino != stbuf.st_ino ||
+       if (!nino->ni_attrtim ||
+           (nino->ni_ident.dev != stat->st_dev ||
+            nino->ni_ident.ino != stat->st_ino ||
 #ifdef HAVE_GENERATION
-            nino->ni_ident.gen != stbuf.st_gen ||
+            nino->ni_ident.gen != stat->st_gen ||
 #endif
-            ((inop)->i_mode & S_IFMT) != (stbuf.st_mode & S_IFMT)) ||
-           (((inop)->i_rdev != stbuf.st_rdev) &&
-              (S_ISCHR((inop)->i_mode) || S_ISBLK((inop)->i_mode))))
+            ((inop)->i_stbuf.st_mode & S_IFMT) != (stat->st_mode & S_IFMT)) ||
+           (((inop)->i_stbuf.st_rdev != stat->st_rdev) &&
+              (S_ISCHR((inop)->i_stbuf.st_mode) ||
+               S_ISBLK((inop)->i_stbuf.st_mode)))) {
+               nino->ni_attrtim = 0;                   /* invalidate attrs */
                return 1;
-       
+       }
        return 0;
 }
 
+static struct inode *
+native_iget(struct filesys *fs, time_t expire, struct intnl_stat *stbp)
+{
+       struct inode *ino;
+       struct native_inode_identifier ident;
+       struct file_identifier fileid;
+
+       bzero(&ident, sizeof(ident)); 
+       ident.dev = stbp->st_dev;
+       ident.ino = stbp->st_ino;
+#ifdef HAVE_GENERATION
+       ident.gen = stbp->st_gen;
+#endif
+       fileid.fid_data = &ident;
+       fileid.fid_len = sizeof(ident);
+       ino = _sysio_i_find(fs, &fileid);
+       if (ino) {
+               ino->i_stbuf = *stbp;
+               I2NI(ino)->ni_attrtim = expire;
+               return ino;
+       }
+       return native_i_new(fs, expire, stbp);
+}
+
 /*
  * Find, and validate, or create i-node by host-relative path. Returned i-node
  * is referenced.
  */
 static int
-native_iget(struct filesys *fs,
-           const char *path,
-           struct inode **inop,
-           int forced)
+native_ibind(struct filesys *fs,
+            char *path,
+            time_t t,
+            struct inode **inop)
 {
+       struct intnl_stat ostbuf, stbuf;
        int     err;
        struct inode *ino;
-       struct intnl_stat stbuf;
-       struct native_inode_identifier ident;
-       struct file_identifier fileid;
 
-       /*
-        * Get file status.
-        */
-       err = native_stat(path, *inop ? I2NI(*inop) : NULL, &stbuf);
-       if (err) {
-               *inop = NULL;
+       if (*inop)
+               ostbuf = (*inop)->i_stbuf;
+
+       err = native_stat(path, *inop, t, &stbuf);
+       if (err)
                return err;
-       }
 
        /* 
         * Validate?
         */
        if (*inop) {
-               if (!native_i_invalid(*inop, stbuf))
+               if (!native_i_invalid(*inop, &ostbuf))
                        return 0;
                /*
                 * Invalidate.
                 */
+               _sysio_i_undead(*inop);
                *inop = NULL;
        }
 
-       /*
-        * I-node is not already known. Find or create it.
-        */
-       bzero(&ident, sizeof(ident)); 
-       ident.dev = stbuf.st_dev;
-       ident.ino = stbuf.st_ino;
-#ifdef HAVE_GENERATION
-       ident.gen = stbuf.st_gen;
-#endif
-       fileid.fid_data = &ident;
-       fileid.fid_len = sizeof(ident);
-       ino = _sysio_i_find(fs, &fileid);
-       if (ino &&
-           (forced || (ino->i_mode & S_IFMT) != (stbuf.st_mode & S_IFMT))) {
-               /*
-                * Insertion was forced or dup inum but it's already present!
-                */
-               if (native_i_invalid(ino, stbuf)) {
-                       /* 
-                        * Cached inode has stale attrs
-                        * make way for the new one
-                        */
-                       I_GONE(ino);
-                       ino = NULL;
-               } else
-                       /* 
-                        * OK to reuse cached inode
-                        */
-                       goto out;
-       }
-
-       if (!ino) {
-               ino = native_i_new(fs, &stbuf);
-               if (!ino)
-                       err = -ENOMEM;
-       }
-out:
-       if (!err)
-               *inop = ino;
-       return err;
-}
-
-/*
- * Look up named object in host's name space by path.
- */
-static int
-native_path_lookup(struct filesys *fs, const char *path, struct inode **inop)
-{
-
-       return native_iget(fs, path, inop, 0);
-}
-
-/*
- * Look up object by it's path node.
- */
-static int
-native_i_lookup(struct filesys *fs, struct pnode_base *pb, struct inode **inop)
-{
-       int     err;
-       char    *path;
-
-       path = _sysio_pb_path(pb, '/');
-       if (!path)
+       if (!(ino = native_iget(fs, t + FS2NFS(fs)->nfs_atimo, &stbuf)))
                return -ENOMEM;
-       err = native_path_lookup(fs, path, inop);
-       free(path);
-       return err;
+
+       *inop = ino;
+       return 0;
 }
 
 static int
@@ -710,11 +660,25 @@ native_inop_lookup(struct pnode *pno,
                   struct intent *intnt __IS_UNUSED,
                   const char *path __IS_UNUSED)
 {
+       time_t  t;
+       char    *fqpath;
+       struct filesys *fs;
        int     err;
 
        *inop = pno->p_base->pb_ino;
 
        /*
+        * Try to use the cached attributes unless the intent
+        * indicates we are looking up the last component and
+        * caller wants attributes. In that case, force a refresh.
+        */
+       t = _SYSIO_LOCAL_TIME();
+       if (*inop &&
+           (path || !intnt || (intnt->int_opmask & INT_GETATTR) == 0) &&
+           NATIVE_ATTRS_VALID(I2NI(*inop), t))
+               return 0;
+
+       /*
         * Don't have an inode yet. Because we translate everything back to
         * a single name space for the host, we will assume the object the
         * caller is looking for has no existing alias in our internal
@@ -724,7 +688,12 @@ native_inop_lookup(struct pnode *pno,
         * The file identifier *will* be unique. It's got to have a different
         * dev.
         */
-       err = native_i_lookup(pno->p_mount->mnt_fs, pno->p_base, inop);
+       fqpath = _sysio_pb_path(pno->p_base, '/');
+       if (!fqpath)
+               return -ENOMEM;
+       fs = pno->p_mount->mnt_fs;
+       err = native_ibind(fs, fqpath, t + FS2NFS(fs)->nfs_atimo, inop);
+       free(fqpath);
        if (err)
                *inop = NULL;
        return err;
@@ -733,30 +702,46 @@ native_inop_lookup(struct pnode *pno,
 static int
 native_inop_getattr(struct pnode *pno,
                    struct inode *ino,
-                   struct intnl_stat *stbuf)
+                   struct intnl_stat *stat)
 {
-       char    *path;
        struct native_inode *nino;
        int     err;
 
-       nino = ino ? I2NI(ino) : NULL;
+       /*
+        * We just cannot use the cached attributes when getattr is
+        * called. Had the caller felt those were sufficient then
+        * they could have (would have?) simply used what was cached
+        * after revalidating. In this case, there's a good chance the
+        * caller is looking for the current time stamps and/or size. Something
+        * pretty volatile anyway.
+        */
        err = 0;                                        /* compiler cookie */
-       if (!ino) {
+       if (pno) {
+               char    *path;
+               struct filesys *fs;
+               time_t  t;
+
                path = _sysio_pb_path(pno->p_base, '/');
                if (!path)
                        return -ENOMEM;
-               err = native_stat(path, nino, stbuf);
+               fs = pno->p_mount->mnt_fs;
+               t = _SYSIO_LOCAL_TIME();
+               err = native_stat(path, ino, t + FS2NFS(fs)->nfs_atimo, stat);
                free(path);
-       } else if (nino->ni_fd >= 0)
-               err = native_fstat(nino->ni_fd, nino, stbuf);
+       } else if ((nino = I2NI(ino))->ni_fd >= 0)
+               /*
+                * Don't have access to the fs record anymore. Just
+                * refresh but keep the current timeout.
+                */
+               err = native_stat(NULL, ino, nino->ni_attrtim, stat);
        else {
                /*
                 * Dev inodes don't open in this driver. We won't have
                 * a file descriptor with which to do the deed then. Satisfy
                 * the request from the cached copy of the attributes.
                 */
-               (void )memcpy(stbuf,
-                             &nino->ni_stat,
+               (void )memcpy(stat,
+                             &ino->i_stbuf,
                              sizeof(struct intnl_stat));
                err = 0;
        }
@@ -764,26 +749,46 @@ native_inop_getattr(struct pnode *pno,
        return err;
 }
 
+#ifdef SYSIO_SYS_utime
+static int
+_ut(const char *path, time_t actime, time_t modtime)
+{
+       struct utimbuf ut;
+
+       ut.actime = actime;
+       ut.modtime = modtime;
+       return syscall(SYSIO_SYS_utime, path, &ut);
+}
+#else
+static int
+_ut(const char *path, time_t actime, time_t modtime)
+{
+       struct timeval tv[2];
+
+       tv[0].tv_sec = actime;
+       tv[0].tv_usec = 0;
+       tv[1].tv_sec = modtime;
+       tv[1].tv_usec = 0;
+       return syscall(SYSIO_SYS_utimes, path, &tv);
+}
+#endif
+
 static int
 native_inop_setattr(struct pnode *pno,
                    struct inode *ino,
                    unsigned mask,
-                   struct intnl_stat *stbuf)
+                   struct intnl_stat *stat)
 {
        char    *path;
        struct native_inode *nino;
        int     fd;
-       struct intnl_stat *stbp, _stbuf;
        int     err;
 
        path = NULL;
        nino = ino ? I2NI(ino) : NULL;
        fd = -1;
-       stbp = &_stbuf;
-       if (nino) {
+       if (nino)
                fd = nino->ni_fd;
-               stbp = &nino->ni_stat;
-       }
        if (fd < 0 || mask & (SETATTR_MTIME|SETATTR_ATIME)) {
                if (!pno)
                        return -EEXIST;
@@ -795,10 +800,7 @@ native_inop_setattr(struct pnode *pno,
        /*
         * Get current status for undo.
         */
-       err =
-           fd < 0
-             ? native_stat(path, nino, stbp)
-             : native_fstat(fd, nino, stbp);
+       err = native_stat(path, ino, 0, NULL);
        if (err)
                goto out;
 
@@ -808,31 +810,30 @@ native_inop_setattr(struct pnode *pno,
                /*
                 * Alter permissions attribute.
                 */
-               mode = stbuf->st_mode & 07777;
+               mode = stat->st_mode & 07777;
                err =
                    fd < 0
-                     ? syscall(SYS_chmod, path, mode)
-                     : syscall(SYS_fchmod, fd, mode);
+                     ? syscall(SYSIO_SYS_chmod, path, mode)
+                     : syscall(SYSIO_SYS_fchmod, fd, mode);
                if (err)
                        err = -errno;
        }
        if (err)
                mask &= ~SETATTR_MODE;
        else if (mask & (SETATTR_MTIME|SETATTR_ATIME)) {
-               struct utimbuf ut;
+               time_t  actime, modtime;
 
                /*
                 * Alter access and/or modify time attributes.
                 */
-               ut.actime = stbuf->st_atime;
-               ut.modtime = stbuf->st_mtime;
-               if (mask & SETATTR_MTIME)
-                       ut.modtime = stbuf->st_mtime;
+               actime  = ino->i_stbuf.st_atime;
+               modtime  = ino->i_stbuf.st_mtime;
                if (mask & SETATTR_ATIME)
-                       ut.actime = stbuf->st_atime;
-               err = syscall(__SYS_UTIME, path, &ut);
-               if (err)
-                       err = -errno;
+                       actime = stat->st_atime;
+               if (mask & SETATTR_MTIME)
+                       modtime = stat->st_mtime;
+               if (_ut(path, actime, modtime) != 0)
+                       return -errno;
        }
        if (err)
                mask &= ~(SETATTR_MTIME|SETATTR_ATIME);
@@ -843,21 +844,21 @@ native_inop_setattr(struct pnode *pno,
                 */
                err =
                    fd < 0
-                     ? syscall(SYS_chown,
+                     ? syscall(SYSIO_SYS_chown,
                                path,
                                mask & SETATTR_UID
-                                 ? stbuf->st_uid
+                                 ? stat->st_uid
                                  : (uid_t )-1,
                                mask & SETATTR_GID
-                                 ? stbuf->st_gid
+                                 ? stat->st_gid
                                  : (gid_t )-1)
-                     : syscall(SYS_fchown,
+                     : syscall(SYSIO_SYS_fchown,
                                fd,
                                mask & SETATTR_UID
-                                 ? stbuf->st_uid
+                                 ? stat->st_uid
                                  : (uid_t )-1,
                                mask & SETATTR_GID
-                                 ? stbuf->st_gid
+                                 ? stat->st_gid
                                  : (gid_t )-1);
                if (err)
                        err = -errno;
@@ -869,8 +870,8 @@ native_inop_setattr(struct pnode *pno,
                 * Do the truncate last. It can't be undone.
                 */
                 (void )(fd < 0
-                          ? syscall(__SYS_TRUNCATE, path, stbuf->st_size)
-                          : syscall(__SYS_FTRUNCATE, fd, stbuf->st_size));
+                          ? syscall(SYSIO_SYS_truncate, path, stat->st_size)
+                          : syscall(SYSIO_SYS_ftruncate, fd, stat->st_size));
        }
        if (!err)
                goto out;
@@ -880,42 +881,35 @@ native_inop_setattr(struct pnode *pno,
         */
        if (mask & (SETATTR_UID|SETATTR_GID)) {
                 (void )(fd < 0
-                          ? syscall(SYS_chown,
+                          ? syscall(SYSIO_SYS_chown,
                                     path,
                                     mask & SETATTR_UID
-                                      ? stbp->st_uid
+                                      ? ino->i_stbuf.st_uid
                                       : (uid_t )-1,
                                     mask & SETATTR_GID
-                                      ? stbp->st_gid
+                                      ? ino->i_stbuf.st_gid
                                       : (gid_t )-1)
-                          : syscall(SYS_fchown,
+                          : syscall(SYSIO_SYS_fchown,
                                     fd,
                                     mask & SETATTR_UID
-                                      ? stbp->st_uid
+                                      ? ino->i_stbuf.st_uid
                                       : (uid_t )-1,
                                     mask & SETATTR_GID
-                                      ? stbp->st_gid
+                                      ? ino->i_stbuf.st_gid
                                       : (gid_t )-1));
        }
-       if (mask & (SETATTR_MTIME|SETATTR_ATIME)) {
-               struct utimbuf ut;
-
-               ut.actime = stbp->st_atime;
-               ut.modtime = stbp->st_mtime;
-               (void )syscall(__SYS_UTIME, path, &ut);
-       }
+       if (mask & (SETATTR_MTIME|SETATTR_ATIME))
+               (void )_ut(path, ino->i_stbuf.st_atime, ino->i_stbuf.st_mtime);
        if (mask & SETATTR_MODE) {
                fd < 0
-                 ? syscall(SYS_chmod, path, stbp->st_mode & 07777)
-                 : syscall(SYS_fchmod, stbp->st_mode & 07777);
+                 ? syscall(SYSIO_SYS_chmod, path, ino->i_stbuf.st_mode & 07777)
+                 : syscall(SYSIO_SYS_fchmod, ino->i_stbuf.st_mode & 07777);
        }
 out:
        /*
-        * We must refresh the cached attributes on success.
+        * We must refresh the cached attributes.
         */
-       if (!err && (fd < 0
-                      ? native_stat(path, nino, stbp)
-                      : native_fstat(fd, nino, stbp)) != 0)
+       if (!err && native_stat(path, ino, _SYSIO_LOCAL_TIME(), NULL) != 0)
                abort();
        if (path)
                free(path);
@@ -931,11 +925,11 @@ native_pos(int fd, _SYSIO_OFF_T *offset, int whence)
        assert(*offset >= 0);
 
        off = *offset;
-#if _LARGEFILE64_SOURCE && defined(SYS__llseek)
+#if _LARGEFILE64_SOURCE && defined(SYSIO_SYS__llseek)
        {
                int     err;
                err =
-                   syscall(SYS__llseek,
+                   syscall(SYSIO_SYS__llseek,
                            (unsigned int)fd,
                            (unsigned int)(off >> 32),
                            (unsigned int)off,
@@ -946,7 +940,7 @@ native_pos(int fd, _SYSIO_OFF_T *offset, int whence)
        }
 #else
        off =
-           syscall(SYS_lseek,
+           syscall(SYSIO_SYS_lseek,
                    fd,
                    off,
                    whence);
@@ -981,16 +975,16 @@ native_filldirentries(struct native_inode *nino,
        nino->ni_fpos = *basep;
 
        cc =
-#if defined(SYS_getdirentries)
-           syscall(SYS_getdirentries,
+#if defined(SYSIO_SYS_getdirentries)
+           syscall(SYSIO_SYS_getdirentries,
                    nino->ni_fd,
                    buf,
                    nbytes,
                    basep);
-#elif defined(SYS_getdents64)
-           syscall(SYS_getdents64, nino->ni_fd, buf, nbytes);
-#elif defined(SYS_getdents)
-           syscall(SYS_getdents, nino->ni_fd, buf, nbytes);
+#elif defined(SYSIO_SYS_getdents64)
+           syscall(SYSIO_SYS_getdents64, nino->ni_fd, buf, nbytes);
+#elif defined(SYSIO_SYS_getdents)
+           syscall(SYSIO_SYS_getdents, nino->ni_fd, buf, nbytes);
 #endif
 
        if (cc < 0)
@@ -1022,6 +1016,12 @@ native_getdirentries(struct inode *ino,
        struct dirent64 *d64p;
        size_t  namlen;
        size_t  reclen;
+       /*
+        * Work-around for broken 64 bit basep update 
+        * Get value of basep to return from last directory 
+        * entry d_off value 
+        */
+       _SYSIO_OFF_T last_offset = *basep;
 #else
 #define bp buf
 #define count nbytes
@@ -1068,12 +1068,15 @@ native_getdirentries(struct inode *ino,
                cc -= ldp->ld_reclen;
                ldp = (struct linux_dirent *)((char *)ldp + ldp->ld_reclen);
                nbytes -= d64p->d_reclen;
+               last_offset = d64p->d_off;
                d64p = (struct dirent64 *)((char *)d64p + d64p->d_reclen);
        }
+       nino->ni_fpos = *basep = last_offset;
        free(bp);
-       if (d64p == (struct dirent64 *)buf && cc)
-               cc = -EINVAL;                           /* buf too small */
-       cc = (char *)d64p - buf;
+       cc =
+           (d64p == (struct dirent64 *)buf && cc)
+             ? -EINVAL
+             : (char *)d64p - buf;
 #else
 #undef bp
 #undef count
@@ -1091,7 +1094,7 @@ native_inop_mkdir(struct pnode *pno, mode_t mode)
        if (!path)
                return -ENOMEM;
 
-       err = syscall(SYS_mkdir, path, mode);
+       err = syscall(SYSIO_SYS_mkdir, path, mode);
        if (err != 0)
                err = -errno;
        free(path);
@@ -1108,7 +1111,7 @@ native_inop_rmdir(struct pnode *pno)
        if (!path)
                return -ENOMEM;
 
-       err = syscall(SYS_rmdir, path);
+       err = syscall(SYSIO_SYS_rmdir, path);
        if (err != 0)
                err = -errno;
        free(path);
@@ -1125,7 +1128,7 @@ native_inop_symlink(struct pnode *pno, const char *data)
        if (!path)
                return -ENOMEM;
 
-       err = syscall(SYS_symlink, data, path);
+       err = syscall(SYSIO_SYS_symlink, data, path);
        if (err != 0)
                err = -errno;
        free(path);
@@ -1141,7 +1144,7 @@ native_inop_readlink(struct pnode *pno, char *buf, size_t bufsiz)
        path = _sysio_pb_path(pno->p_base, '/');
        if (!path)
                return -ENOMEM;
-       i = syscall(SYS_readlink, path, buf, bufsiz);
+       i = syscall(SYSIO_SYS_readlink, path, buf, bufsiz);
        if (i < 0)
                i = -errno;
        free(path);
@@ -1174,20 +1177,22 @@ native_inop_open(struct pnode *pno, int flags, mode_t mode)
 #ifdef O_LARGEFILE
        flags |= O_LARGEFILE;
 #endif
-       fd = syscall(SYS_open, path, flags, mode);
+       fd = syscall(SYSIO_SYS_open, path, flags, mode);
        if (!pno->p_base->pb_ino && fd >= 0) {
+               struct filesys *fs;
                int     err;
 
                /*
                 * Success but we need to return an i-node.
                 */
+               fs = pno->p_mount->mnt_fs;
                err =
-                   native_iget(pno->p_mount->mnt_fs,
-                               path,
-                               &pno->p_base->pb_ino,
-                               1);
+                   native_ibind(fs,
+                                path,
+                                _SYSIO_LOCAL_TIME() + FS2NFS(fs)->nfs_atimo,
+                                &pno->p_base->pb_ino);
                if (err) {
-                       (void )syscall(SYS_close, fd);
+                       (void )syscall(SYSIO_SYS_close, fd);
                        if (err == -EEXIST)
                                abort();
                        fd = err;
@@ -1210,10 +1215,10 @@ native_inop_open(struct pnode *pno, int flags, mode_t mode)
                        /*
                         * Keep existing.
                         */
-                       (void )syscall(SYS_close, fd);
+                       (void )syscall(SYSIO_SYS_close, fd);
                        return 0;
                }
-               (void )syscall(SYS_close, nino->ni_fd);
+               (void )syscall(SYSIO_SYS_close, nino->ni_fd);
        }
        /*
         * Invariant; First open. Must init.
@@ -1250,7 +1255,7 @@ native_inop_close(struct inode *ino)
                return 0;
        }
 
-       err = syscall(SYS_close, nino->ni_fd);
+       err = syscall(SYSIO_SYS_close, nino->ni_fd);
        if (err)
                return -errno;
 
@@ -1274,7 +1279,7 @@ native_inop_link(struct pnode *old, struct pnode *new)
                goto out;
        }
 
-       err = syscall(SYS_link, opath, npath);
+       err = syscall(SYSIO_SYS_link, opath, npath);
        if (err != 0)
                err = -errno;
 
@@ -1283,7 +1288,6 @@ out:
                free(opath);
        if (npath)
                free(npath);
-
        return err;
 }
 
@@ -1309,7 +1313,7 @@ native_inop_unlink(struct pnode *pno)
         * (usually .NFSXXXXXX, where the X's are replaced by the PID and some
         * unique characters) in order to simulate the proper semantic.
         */
-       if (syscall(SYS_unlink, path) != 0)
+       if (syscall(SYSIO_SYS_unlink, path) != 0)
                err = -errno;
        free(path);
        return err;
@@ -1328,7 +1332,7 @@ native_inop_rename(struct pnode *old, struct pnode *new)
                goto out;
        }
 
-       err = syscall(SYS_rename, opath, npath);
+       err = syscall(SYSIO_SYS_rename, opath, npath);
        if (err != 0)
                err = -errno;
 
@@ -1337,22 +1341,12 @@ out:
                free(opath);
        if (npath)
                free(npath);
-
        return err;
 }
 
 static ssize_t
 dopio(void *buf, size_t count, _SYSIO_OFF_T off, struct native_io *nio)
 {
-#if defined(_LARGEFILE64_SOURCE) && \
-    defined(SYS_pread64) && \
-    defined(SYS_pwrite64)
-#define _NATIVE_SYSCALL_PREAD SYS_pread64
-#define _NATIVE_SYSCALL_PWRITE SYS_pwrite64
-#else
-#define _NATIVE_SYSCALL_PREAD SYS_pread
-#define _NATIVE_SYSCALL_PWRITE SYS_pwrite
-#endif
        ssize_t cc;
 
        if (!(off == nio->nio_nino->ni_fpos || nio->nio_nino->ni_seekok))
@@ -1368,7 +1362,9 @@ dopio(void *buf, size_t count, _SYSIO_OFF_T off, struct native_io *nio)
                        return -1;
                }
                cc =
-                   syscall(nio->nio_op == 'r' ? SYS_read : SYS_write,
+                   syscall(nio->nio_op == 'r'
+                             ? SYSIO_SYS_read
+                             : SYSIO_SYS_write,
                            nio->nio_nino->ni_fd,
                            buf,
                            count);
@@ -1377,16 +1373,14 @@ dopio(void *buf, size_t count, _SYSIO_OFF_T off, struct native_io *nio)
        } else
                cc =
                    syscall((nio->nio_op == 'r'
-                              ? _NATIVE_SYSCALL_PREAD
-                              : _NATIVE_SYSCALL_PWRITE),
+                              ? SYSIO_SYS_pread
+                              : SYSIO_SYS_pwrite),
                            nio->nio_nino->ni_fd,
                            buf,
                            count,
                            off);
 
        return cc;
-#undef _NATIVE_SYSCALL_PREAD
-#undef _NATIVE_SYSCALL_PWRITE
 }
 
 static ssize_t
@@ -1399,9 +1393,10 @@ doiov(const struct iovec *iov,
        ssize_t cc;
 
 #if !(defined(REDSTORM) || defined(MAX_IOVEC))
-#define MAX_IOVEC      INT_MAX
+#define MAX_IOVEC      INT_MAX
 #endif
 
+
        if (count <= 0)
                return -EINVAL;
 
@@ -1426,7 +1421,7 @@ doiov(const struct iovec *iov,
        cc =
 #ifndef REDSTORM
            count <= MAX_IOVEC
-             ? syscall(nio->nio_op == 'r' ? SYS_readv : SYS_writev,
+             ? syscall(nio->nio_op == 'r' ? SYSIO_SYS_readv : SYSIO_SYS_writev,
                        nio->nio_nino->ni_fd,
                        iov,
                        count)
@@ -1471,13 +1466,7 @@ lockop_all(struct native_inode *nino,
                flock.l_len = xtv->xtv_len;
                xtv++;
                err =
-                   syscall(
-#if !_LARGEFILE64_SOURCE
-                           SYS_fcntl64
-#else
-                           SYS_fcntl
-#endif
-                           ,
+                   syscall(SYSIO_SYS_fcntl,
                            nino->ni_fd,
                            F_SETLK,
                            &flock);
@@ -1631,7 +1620,7 @@ native_inop_fcntl(struct inode *ino,
 #ifdef F_GETOWN
        case F_GETOWN:
 #endif
-               *rtn = syscall(SYS_fcntl, nino->ni_fd, cmd);
+               *rtn = syscall(SYSIO_SYS_fcntl, nino->ni_fd, cmd);
                if (*rtn == -1)
                        err = -errno;
                break;
@@ -1645,7 +1634,7 @@ native_inop_fcntl(struct inode *ino,
        case F_SETOWN:
 #endif
                arg = va_arg(ap, long);
-               *rtn = syscall(SYS_fcntl, nino->ni_fd, cmd, arg);
+               *rtn = syscall(SYSIO_SYS_fcntl, nino->ni_fd, cmd, arg);
                if (*rtn == -1)
                        err = -errno;
                break;
@@ -1683,16 +1672,16 @@ native_inop_statvfs(struct pnode *pno,
        }
 
        /*
-        * The syscall interface does not support SYS_fstatvfs.
+        * The syscall interface does not support SYSIO_SYS_fstatvfs.
         * Should possibly return ENOSYS, but thought it
-        * better to use SYS_fstatfs and fill in as much of
+        * better to use SYSIO_SYS_fstatfs and fill in as much of
         * the statvfs structure as possible.  This allows
         * for more of a test of the sysio user interface.
         */
        rc =
            path
-             ? syscall(SYS_statfs, path, &fs)
-             : syscall(SYS_fstatfs, I2NI(ino)->ni_fd, &fs);
+             ? syscall(SYSIO_SYS_statfs, path, &fs)
+             : syscall(SYSIO_SYS_fstatfs, I2NI(ino)->ni_fd, &fs);
        if (path)
                free(path);
        if (rc < 0)
@@ -1720,7 +1709,7 @@ native_inop_sync(struct inode *ino)
 
        assert(I2NI(ino)->ni_fd >= 0);
 
-       err = syscall(SYS_fsync, I2NI(ino)->ni_fd);
+       err = syscall(SYSIO_SYS_fsync, I2NI(ino)->ni_fd);
        if (err)
                err = -errno;
        return err;
@@ -1729,17 +1718,19 @@ native_inop_sync(struct inode *ino)
 static int
 native_inop_datasync(struct inode *ino)
 {
+       struct native_inode *nino;
        int     err;
 
-       assert(I2NI(ino)->ni_fd >= 0);
+       nino = I2NI(ino);
+       assert(nino->ni_fd >= 0);
 
-#ifdef NATIVE_FDATASYNC
-       err = syscall(NATIVE_FDATASYNC, I2NI(ino)->ni_fd);
+#ifdef SYSIO_SYS_fdatasync
+       err = syscall(SYSIO_SYS_fdatasync, I2NI(ino)->ni_fd);
 #else
 #if 0
 #warning No fdatasync system call -- Using fsync instead!
 #endif
-       err = syscall(SYS_fsync, I2NI(ino)->ni_fd);
+       err = syscall(SYSIO_SYS_fsync, I2NI(ino)->ni_fd);
 #endif
        if (err)
                err = -errno;
@@ -1752,16 +1743,17 @@ native_inop_ioctl(struct inode *ino,
                  unsigned long int request,
                  va_list ap)
 {
+       struct native_inode *nino;
        long arg1, arg2, arg3, arg4;
 
-       assert(I2NI(ino)->ni_fd >= 0);
-
+       nino = I2NI(ino);
+       assert(nino->ni_fd >= 0);
        arg1 = va_arg(ap, long);
        arg2 = va_arg(ap, long);
        arg3 = va_arg(ap, long);
        arg4 = va_arg(ap, long);
 
-       return syscall(SYS_ioctl, I2NI(ino)->ni_fd, request,
+       return syscall(SYSIO_SYS_ioctl, I2NI(ino)->ni_fd, request,
                       arg1, arg2, arg3, arg4);
 }
 #else
@@ -1785,7 +1777,7 @@ native_inop_gone(struct inode *ino)
        struct native_inode *nino = I2NI(ino);
 
        if (nino->ni_fd >= 0)
-               (void )syscall(SYS_close, nino->ni_fd);
+               (void )syscall(SYSIO_SYS_close, nino->ni_fd);
 
        free(ino->i_private);
 }
@@ -1794,6 +1786,7 @@ static void
 native_fsop_gone(struct filesys *fs __IS_UNUSED)
 {
 
+       free(fs->fs_private);
        /*
         * Do nothing. There is no private part maintained for the
         * native file interface.
index b037e60..3ac7894 100644 (file)
 #include <sys/fcntl.h>
 #include <sys/syscall.h>
 #include <sys/socket.h>
+#ifdef __linux__
 #include <linux/net.h>
+#endif
 #include <sys/uio.h>
 #include <sys/queue.h>
 
 #include "xtio.h"
 #include "sysio.h"
+#include "native.h"
 #include "fs.h"
 #include "inode.h"
 #include "file.h"
@@ -116,7 +119,7 @@ struct filesys_ops sockets_filesys_ops = {
        (void (*)(struct filesys *))sockets_illop
 };
 
-static struct filesys *sockets_fs;
+static struct filesys *sockets_fs = NULL;
 
 static struct inode_ops sockets_i_ops;
 
@@ -127,6 +130,8 @@ int
 _sysio_sockets_init()
 {
 
+       assert(!sockets_fs);
+
        sockets_i_ops = _sysio_nodev_ops;
        sockets_i_ops.inop_close = sockets_inop_close;
        sockets_i_ops.inop_read = sockets_inop_read;
@@ -155,7 +160,7 @@ sockets_inop_close(struct inode *ino)
        if (ski->ski_fd < 0)
                return -EBADF;
 
-       err = syscall(SYS_close, ski->ski_fd);
+       err = syscall(SYSIO_SYS_close, ski->ski_fd);
        if (err)
                return -errno;
        ski->ski_fd = -1;
@@ -206,7 +211,7 @@ static ssize_t
 _readv(int fd, const struct iovec *vector, int count)
 {
 
-       return syscall(SYS_readv, fd, vector, count);
+       return syscall(SYSIO_SYS_readv, fd, vector, count);
 }
 
 static int
@@ -224,7 +229,7 @@ static ssize_t
 _writev(int fd, const struct iovec *vector, int count)
 {
 
-       return syscall(SYS_writev, fd, vector, count);
+       return syscall(SYSIO_SYS_writev, fd, vector, count);
 }
 
 static int
@@ -265,7 +270,7 @@ sockets_inop_fcntl(struct inode *ino __IS_UNUSED,
        case F_GETFD:
        case F_GETFL:
        case F_GETOWN:
-               *rtn = syscall(SYS_fcntl, I2SKI(ino)->ski_fd, cmd);
+               *rtn = syscall(SYSIO_SYS_fcntl, I2SKI(ino)->ski_fd, cmd);
                break;
        case F_DUPFD:
        case F_SETFD:
@@ -275,7 +280,7 @@ sockets_inop_fcntl(struct inode *ino __IS_UNUSED,
        case F_SETLKW:
        case F_SETOWN:
                arg = va_arg(ap, long);
-               *rtn = syscall(SYS_fcntl, I2SKI(ino)->ski_fd, cmd, arg);
+               *rtn = syscall(SYSIO_SYS_fcntl, I2SKI(ino)->ski_fd, cmd, arg);
                break;
        default:
                *rtn = -1;
@@ -290,7 +295,7 @@ sockets_inop_sync(struct inode *ino)
 
        assert(I2SKI(ino)->ski_fd >= 0);
 
-       return syscall(SYS_fsync, I2SKI(ino)->ski_fd);
+       return syscall(SYSIO_SYS_fsync, I2SKI(ino)->ski_fd);
 }
 
 static int
@@ -299,7 +304,7 @@ sockets_inop_datasync(struct inode *ino)
 
        assert(I2SKI(ino)->ski_fd >= 0);
 
-       return syscall(SYS_fdatasync, I2SKI(ino)->ski_fd);
+       return syscall(SYSIO_SYS_fdatasync, I2SKI(ino)->ski_fd);
 }
 
 #ifdef HAVE_LUSTRE_HACK
@@ -321,7 +326,7 @@ sockets_inop_ioctl(struct inode *ino,
        arg3 = va_arg(ap, long);
        arg4 = va_arg(ap, long);
 
-       return syscall(SYS_ioctl, I2SKI(ino)->ski_fd, request,
+       return syscall(SYSIO_SYS_ioctl, I2SKI(ino)->ski_fd, request,
                       arg1, arg2, arg3, arg4);
 }
 #else
@@ -358,6 +363,7 @@ _sysio_sockets_inew()
        static ino_t inum = 1;
        struct socket_info *ski;
        struct inode *ino;
+       static struct intnl_stat zero_stat;
 
        ski = malloc(sizeof(struct socket_info));
        if (!ski)
@@ -370,8 +376,7 @@ _sysio_sockets_inew()
        ino =
            _sysio_i_new(sockets_fs,
                         &ski->ski_fileid,
-                        0,
-                        0,
+                        &zero_stat,
                         0,
                         &sockets_i_ops,
                         ski);
@@ -399,12 +404,13 @@ socket(int domain, int type, int protocol)
        }
 
        ski = I2SKI(ino);
-#ifndef SYS_socketcall
-       ski->ski_fd = syscall(SYS_socket, domain, type, protocol);
+#ifndef SYSIO_SYS_socketcall
+       ski->ski_fd = syscall(SYSIO_SYS_socket, domain, type, protocol);
 #else
        {
                unsigned long avec[3] = {domain, type, protocol};
-               ski->ski_fd = syscall(SYS_socketcall, SYS_SOCKET, avec);
+               ski->ski_fd =
+                   syscall(SYSIO_SYS_socketcall, SYS_SOCKET, avec);
        }
 #endif
        if (ski->ski_fd < 0) {
@@ -469,16 +475,20 @@ accept(int s, struct sockaddr *addr, socklen_t *addrlen)
        }
 
        ski = I2SKI(ino);
-#ifndef SYS_socketcall
-       ski->ski_fd = syscall(SYS_accept, I2SKI(ofil->f_ino)->ski_fd,
-                               addr, addrlen);
+#ifndef SYSIO_SYS_socketcall
+       ski->ski_fd =
+           syscall(SYSIO_SYS_accept,
+                   I2SKI(ofil->f_ino)->ski_fd,
+                   addr,
+                   addrlen);
 #else
        {
                unsigned long avec[3] = {
                        (unsigned long) I2SKI(ofil->f_ino)->ski_fd,
                        (unsigned long) addr,
                        (unsigned long) addrlen};
-               ski->ski_fd = syscall(SYS_socketcall, SYS_ACCEPT, avec);
+               ski->ski_fd =
+                   syscall(SYSIO_SYS_socketcall, SYS_ACCEPT, avec);
        }
 #endif
        if (ski->ski_fd < 0) {
@@ -521,13 +531,16 @@ bind(int sockfd, const struct sockaddr *my_addr, socklen_t addrlen)
                goto out;
        }
 
-#ifndef SYS_socketcall
-       if (syscall(SYS_bind, I2SKI(fil->f_ino)->ski_fd, my_addr, addrlen)) {
+#ifndef SYSIO_SYS_socketcall
+       if (syscall(SYSIO_SYS_bind,
+                   I2SKI(fil->f_ino)->ski_fd,
+                   my_addr,
+                   addrlen)) {
 #else
        avec[0] = I2SKI(fil->f_ino)->ski_fd;
        avec[1] = (unsigned long )my_addr;
        avec[2] = addrlen;
-       if (syscall(SYS_socketcall, SYS_BIND, avec) != 0) {
+       if (syscall(SYSIO_SYS_socketcall, SYS_BIND, avec) != 0) {
 #endif
                err = -errno;
                goto out;
@@ -554,12 +567,14 @@ listen(int s, int backlog)
                goto out;
        }
 
-#ifndef SYS_socketcall
-       if (syscall(SYS_listen, I2SKI(fil->f_ino)->ski_fd, backlog) != 0) {
+#ifndef SYSIO_SYS_socketcall
+       if (syscall(SYSIO_SYS_listen,
+                   I2SKI(fil->f_ino)->ski_fd,
+                   backlog) != 0) {
 #else
        avec[0] = I2SKI(fil->f_ino)->ski_fd;
        avec[1] = backlog;
-       if (syscall(SYS_socketcall, SYS_LISTEN, avec) != 0) {
+       if (syscall(SYSIO_SYS_socketcall, SYS_LISTEN, avec) != 0) {
 #endif
                err = -errno;
                goto out;
@@ -586,14 +601,16 @@ connect(int sockfd, const struct sockaddr *serv_addr, socklen_t addrlen)
                goto out;
        }
 
-#ifndef SYS_socketcall
-       if (syscall(SYS_connect, I2SKI(fil->f_ino)->ski_fd,
-                   serv_addr, addrlen) != 0) {
+#ifndef SYSIO_SYS_socketcall
+       if (syscall(SYSIO_SYS_connect,
+                   I2SKI(fil->f_ino)->ski_fd,
+                   serv_addr,
+                   addrlen) != 0) {
 #else
        avec[0] = I2SKI(fil->f_ino)->ski_fd;
        avec[1] = (unsigned long )serv_addr;
        avec[2] = addrlen;
-       if (syscall(SYS_socketcall, SYS_CONNECT, avec) != 0) {
+       if (syscall(SYSIO_SYS_socketcall, SYS_CONNECT, avec) != 0) {
 #endif
                err = -errno;
                goto out;
index 62eb9f2..c9bfcf3 100644 (file)
@@ -293,6 +293,7 @@ yod_i_new(struct filesys *fs, struct intnl_stat *buf)
        if (!nino)
                return NULL;
        bzero(&nino->ni_ident, sizeof(nino->ni_ident));
+       nino->ni_seekok = 0;
        nino->ni_ident.dev = buf->st_dev;
        nino->ni_ident.ino = buf->st_ino;
 #ifdef HAVE_GENERATION
@@ -307,12 +308,7 @@ yod_i_new(struct filesys *fs, struct intnl_stat *buf)
        ino =
            _sysio_i_new(fs,
                         &nino->ni_fileid,
-#ifndef AUTOMOUNT_FILE_NAME
-                        buf->st_mode & S_IFMT,
-#else
-                        buf->st_mode,                  /* all of the bits! */
-#endif
-                        0,
+                        buf,
                         0,
                         &yod_i_ops,
                         nino);
@@ -480,21 +476,22 @@ yod_fsswop_mount(const char *source,
 }
 
 static int
-yod_i_invalid(struct inode *inop, struct intnl_stat stbuf)
+yod_i_invalid(struct inode *inop, struct intnl_stat *stat)
 {
        /*
         * Validate passed in inode against stat struct info
         */
        struct yod_inode *nino = I2NI(inop);
        
-       if ((nino->ni_ident.dev != stbuf.st_dev ||
-            nino->ni_ident.ino != stbuf.st_ino ||
+       if ((nino->ni_ident.dev != stat->st_dev ||
+            nino->ni_ident.ino != stat->st_ino ||
 #ifdef HAVE_GENERATION
-            nino->ni_ident.gen != stbuf.st_gen ||
+            nino->ni_ident.gen != stat->st_gen ||
 #endif
-            ((inop)->i_mode & S_IFMT) != (stbuf.st_mode & S_IFMT)) ||
-           (((inop)->i_rdev != stbuf.st_rdev) &&
-              (S_ISCHR((inop)->i_mode) || S_ISBLK((inop)->i_mode))))
+            ((inop)->i_stbuf.st_mode & S_IFMT) != (stat->st_mode & S_IFMT)) ||
+           (((inop)->i_stbuf.st_rdev != stat->st_rdev) &&
+              (S_ISCHR((inop)->i_stbuf.st_mode) ||
+               S_ISBLK((inop)->i_stbuf.st_mode))))
                return 1;
        
        return 0;
@@ -529,7 +526,7 @@ yod_iget(struct filesys *fs,
         * Validate?
         */
        if (*inop) {
-               if (!yod_i_invalid(*inop, stbuf))
+               if (!yod_i_invalid(*inop, &stbuf))
                        return 0;
                /*
                 * Invalidate.
@@ -553,7 +550,7 @@ yod_iget(struct filesys *fs,
                /*
                 * Insertion was forced but it's already present!
                 */
-               if (yod_i_invalid(ino, stbuf)) {
+               if (yod_i_invalid(ino, &stbuf)) {
                        /* 
                         * Cached inode has stale attrs
                         * make way for the new one
@@ -747,10 +744,10 @@ static ssize_t
 yod_getdirentries(struct inode *ino,
                     char *buf,
                     size_t nbytes,
-                    off64_t *basep)
+                    _SYSIO_OFF_T *basep)
 {
        struct yod_inode *nino = I2NI(ino);
-       loff_t  result;
+       _SYSIO_OFF_T result;
        ssize_t cc;
 
        assert(nino->ni_fd >= 0);
@@ -762,10 +759,11 @@ yod_getdirentries(struct inode *ino,
                                SEEK_SET) == -1))
                return -errno;
        nino->ni_fpos = result;
+       memset(buf, 0, nbytes);
        cc = getdirentries_yod(nino->ni_fd, buf, nbytes, &result);
        if (cc < 0)
                return -errno;
-       nino->ni_fpos += cc;
+       nino->ni_fpos = *basep = result;
        return cc;
 }
 
index 9431734..e6d9843 100644 (file)
@@ -135,9 +135,8 @@ struct inode {
        i_immune                        : 1,            /* immune from GC */
        i_zombie                        : 1;            /* stale inode */
     unsigned i_ref;                                     /* soft ref counter */
-    mode_t  i_mode;                                     /* mode (see stat.h) */
-    dev_t   i_rdev;                                    /* dev (if device) */
     struct inode_ops i_ops;                             /* operations */
+    struct intnl_stat i_stbuf;                         /* attrs */
     struct filesys *i_fs;                               /* file system ptr */
     struct file_identifier *i_fid;                      /* file ident */
     void    *i_private;                                 /* driver data */
@@ -147,14 +146,13 @@ struct inode {
 /*
  * Init an i-node record.
  */
-#define I_INIT(ino, fs, mode, rdev, ops, fid, immunity, private) \
+#define I_INIT(ino, fs, stat, ops, fid, immunity, private) \
     do { \
         (ino)->i_immune = (immunity) ? 1 : 0; \
         (ino)->i_zombie = 0; \
         (ino)->i_ref = 0; \
-        (ino)->i_mode = (mode); \
-        (ino)->i_rdev = (rdev); \
         (ino)->i_ops = *(ops); \
+        (ino)->i_stbuf = *(stat); \
         (ino)->i_fs = (fs); \
         (ino)->i_fid = (fid); \
         (ino)->i_private = (private); \
@@ -423,8 +421,7 @@ extern void _sysio_i_shutdown(void);
 #endif
 extern struct inode *_sysio_i_new(struct filesys *fs,
                                   struct file_identifier *fid,
-                                  mode_t type,
-                                  dev_t rdev,
+                                 struct intnl_stat *stat,
                                  unsigned immunity,
                                   struct inode_ops *ops,
                                   void *private);
@@ -466,6 +463,7 @@ extern int _sysio_path_walk(struct pnode *parent, struct nameidata *nd);
 #ifdef AUTOMOUNT_FILE_NAME
 extern void _sysio_next_component(const char *path, struct qstr *name);
 #endif
+extern int _sysio_permitted(struct inode *ino, int amode);
 extern int _sysio_namei(struct pnode *pno,
                         const char *path,
                         unsigned flags,
@@ -487,30 +485,4 @@ extern void _sysio_ioctx_cb_free(struct ioctx_callback *cb);
 extern struct ioctx *_sysio_ioctx_find(void *id);
 extern ssize_t _sysio_ioctx_wait(struct ioctx *ioctx);
 extern void _sysio_ioctx_complete(struct ioctx *ioctx);
-extern ssize_t _sysio_validx(const struct intnl_xtvec *xtv, size_t xtvlen,
-                            const struct iovec *iov, size_t iovlen,
-                            _SYSIO_OFF_T limit);
-extern ssize_t _sysio_enumerate_extents(const struct intnl_xtvec *xtv,
-                                       size_t xtvlen,
-                                       const struct iovec *iov,
-                                       size_t iovlen,
-                                       ssize_t (*f)(const struct iovec *,
-                                                    int,
-                                                    _SYSIO_OFF_T,
-                                                    ssize_t,
-                                                    void *),
-                                       void *arg);
-extern ssize_t _sysio_enumerate_iovec(const struct iovec *iov,
-                                     size_t count,
-                                     _SYSIO_OFF_T off,
-                                     ssize_t limit,
-                                     ssize_t (*f)(void *,
-                                                  size_t,
-                                                  _SYSIO_OFF_T,
-                                                  void *),
-                                     void *arg);
-extern ssize_t _sysio_doio(const struct intnl_xtvec *xtv, size_t xtvlen,
-                          const struct iovec *iov, size_t iovlen,
-                          ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
-                          void *arg);
 extern int _sysio_open(struct pnode *pno, int flags, mode_t mode);
index ce1c427..b8aa5e4 100644 (file)
@@ -1,4 +1,5 @@
 INCLUDE_EXTRA = include/dev.h include/file.h include/fs.h \
        include/inode.h include/mount.h include/sysio.h \
        include/sysio-symbols.h include/cplant-yod.h \
-       include/module.mk include/xtio.h
+       include/module.mk include/xtio.h include/stddir.h \
+       include/native.h
diff --git a/libsysio/include/native.h b/libsysio/include/native.h
new file mode 100644 (file)
index 0000000..1409817
--- /dev/null
@@ -0,0 +1,243 @@
+/*
+ *    This Cplant(TM) source code is the property of Sandia National
+ *    Laboratories.
+ *
+ *    This Cplant(TM) source code is copyrighted by Sandia National
+ *    Laboratories.
+ *
+ *    The redistribution of this Cplant(TM) source code is subject to the
+ *    terms of the GNU Lesser General Public License
+ *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
+ *
+ *    Cplant(TM) Copyright 1998-2004 Sandia Corporation. 
+ *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
+ *    license for use of this work by or on behalf of the US Government.
+ *    Export of this program may require a license from the United States
+ *    Government.
+ */
+
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ * Questions or comments about this library should be sent to:
+ *
+ * Lee Ward
+ * Sandia National Laboratories, New Mexico
+ * P.O. Box 5800
+ * Albuquerque, NM 87185-1110
+ *
+ * lee@sandia.gov
+ */
+
+/*
+ * Native file system support.
+ */
+
+#if ALPHA_LINUX
+
+/*
+ * stat struct from asm/stat.h, as returned 
+ * by alpha linux kernel
+ */
+struct _sysio_native_stat {
+       unsigned int    st_dev;
+       unsigned int    st_ino;
+       unsigned int    st_mode;
+       unsigned int    st_nlink;
+       unsigned int    st_uid;
+       unsigned int    st_gid;
+       unsigned int    st_rdev;
+       long            st_size;
+       unsigned long   st_atime;
+       unsigned long   st_mtime;
+       unsigned long   st_ctime;
+       unsigned int    st_blksize;
+       int             st_blocks;
+       unsigned int    st_flags;
+       unsigned int    st_gen;
+};
+
+#define SYSIO_COPY_STAT(src, dest)                    \
+do {                                            \
+       memset((dest), 0, sizeof((*dest)));     \
+       (dest)->st_dev     = (src)->st_dev;     \
+       (dest)->st_ino     = (src)->st_ino;     \
+       (dest)->st_mode    = (src)->st_mode;    \
+       (dest)->st_nlink   = (src)->st_nlink;   \
+       (dest)->st_uid     = (src)->st_uid;     \
+       (dest)->st_gid     = (src)->st_gid;     \
+       (dest)->st_rdev    = (src)->st_rdev;    \
+       (dest)->st_size    = (src)->st_size;    \
+       (dest)->st_atime   = (src)->st_atime;   \
+       (dest)->st_mtime   = (src)->st_mtime;   \
+       (dest)->st_ctime   = (src)->st_ctime;   \
+       (dest)->st_blksize = (src)->st_blksize; \
+       (dest)->st_blocks  = (src)->st_blocks;  \
+       (dest)->st_flags   = (src)->st_flags;   \
+       (dest)->st_gen     = (src)->st_gen;     \
+} while (0);
+
+#else 
+#define _sysio_native_stat intnl_stat
+#define SYSIO_COPY_STAT(src, dest) *(dest) = *(src) 
+#endif
+
+/*
+ * System calls.
+ */
+#if _LARGEFILE64_SOURCE && defined(SYS_lstat64)
+#define SYSIO_SYS_stat         SYS_lstat64
+#elif defined(SYS_lstat)
+#define SYSIO_SYS_stat         SYS_lstat
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_fstat64)
+#define SYSIO_SYS_fstat                SYS_fstat64
+#elif defined(SYS_fstat)
+#define SYSIO_SYS_fstat                SYS_fstat
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_truncate64)
+#define SYSIO_SYS_truncate     SYS_truncate64
+#elif defined(SYS_truncate)
+#define SYSIO_SYS_truncate     SYS_truncate
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_ftruncate64)
+#define SYSIO_SYS_ftruncate    SYS_ftruncate64
+#elif defined(SYS_ftruncate)
+#define SYSIO_SYS_ftruncate    SYS_ftruncate
+#endif
+#if defined(SYS_open)
+#define SYSIO_SYS_open         SYS_open
+#endif
+#if defined(SYS_close)
+#define SYSIO_SYS_close                SYS_close
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_lseek64)
+#define SYSIO_SYS_lseek                SYS_lseek64
+#elif defined(SYS_lseek)
+#define SYSIO_SYS_lseek                SYS_lseek
+#endif
+#if defined(SYS__llseek)
+#define SYSIO_SYS__llseek      SYS__llseek
+#endif
+#if defined(SYS_read)
+#define SYSIO_SYS_read         SYS_read
+#endif
+#if defined(SYS_write)
+#define SYSIO_SYS_write                SYS_write
+#endif
+#if defined(SYS_readv)
+#define SYSIO_SYS_readv                SYS_readv
+#endif
+#if defined(SYS_writev)
+#define SYSIO_SYS_writev       SYS_writev
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_pread64)
+#define SYSIO_SYS_pread                SYS_pread64
+#elif defined(SYS_pread)
+#define SYSIO_SYS_pread                SYS_pread
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_pwrite64)
+#define SYSIO_SYS_pwrite       SYS_pwrite64
+#elif defined(SYS_pwrite)
+#define SYSIO_SYS_pwrite       SYS_pwrite
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_fcntl64)
+#define SYSIO_SYS_fcntl                SYS_fcntl64
+#elif defined(SYS_fcntl)
+#define SYSIO_SYS_fcntl                SYS_fcntl
+#endif
+#if defined(SYS_fsync)
+#define SYSIO_SYS_fsync                SYS_fsync
+#endif
+#if ALPHA_LINUX && defined(SYS_osf_fdatasync)
+#define SYSIO_SYS_fdatasync    SYS_osf_fdatasync
+#elif defined(SYS_fdatasync)
+#define SYSIO_SYS_fdatasync    SYS_fdatasync
+#endif
+#if defined(SYS_chmod)
+#define SYSIO_SYS_chmod                SYS_chmod
+#endif
+#if defined(SYS_fchmod)
+#define SYSIO_SYS_fchmod       SYS_fchmod
+#endif
+#if defined(SYS_chown)
+#define SYSIO_SYS_chown                SYS_chown
+#endif
+#if defined(SYS_fchown)
+#define SYSIO_SYS_fchown       SYS_fchown
+#endif
+#if defined(SYS_umask)
+#define SYSIO_SYS_umask                SYS_umask
+#endif
+#if defined(SYS_mkdir)
+#define SYSIO_SYS_mkdir                SYS_mkdir
+#endif
+#if defined(SYS_rmdir)
+#define SYSIO_SYS_rmdir                SYS_rmdir
+#endif
+#if defined(SYS_getdirentries)
+#if _LARGEFILE64_SOURCE && defined(SYS_getdirentries64)
+#define SYSIO_SYS_getdirentries        SYS_getdirentries64
+#elif defined(SYS_getdirentries)
+#define SYSIO_SYS_getdirentries        SYS_getdirentries
+#endif
+#endif
+#if _LARGEFILE64_SOURCE && defined(SYS_getdents64)
+#define SYSIO_SYS_getdents64   SYS_getdents64
+#elif defined(SYS_getdents)
+#define SYSIO_SYS_getdents     SYS_getdents
+#endif
+#if defined(SYS_link)
+#define SYSIO_SYS_link         SYS_link
+#endif
+#if defined(SYS_unlink)
+#define SYSIO_SYS_unlink       SYS_unlink
+#endif
+#if defined(SYS_symlink)
+#define SYSIO_SYS_symlink      SYS_symlink
+#endif
+#if defined(SYS_rename)
+#define SYSIO_SYS_rename       SYS_rename
+#endif
+#if defined(SYS_readlink)
+#define SYSIO_SYS_readlink     SYS_readlink
+#endif
+#if defined(SYS_utimes)
+#define SYSIO_SYS_utimes       SYS_utimes
+#endif
+#if defined(SYS_utime)
+#define SYSIO_SYS_utime                SYS_utime
+#endif
+#if defined(SYS_socketcall)
+#define SYSIO_SYS_socketcall   SYS_socketcall
+#endif
+#if defined(SYS_socket)
+#define SYSIO_SYS_socket       SYS_socket
+#endif
+#if defined(SYS_accept)
+#define SYSIO_SYS_accept       SYS_accept
+#endif
+#if defined(SYS_bind)
+#define SYSIO_SYS_bind         SYS_bind
+#endif
+#if defined(SYS_listen)
+#define SYSIO_SYS_listen       SYS_listen
+#endif
+#if defined(SYS_connect)
+#define SYSIO_SYS_connect      SYS_connect
+#endif
+#if defined(SYS_ioctl)
+#define SYSIO_SYS_ioctl                SYS_ioctl
+#endif
diff --git a/libsysio/include/stddir.h b/libsysio/include/stddir.h
new file mode 100644 (file)
index 0000000..ff830c7
--- /dev/null
@@ -0,0 +1,67 @@
+/*
+ *    This Cplant(TM) source code is the property of Sandia National
+ *    Laboratories.
+ *
+ *    This Cplant(TM) source code is copyrighted by Sandia National
+ *    Laboratories.
+ *
+ *    The redistribution of this Cplant(TM) source code is subject to the
+ *    terms of the GNU Lesser General Public License
+ *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
+ *
+ *    Cplant(TM) Copyright 1998-2004 Sandia Corporation. 
+ *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
+ *    license for use of this work by or on behalf of the US Government.
+ *    Export of this program may require a license from the United States
+ *    Government.
+ */
+
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ * Questions or comments about this library should be sent to:
+ *
+ * Lee Ward
+ * Sandia National Laboratories, New Mexico
+ * P.O. Box 5800
+ * Albuquerque, NM 87185-1110
+ *
+ * lee@sandia.gov
+ */
+
+/*
+ * Support for directory functions
+ */
+
+#ifndef _STDDIR_H_
+#define _STDDIR_H_
+
+#undef  BUFSIZE
+#define BUFSIZE        4096
+
+struct __dirstream {
+       int             fd;
+       _SYSIO_OFF_T    base;           /* start pos for next system call */
+       _SYSIO_OFF_T    filepos;        /* current pos in dir file stream */
+       size_t          cur;            /* current byte pos in data buffer */
+       size_t          effective;      /* effective data size in buffer */
+       char            buf[BUFSIZE];
+};
+
+#ifndef MAX
+#define MAX(a,b) (a) > (b) ? (a) : (b)
+#endif
+
+#endif /* ! _STDDIR_H_ */
diff --git a/libsysio/include/sysio-cmn.h b/libsysio/include/sysio-cmn.h
new file mode 100644 (file)
index 0000000..830f187
--- /dev/null
@@ -0,0 +1,209 @@
+/*
+ *    This Cplant(TM) source code is the property of Sandia National
+ *    Laboratories.
+ *
+ *    This Cplant(TM) source code is copyrighted by Sandia National
+ *    Laboratories.
+ *
+ *    The redistribution of this Cplant(TM) source code is subject to the
+ *    terms of the GNU Lesser General Public License
+ *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
+ *
+ *    Cplant(TM) Copyright 1998-2004 Sandia Corporation. 
+ *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
+ *    license for use of this work by or on behalf of the US Government.
+ *    Export of this program may require a license from the United States
+ *    Government.
+ */
+
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ * Questions or comments about this library should be sent to:
+ *
+ * Lee Ward
+ * Sandia National Laboratories, New Mexico
+ * P.O. Box 5800
+ * Albuquerque, NM 87185-1110
+ *
+ * lee@sandia.gov
+ */
+
+/*
+ * System IO common information.
+ */
+
+#if !defined(__IS_UNUSED) && defined(__GNUC__)
+#define __IS_UNUSED    __attribute__ ((unused))
+#else
+#define __IS_UNUSED
+#endif
+
+#ifndef _LARGEFILE64_SOURCE
+/*
+ * Not glibc I guess. Define this ourselves.
+ */
+#define _LARGEFILE64_SOURCE            0
+#endif
+
+/*
+ * Define internal file-offset type and it's maximum value.
+ */
+#if _LARGEFILE64_SOURCE
+#define _SYSIO_OFF_T                   off64_t
+#ifdef LLONG_MAX
+#define _SYSIO_OFF_T_MAX               (LLONG_MAX)
+#else
+/*
+ * Don't have LLONG_MAX before C99. We'll need to define it ourselves.
+ */
+#define _SYSIO_OFF_T_MAX               (9223372036854775807LL)
+#endif
+#else
+#define _SYSIO_OFF_T                   off_t
+#define _SYSIO_OFF_T_MAX               LONG_MAX
+#endif
+
+/*
+ * Internally, all file status is carried in the 64-bit capable
+ * structure.
+ */
+#if _LARGEFILE64_SOURCE
+#define intnl_xtvec xtvec64
+#else
+#define intnl_xtvec xtvec
+#endif
+struct intnl_xtvec;
+
+struct iovec;
+
+/*
+ * SYSIO name label macros
+ */
+#define XPREPEND(p,x) p ## x
+#define PREPEND(p,x) XPREPEND(p,x)
+#define SYSIO_LABEL_NAMES 0
+#if SYSIO_LABEL_NAMES
+#define SYSIO_INTERFACE_NAME(x) PREPEND(sysio__, x)
+#else
+#define SYSIO_INTERFACE_NAME(x) x
+#endif
+
+/* for debugging */
+#if 0
+#define ASSERT(cond)                                                   \
+       if (!(cond)) {                                                  \
+               printf("ASSERTION(" #cond ") failed: " __FILE__ ":"     \
+                       __FUNCTION__ ":%d\n", __LINE__);                \
+               abort();                                                \
+       }
+
+#define ERROR(fmt, a...)                                               \
+       do {                                                            \
+               printf("ERROR(" __FILE__ ":%d):" fmt, __LINE__, ##a);   \
+       while(0)
+
+#else
+#define ERROR(fmt)     do{}while(0)
+#define ASSERT         do{}while(0)
+#endif
+
+/*
+ * SYSIO interface frame macros
+ *
+ * + DISPLAY_BLOCK; Allocates storage on the stack for use by the set of
+ *     macros.
+ * + ENTER; Performs entry point work
+ * + RETURN; Returns a value and performs exit point work
+ *
+ * NB: For RETURN, the arguments are the return value and value for errno.
+ * If the value for errno is non-zero then that value, *negated*, is set
+ * into errno.
+ */
+#define SYSIO_INTERFACE_DISPLAY_BLOCK \
+       int _saved_errno;
+#define SYSIO_INTERFACE_ENTER \
+       do { \
+               _saved_errno = errno; \
+               SYSIO_ENTER; \
+       } while (0)
+#define SYSIO_INTERFACE_RETURN(rtn, err) \
+       do { \
+               SYSIO_LEAVE; \
+               errno = (err) ? -(err) : _saved_errno; \
+               return (rtn); \
+       } while(0) 
+
+/* Interface enter/leave hook functions  */
+#if 0
+extern void _sysio_sysenter();
+extern void _sysio_sysleave();
+
+#define SYSIO_ENTER                                                    \
+       do {                                                            \
+               _sysio_sysenter();                                      \
+       } while(0)
+
+#define SYSIO_LEAVE                                                    \
+       do {                                                            \
+               _sysio_sysleave();                                      \
+       } while(0)
+#else
+#define SYSIO_ENTER
+#define SYSIO_LEAVE
+
+#endif
+
+/* accounting for IO stats read and write char count */
+#if defined(REDSTORM)
+#define _SYSIO_UPDACCT(w, cc) \
+       do { \
+               if ((cc) < 0) \
+                       break; \
+               if (!w) \
+                       _add_iostats(0, (size_t )(cc)); \
+               else \
+                       _add_iostats((size_t )(cc), 0); \
+       } while(0)
+#else
+#define _SYSIO_UPDACCT(w, cc)
+#endif
+
+extern ssize_t _sysio_validx(const struct intnl_xtvec *xtv, size_t xtvlen,
+                            const struct iovec *iov, size_t iovlen,
+                            _SYSIO_OFF_T limit);
+extern ssize_t _sysio_enumerate_extents(const struct intnl_xtvec *xtv,
+                                       size_t xtvlen,
+                                       const struct iovec *iov,
+                                       size_t iovlen,
+                                       ssize_t (*f)(const struct iovec *,
+                                                    int,
+                                                    _SYSIO_OFF_T,
+                                                    ssize_t,
+                                                    void *),
+                                       void *arg);
+extern ssize_t _sysio_enumerate_iovec(const struct iovec *iov,
+                                     size_t count,
+                                     _SYSIO_OFF_T off,
+                                     ssize_t limit,
+                                     ssize_t (*f)(void *,
+                                                  size_t,
+                                                  _SYSIO_OFF_T,
+                                                  void *),
+                                     void *arg);
+extern ssize_t _sysio_doio(const struct intnl_xtvec *xtv, size_t xtvlen,
+                          const struct iovec *iov, size_t iovlen,
+                          ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
+                          void *arg);
index bd31365..c6139d7 100644 (file)
 #include <limits.h>
 #include <stdarg.h>
 
-#if !defined(__IS_UNUSED) && defined(__GNUC__)
-#define __IS_UNUSED    __attribute__ ((unused))
-#else
-#define __IS_UNUSED
-#endif
+#include "sysio-cmn.h"
 
 #ifndef PATH_SEPARATOR
 /*
 #define MAX_SYMLINK                    250
 #endif
 
-#ifndef _LARGEFILE64_SOURCE
-/*
- * Not glibc I guess. Define this ourselves.
- */
-#define _LARGEFILE64_SOURCE            0
-#endif
-
-/*
- * Define internal file-offset type and it's maximum value.
- */
-#if _LARGEFILE64_SOURCE
-#define _SYSIO_OFF_T                   off64_t
-#ifdef LLONG_MAX
-#define _SYSIO_OFF_T_MAX               (LLONG_MAX)
-#else
-/*
- * Don't have LLONG_MAX before C99. We'll need to define it ourselves.
- */
-#define _SYSIO_OFF_T_MAX               (9223372036854775807LL)
-#endif
-#else
-#define _SYSIO_OFF_T                   off_t
-#define _SYSIO_OFF_T_MAX               LONG_MAX
-#endif
-
 /*
  * Internally, all directory entries are carried in the 64-bit capable
  * structure.
@@ -126,44 +97,46 @@ struct statvfs;
 struct intnl_statvfs;
 #endif
 
-/*
- * Internally, all file status is carried in the 64-bit capable
- * structure.
- */
-#if _LARGEFILE64_SOURCE
-#define intnl_xtvec xtvec64
-#else
-#define intnl_xtvec xtvec
-#endif
-struct intnl_xtvec;
-
-struct iovec;
-
 struct utimbuf;
 
 struct intnl_stat;
 
 struct pnode;
 
+#if DEFER_INIT_CWD
+extern const char *_sysio_init_cwd;
+#endif
+
 extern struct pnode *_sysio_cwd;
 
 extern mode_t _sysio_umask;
 
 extern int _sysio_init(void);
 extern void _sysio_shutdown(void);
+#if DEFER_INIT_CWD
+extern int _sysio_boot(const char *buf, const char *path);
+#else
 extern int _sysio_boot(const char *buf);
+#endif
 
 /*
- * SYSIO name label macros
+ * Option-value pair information.
  */
-#define XPREPEND(p,x) p ## x
-#define PREPEND(p,x) XPREPEND(p,x)
-#define SYSIO_LABEL_NAMES 0
-#if SYSIO_LABEL_NAMES
-#define SYSIO_INTERFACE_NAME(x) PREPEND(sysio__, x)
-#else
-#define SYSIO_INTERFACE_NAME(x) x
-#endif
+struct option_value_info {
+       const char *ovi_name;                                   /* name */
+       char *ovi_value;                                        /* value */
+};
+
+extern const char * _sysio_get_token(const char *buf,
+                                    int accepts,
+                                    const char *delim,
+                                    const char *ignore,
+                                    char *tbuf);
+extern char * _sysio_get_args(char *buf, struct option_value_info *vec);
+
+#define _SYSIO_LOCAL_TIME()    _sysio_local_time()
+
+extern time_t _sysio_local_time(void);
 
 /*
  * The following should be defined by the system includes, and probably are,
@@ -256,83 +229,3 @@ extern int SYSIO_INTERFACE_NAME(mount)(const char *source, const char *target,
                                       unsigned long mountflags,
                                       const void *data);
 extern int SYSIO_INTERFACE_NAME(umount)(const char *target);
-
-/* for debugging */
-#if 0
-#define ASSERT(cond)                                                   \
-       if (!(cond)) {                                                  \
-               printf("ASSERTION(" #cond ") failed: " __FILE__ ":"     \
-                       __FUNCTION__ ":%d\n", __LINE__);                \
-               abort();                                                \
-       }
-
-#define ERROR(fmt, a...)                                               \
-       do {                                                            \
-               printf("ERROR(" __FILE__ ":%d):" fmt, __LINE__, ##a);   \
-       while(0)
-
-#else
-#define ERROR(fmt)     do{}while(0)
-#define ASSERT         do{}while(0)
-#endif
-
-/*
- * SYSIO interface frame macros
- *
- * + DISPLAY_BLOCK; Allocates storage on the stack for use by the set of
- *     macros.
- * + ENTER; Performs entry point work
- * + RETURN; Returns a value and performs exit point work
- *
- * NB: For RETURN, the arguments are the return value and value for errno.
- * If the value for errno is non-zero then that value, *negated*, is set
- * into errno.
- */
-#define SYSIO_INTERFACE_DISPLAY_BLOCK \
-       int _saved_errno;
-#define SYSIO_INTERFACE_ENTER \
-       do { \
-               _saved_errno = errno; \
-               SYSIO_ENTER; \
-       } while (0)
-#define SYSIO_INTERFACE_RETURN(rtn, err) \
-       do { \
-               SYSIO_LEAVE; \
-               errno = (err) ? -(err) : _saved_errno; \
-               return (rtn); \
-       } while(0) 
-
-/* syscall enter/leave hook functions  */
-#if 0
-extern void _sysio_sysenter();
-extern void _sysio_sysleave();
-
-#define SYSIO_ENTER                                                    \
-       do {                                                            \
-               _sysio_sysenter();                                      \
-       } while(0)
-
-#define SYSIO_LEAVE                                                    \
-       do {                                                            \
-               _sysio_sysleave();                                      \
-       } while(0)
-#else
-#define SYSIO_ENTER
-#define SYSIO_LEAVE
-
-#endif
-
-/* accounting for IO stats read and write char count */
-#if defined(REDSTORM)
-#define _SYSIO_UPDACCT(w, cc) \
-       do { \
-               if ((cc) < 0) \
-                       break; \
-               if (!w) \
-                       _add_iostats(0, (size_t )(cc)); \
-               else \
-                       _add_iostats((size_t )(cc), 0); \
-       } while(0)
-#else
-#define _SYSIO_UPDACCT(w, cc)
-#endif
diff --git a/libsysio/install-sh b/libsysio/install-sh
new file mode 100755 (executable)
index 0000000..6ce63b9
--- /dev/null
@@ -0,0 +1,294 @@
+#!/bin/sh
+#
+# install - install a program, script, or datafile
+#
+# This originates from X11R5 (mit/util/scripts/install.sh), which was
+# later released in X11R6 (xc/config/util/install.sh) with the
+# following copyright and license.
+#
+# Copyright (C) 1994 X Consortium
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to
+# deal in the Software without restriction, including without limitation the
+# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+# sell copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
+# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
+# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+# Except as contained in this notice, the name of the X Consortium shall not
+# be used in advertising or otherwise to promote the sale, use or other deal-
+# ings in this Software without prior written authorization from the X Consor-
+# tium.
+#
+#
+# FSF changes to this file are in the public domain.
+#
+# Calling this script install-sh is preferred over install.sh, to prevent
+# `make' implicit rules from creating a file called install from it
+# when there is no Makefile.
+#
+# This script is compatible with the BSD install script, but was written
+# from scratch.  It can only install one file at a time, a restriction
+# shared with many OS's install programs.
+
+
+# set DOITPROG to echo to test this script
+
+# Don't use :- since 4.3BSD and earlier shells don't like it.
+doit="${DOITPROG-}"
+
+
+# put in absolute paths if you don't have them in your path; or use env. vars.
+
+mvprog="${MVPROG-mv}"
+cpprog="${CPPROG-cp}"
+chmodprog="${CHMODPROG-chmod}"
+chownprog="${CHOWNPROG-chown}"
+chgrpprog="${CHGRPPROG-chgrp}"
+stripprog="${STRIPPROG-strip}"
+rmprog="${RMPROG-rm}"
+mkdirprog="${MKDIRPROG-mkdir}"
+
+transformbasename=""
+transform_arg=""
+instcmd="$mvprog"
+chmodcmd="$chmodprog 0755"
+chowncmd=""
+chgrpcmd=""
+stripcmd=""
+rmcmd="$rmprog -f"
+mvcmd="$mvprog"
+src=""
+dst=""
+dir_arg=""
+
+while [ x"$1" != x ]; do
+    case $1 in
+       -c) instcmd=$cpprog
+           shift
+           continue;;
+
+       -d) dir_arg=true
+           shift
+           continue;;
+
+       -m) chmodcmd="$chmodprog $2"
+           shift
+           shift
+           continue;;
+
+       -o) chowncmd="$chownprog $2"
+           shift
+           shift
+           continue;;
+
+       -g) chgrpcmd="$chgrpprog $2"
+           shift
+           shift
+           continue;;
+
+       -s) stripcmd=$stripprog
+           shift
+           continue;;
+
+       -t=*) transformarg=`echo $1 | sed 's/-t=//'`
+           shift
+           continue;;
+
+       -b=*) transformbasename=`echo $1 | sed 's/-b=//'`
+           shift
+           continue;;
+
+       *)  if [ x"$src" = x ]
+           then
+               src=$1
+           else
+               # this colon is to work around a 386BSD /bin/sh bug
+               :
+               dst=$1
+           fi
+           shift
+           continue;;
+    esac
+done
+
+if [ x"$src" = x ]
+then
+       echo "$0: no input file specified" >&2
+       exit 1
+else
+       :
+fi
+
+if [ x"$dir_arg" != x ]; then
+       dst=$src
+       src=""
+
+       if [ -d "$dst" ]; then
+               instcmd=:
+               chmodcmd=""
+       else
+               instcmd=$mkdirprog
+       fi
+else
+
+# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
+# might cause directories to be created, which would be especially bad
+# if $src (and thus $dsttmp) contains '*'.
+
+       if [ -f "$src" ] || [ -d "$src" ]
+       then
+               :
+       else
+               echo "$0: $src does not exist" >&2
+               exit 1
+       fi
+
+       if [ x"$dst" = x ]
+       then
+               echo "$0: no destination specified" >&2
+               exit 1
+       else
+               :
+       fi
+
+# If destination is a directory, append the input filename; if your system
+# does not like double slashes in filenames, you may need to add some logic
+
+       if [ -d "$dst" ]
+       then
+               dst=$dst/`basename "$src"`
+       else
+               :
+       fi
+fi
+
+## this sed command emulates the dirname command
+dstdir=`echo "$dst" | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
+
+# Make sure that the destination directory exists.
+#  this part is taken from Noah Friedman's mkinstalldirs script
+
+# Skip lots of stat calls in the usual case.
+if [ ! -d "$dstdir" ]; then
+defaultIFS='
+       '
+IFS="${IFS-$defaultIFS}"
+
+oIFS=$IFS
+# Some sh's can't handle IFS=/ for some reason.
+IFS='%'
+set - `echo "$dstdir" | sed -e 's@/@%@g' -e 's@^%@/@'`
+IFS=$oIFS
+
+pathcomp=''
+
+while [ $# -ne 0 ] ; do
+       pathcomp=$pathcomp$1
+       shift
+
+       if [ ! -d "$pathcomp" ] ;
+        then
+               $mkdirprog "$pathcomp"
+       else
+               :
+       fi
+
+       pathcomp=$pathcomp/
+done
+fi
+
+if [ x"$dir_arg" != x ]
+then
+       $doit $instcmd "$dst" &&
+
+       if [ x"$chowncmd" != x ]; then $doit $chowncmd "$dst"; else : ; fi &&
+       if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd "$dst"; else : ; fi &&
+       if [ x"$stripcmd" != x ]; then $doit $stripcmd "$dst"; else : ; fi &&
+       if [ x"$chmodcmd" != x ]; then $doit $chmodcmd "$dst"; else : ; fi
+else
+
+# If we're going to rename the final executable, determine the name now.
+
+       if [ x"$transformarg" = x ]
+       then
+               dstfile=`basename "$dst"`
+       else
+               dstfile=`basename "$dst" $transformbasename |
+                       sed $transformarg`$transformbasename
+       fi
+
+# don't allow the sed command to completely eliminate the filename
+
+       if [ x"$dstfile" = x ]
+       then
+               dstfile=`basename "$dst"`
+       else
+               :
+       fi
+
+# Make a couple of temp file names in the proper directory.
+
+       dsttmp=$dstdir/_inst.$$_
+       rmtmp=$dstdir/_rm.$$_
+
+# Trap to clean up temp files at exit.
+
+       trap 'status=$?; rm -f "$dsttmp" "$rmtmp" && exit $status' 0
+       trap '(exit $?); exit' 1 2 13 15
+
+# Move or copy the file name to the temp name
+
+       $doit $instcmd "$src" "$dsttmp" &&
+
+# and set any options; do chmod last to preserve setuid bits
+
+# If any of these fail, we abort the whole thing.  If we want to
+# ignore errors from any of these, just make sure not to ignore
+# errors from the above "$doit $instcmd $src $dsttmp" command.
+
+       if [ x"$chowncmd" != x ]; then $doit $chowncmd "$dsttmp"; else :;fi &&
+       if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd "$dsttmp"; else :;fi &&
+       if [ x"$stripcmd" != x ]; then $doit $stripcmd "$dsttmp"; else :;fi &&
+       if [ x"$chmodcmd" != x ]; then $doit $chmodcmd "$dsttmp"; else :;fi &&
+
+# Now remove or move aside any old file at destination location.  We try this
+# two ways since rm can't unlink itself on some systems and the destination
+# file might be busy for other reasons.  In this case, the final cleanup
+# might fail but the new file should still install successfully.
+
+{
+       if [ -f "$dstdir/$dstfile" ]
+       then
+               $doit $rmcmd -f "$dstdir/$dstfile" 2>/dev/null ||
+               $doit $mvcmd -f "$dstdir/$dstfile" "$rmtmp" 2>/dev/null ||
+               {
+                 echo "$0: cannot unlink or rename $dstdir/$dstfile" >&2
+                 (exit 1); exit
+               }
+       else
+               :
+       fi
+} &&
+
+# Now rename the file to the real destination.
+
+       $doit $mvcmd "$dsttmp" "$dstdir/$dstfile"
+
+fi &&
+
+# The final little trick to "correctly" pass the exit status to the exit trap.
+
+{
+       (exit 0); exit
+}
index 3e9861e..ea1c0ec 100644 (file)
@@ -34,7 +34,6 @@ export SYSIO_NAMESPACE="\
        {open,  nm=\"/dev/fd/1\",fd=1,m=1} \
        {creat, ft=chr,nm=\"/dev/fd/2\",pm=0200,mm=0+2} \
        {open,  nm=\"/dev/fd/2\",fd=2,m=1} \
-       {cd,    dir=\"$HOME\"} \
        ${_extras} \
 "
 unset _root_flags
diff --git a/libsysio/missing b/libsysio/missing
new file mode 100755 (executable)
index 0000000..6a37006
--- /dev/null
@@ -0,0 +1,336 @@
+#! /bin/sh
+# Common stub for a few missing GNU programs while installing.
+# Copyright (C) 1996, 1997, 1999, 2000, 2002 Free Software Foundation, Inc.
+# Originally by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
+
+# 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., 59 Temple Place - Suite 330, Boston, MA
+# 02111-1307, USA.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+if test $# -eq 0; then
+  echo 1>&2 "Try \`$0 --help' for more information"
+  exit 1
+fi
+
+run=:
+
+# In the cases where this matters, `missing' is being run in the
+# srcdir already.
+if test -f configure.ac; then
+  configure_ac=configure.ac
+else
+  configure_ac=configure.in
+fi
+
+case "$1" in
+--run)
+  # Try to run requested program, and just exit if it succeeds.
+  run=
+  shift
+  "$@" && exit 0
+  ;;
+esac
+
+# If it does not exist, or fails to run (possibly an outdated version),
+# try to emulate it.
+case "$1" in
+
+  -h|--h|--he|--hel|--help)
+    echo "\
+$0 [OPTION]... PROGRAM [ARGUMENT]...
+
+Handle \`PROGRAM [ARGUMENT]...' for when PROGRAM is missing, or return an
+error status if there is no known handling for PROGRAM.
+
+Options:
+  -h, --help      display this help and exit
+  -v, --version   output version information and exit
+  --run           try to run the given command, and emulate it if it fails
+
+Supported PROGRAM values:
+  aclocal      touch file \`aclocal.m4'
+  autoconf     touch file \`configure'
+  autoheader   touch file \`config.h.in'
+  automake     touch all \`Makefile.in' files
+  bison        create \`y.tab.[ch]', if possible, from existing .[ch]
+  flex         create \`lex.yy.c', if possible, from existing .c
+  help2man     touch the output file
+  lex          create \`lex.yy.c', if possible, from existing .c
+  makeinfo     touch the output file
+  tar          try tar, gnutar, gtar, then tar without non-portable flags
+  yacc         create \`y.tab.[ch]', if possible, from existing .[ch]"
+    ;;
+
+  -v|--v|--ve|--ver|--vers|--versi|--versio|--version)
+    echo "missing 0.4 - GNU automake"
+    ;;
+
+  -*)
+    echo 1>&2 "$0: Unknown \`$1' option"
+    echo 1>&2 "Try \`$0 --help' for more information"
+    exit 1
+    ;;
+
+  aclocal*)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified \`acinclude.m4' or \`${configure_ac}'.  You might want
+         to install the \`Automake' and \`Perl' packages.  Grab them from
+         any GNU archive site."
+    touch aclocal.m4
+    ;;
+
+  autoconf)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified \`${configure_ac}'.  You might want to install the
+         \`Autoconf' and \`GNU m4' packages.  Grab them from any GNU
+         archive site."
+    touch configure
+    ;;
+
+  autoheader)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified \`acconfig.h' or \`${configure_ac}'.  You might want
+         to install the \`Autoconf' and \`GNU m4' packages.  Grab them
+         from any GNU archive site."
+    files=`sed -n 's/^[ ]*A[CM]_CONFIG_HEADER(\([^)]*\)).*/\1/p' ${configure_ac}`
+    test -z "$files" && files="config.h"
+    touch_files=
+    for f in $files; do
+      case "$f" in
+      *:*) touch_files="$touch_files "`echo "$f" |
+                                      sed -e 's/^[^:]*://' -e 's/:.*//'`;;
+      *) touch_files="$touch_files $f.in";;
+      esac
+    done
+    touch $touch_files
+    ;;
+
+  automake*)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified \`Makefile.am', \`acinclude.m4' or \`${configure_ac}'.
+         You might want to install the \`Automake' and \`Perl' packages.
+         Grab them from any GNU archive site."
+    find . -type f -name Makefile.am -print |
+          sed 's/\.am$/.in/' |
+          while read f; do touch "$f"; done
+    ;;
+
+  autom4te)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is needed, and you do not seem to have it handy on your
+         system.  You might have modified some files without having the
+         proper tools for further handling them.
+         You can get \`$1Help2man' as part of \`Autoconf' from any GNU
+         archive site."
+
+    file=`echo "$*" | sed -n 's/.*--output[ =]*\([^ ]*\).*/\1/p'`
+    test -z "$file" && file=`echo "$*" | sed -n 's/.*-o[ ]*\([^ ]*\).*/\1/p'`
+    if test -f "$file"; then
+       touch $file
+    else
+       test -z "$file" || exec >$file
+       echo "#! /bin/sh"
+       echo "# Created by GNU Automake missing as a replacement of"
+       echo "#  $ $@"
+       echo "exit 0"
+       chmod +x $file
+       exit 1
+    fi
+    ;;
+
+  bison|yacc)
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified a \`.y' file.  You may need the \`Bison' package
+         in order for those modifications to take effect.  You can get
+         \`Bison' from any GNU archive site."
+    rm -f y.tab.c y.tab.h
+    if [ $# -ne 1 ]; then
+        eval LASTARG="\${$#}"
+       case "$LASTARG" in
+       *.y)
+           SRCFILE=`echo "$LASTARG" | sed 's/y$/c/'`
+           if [ -f "$SRCFILE" ]; then
+                cp "$SRCFILE" y.tab.c
+           fi
+           SRCFILE=`echo "$LASTARG" | sed 's/y$/h/'`
+           if [ -f "$SRCFILE" ]; then
+                cp "$SRCFILE" y.tab.h
+           fi
+         ;;
+       esac
+    fi
+    if [ ! -f y.tab.h ]; then
+       echo >y.tab.h
+    fi
+    if [ ! -f y.tab.c ]; then
+       echo 'main() { return 0; }' >y.tab.c
+    fi
+    ;;
+
+  lex|flex)
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified a \`.l' file.  You may need the \`Flex' package
+         in order for those modifications to take effect.  You can get
+         \`Flex' from any GNU archive site."
+    rm -f lex.yy.c
+    if [ $# -ne 1 ]; then
+        eval LASTARG="\${$#}"
+       case "$LASTARG" in
+       *.l)
+           SRCFILE=`echo "$LASTARG" | sed 's/l$/c/'`
+           if [ -f "$SRCFILE" ]; then
+                cp "$SRCFILE" lex.yy.c
+           fi
+         ;;
+       esac
+    fi
+    if [ ! -f lex.yy.c ]; then
+       echo 'main() { return 0; }' >lex.yy.c
+    fi
+    ;;
+
+  help2man)
+    if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
+       # We have it, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+        you modified a dependency of a manual page.  You may need the
+        \`Help2man' package in order for those modifications to take
+        effect.  You can get \`Help2man' from any GNU archive site."
+
+    file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'`
+    if test -z "$file"; then
+       file=`echo "$*" | sed -n 's/.*--output=\([^ ]*\).*/\1/p'`
+    fi
+    if [ -f "$file" ]; then
+       touch $file
+    else
+       test -z "$file" || exec >$file
+       echo ".ab help2man is required to generate this page"
+       exit 1
+    fi
+    ;;
+
+  makeinfo)
+    if test -z "$run" && (makeinfo --version) > /dev/null 2>&1; then
+       # We have makeinfo, but it failed.
+       exit 1
+    fi
+
+    echo 1>&2 "\
+WARNING: \`$1' is missing on your system.  You should only need it if
+         you modified a \`.texi' or \`.texinfo' file, or any other file
+         indirectly affecting the aspect of the manual.  The spurious
+         call might also be the consequence of using a buggy \`make' (AIX,
+         DU, IRIX).  You might want to install the \`Texinfo' package or
+         the \`GNU make' package.  Grab either from any GNU archive site."
+    file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'`
+    if test -z "$file"; then
+      file=`echo "$*" | sed 's/.* \([^ ]*\) *$/\1/'`
+      file=`sed -n '/^@setfilename/ { s/.* \([^ ]*\) *$/\1/; p; q; }' $file`
+    fi
+    touch $file
+    ;;
+
+  tar)
+    shift
+    if test -n "$run"; then
+      echo 1>&2 "ERROR: \`tar' requires --run"
+      exit 1
+    fi
+
+    # We have already tried tar in the generic part.
+    # Look for gnutar/gtar before invocation to avoid ugly error
+    # messages.
+    if (gnutar --version > /dev/null 2>&1); then
+       gnutar "$@" && exit 0
+    fi
+    if (gtar --version > /dev/null 2>&1); then
+       gtar "$@" && exit 0
+    fi
+    firstarg="$1"
+    if shift; then
+       case "$firstarg" in
+       *o*)
+           firstarg=`echo "$firstarg" | sed s/o//`
+           tar "$firstarg" "$@" && exit 0
+           ;;
+       esac
+       case "$firstarg" in
+       *h*)
+           firstarg=`echo "$firstarg" | sed s/h//`
+           tar "$firstarg" "$@" && exit 0
+           ;;
+       esac
+    fi
+
+    echo 1>&2 "\
+WARNING: I can't seem to be able to run \`tar' with the given arguments.
+         You may want to install GNU tar or Free paxutils, or check the
+         command line arguments."
+    exit 1
+    ;;
+
+  *)
+    echo 1>&2 "\
+WARNING: \`$1' is needed, and you do not seem to have it handy on your
+         system.  You might have modified some files without having the
+         proper tools for further handling them.  Check the \`README' file,
+         it often tells you about the needed prerequirements for installing
+         this package.  You may also peek at any GNU archive site, in case
+         some other package would contain this missing \`$1' program."
+    exit 1
+    ;;
+esac
+
+exit 0
diff --git a/libsysio/mkinstalldirs b/libsysio/mkinstalldirs
new file mode 100755 (executable)
index 0000000..d2d5f21
--- /dev/null
@@ -0,0 +1,111 @@
+#! /bin/sh
+# mkinstalldirs --- make directory hierarchy
+# Author: Noah Friedman <friedman@prep.ai.mit.edu>
+# Created: 1993-05-16
+# Public domain
+
+errstatus=0
+dirmode=""
+
+usage="\
+Usage: mkinstalldirs [-h] [--help] [-m mode] dir ..."
+
+# process command line arguments
+while test $# -gt 0 ; do
+  case $1 in
+    -h | --help | --h*)         # -h for help
+      echo "$usage" 1>&2
+      exit 0
+      ;;
+    -m)                         # -m PERM arg
+      shift
+      test $# -eq 0 && { echo "$usage" 1>&2; exit 1; }
+      dirmode=$1
+      shift
+      ;;
+    --)                         # stop option processing
+      shift
+      break
+      ;;
+    -*)                         # unknown option
+      echo "$usage" 1>&2
+      exit 1
+      ;;
+    *)                          # first non-opt arg
+      break
+      ;;
+  esac
+done
+
+for file
+do
+  if test -d "$file"; then
+    shift
+  else
+    break
+  fi
+done
+
+case $# in
+  0) exit 0 ;;
+esac
+
+case $dirmode in
+  '')
+    if mkdir -p -- . 2>/dev/null; then
+      echo "mkdir -p -- $*"
+      exec mkdir -p -- "$@"
+    fi
+    ;;
+  *)
+    if mkdir -m "$dirmode" -p -- . 2>/dev/null; then
+      echo "mkdir -m $dirmode -p -- $*"
+      exec mkdir -m "$dirmode" -p -- "$@"
+    fi
+    ;;
+esac
+
+for file
+do
+  set fnord `echo ":$file" | sed -ne 's/^:\//#/;s/^://;s/\// /g;s/^#/\//;p'`
+  shift
+
+  pathcomp=
+  for d
+  do
+    pathcomp="$pathcomp$d"
+    case $pathcomp in
+      -*) pathcomp=./$pathcomp ;;
+    esac
+
+    if test ! -d "$pathcomp"; then
+      echo "mkdir $pathcomp"
+
+      mkdir "$pathcomp" || lasterr=$?
+
+      if test ! -d "$pathcomp"; then
+       errstatus=$lasterr
+      else
+       if test ! -z "$dirmode"; then
+         echo "chmod $dirmode $pathcomp"
+         lasterr=""
+         chmod "$dirmode" "$pathcomp" || lasterr=$?
+
+         if test ! -z "$lasterr"; then
+           errstatus=$lasterr
+         fi
+       fi
+      fi
+    fi
+
+    pathcomp="$pathcomp/"
+  done
+done
+
+exit $errstatus
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# End:
+# mkinstalldirs ends here
index 9d2664f..6b92f64 100644 (file)
 #include <stdlib.h>
 #include <errno.h>
 #include <unistd.h>
+#include <assert.h>
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
+#include "inode.h"
 #include "sysio-symbols.h"
 
-int
-SYSIO_INTERFACE_NAME(access)(const char *path, int amode)
+/*
+ * Check given access type on given inode.
+ */
+static int
+_sysio_check_permission(struct inode *ino,
+                       uid_t uid, gid_t gid,
+                       gid_t gids[], size_t ngids,
+                       int amode)
 {
-       gid_t   *list, *entry;
-       size_t  n;
-       int     err = 0;
-       unsigned mask, mode;
-       struct stat stbuf;
-       SYSIO_INTERFACE_DISPLAY_BLOCK;
-
-       SYSIO_INTERFACE_ENTER;
-       err = 0;
+       mode_t  mask;
+       struct intnl_stat *stat;
 
        /*
         * Check amode.
         */
        if ((amode & (R_OK|W_OK|X_OK)) != amode)
-               SYSIO_INTERFACE_RETURN(-1, -EINVAL);
+               return -EINVAL;
 
-       n = getgroups(0, NULL);
-       list = NULL;
-       if (n) {
-               list = malloc(n * sizeof(gid_t));
-               if (!list) {
-                       err = -ENOMEM;
-                       goto out;
-               }
-       }
-       err = getgroups(n, list);
-       if (err != (int ) n)
-               goto out;
-
-       err = SYSIO_INTERFACE_NAME(stat)(path, &stbuf);
-       if (err) {
-               err = -errno;
-               goto out;
-       }
        if (!amode)
-               SYSIO_INTERFACE_RETURN(0, 0);
-
+               return 0;
 
        mask = 0;
        if (amode & R_OK)
@@ -100,29 +82,91 @@ SYSIO_INTERFACE_NAME(access)(const char *path, int amode)
        if (amode & X_OK)
                mask |= S_IXUSR;
 
-       mode = stbuf.st_mode;
-       if (stbuf.st_uid == getuid() && (mode & mask) == mask) 
-               goto out;
+       stat = &ino->i_stbuf;
+       if (stat->st_uid == uid && (stat->st_mode & mask) == mask) 
+               return 0;
 
        mask >>= 3;
-       if (stbuf.st_gid == getgid() && (mode & mask) == mask)
-               goto out;
+       if (stat->st_gid == gid && (stat->st_mode & mask) == mask)
+               return 0;
 
-       entry = list;
-       while (n--)
-               if (stbuf.st_gid == *entry++ && (mode & mask) == mask)
-                       goto out;
+       while (ngids) {
+               ngids--;
+               if (stat->st_gid == *gids++ && (stat->st_mode & mask) == mask)
+                       return 0;
+       }
 
        mask >>= 3;
-       if ((mode & mask) == mask)
-               goto out;
+       if ((stat->st_mode & mask) == mask)
+               return 0;
+
+       return -EACCES;
+}
+
+/*
+ * Determine if a given access is permitted to a give file.
+ */
+int
+_sysio_permitted(struct inode *ino, int amode)
+{
+       int     err;
+       gid_t   *gids;
+       int     n;
+       void    *p;
 
-       err = -EACCES;
+       err = 0;
+       gids = NULL;
+       for (;;) {
+               n = getgroups(0, NULL);
+               if (!n)
+                       break;
+               p = realloc(gids, n * sizeof(gid_t));
+               if (!p && gids) {
+                       err = -ENOMEM;
+                       break;
+               }
+               gids = p;
+               err = getgroups(n, gids);
+               if (err < 0) {
+                       if (errno == EINVAL)
+                               continue;
+                       err = -errno;
+                       break;
+               }
+               err =
+                   _sysio_check_permission(ino,
+                                           geteuid(), getegid(),
+                                           gids, (size_t )n,
+                                           amode);
+               break;
+       }
+       if (!gids)
+               return err;
+       free(gids);
+       return err;
+}
+
+int
+SYSIO_INTERFACE_NAME(access)(const char *path, int amode)
+{
+       struct intent intent;
+       int     err;
+       struct pnode *pno;
+
+       SYSIO_INTERFACE_DISPLAY_BLOCK;
 
-out:
-       if (list)
-               free(list);
+       SYSIO_INTERFACE_ENTER;
 
+       INTENT_INIT(&intent, INT_GETATTR, NULL, NULL);
+       err = _sysio_namei(_sysio_cwd, path, 0, &intent, &pno);
+       if (err)
+               SYSIO_INTERFACE_RETURN(-1, err);
+       err =
+           _sysio_check_permission(pno->p_base->pb_ino,
+                                   getuid(), getgid(),
+                                   NULL, 0,
+                                   amode);
+       P_RELE(pno);
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
 }
 
index 36c4757..c943d8f 100644 (file)
 #include "file.h"
 #include "sysio-symbols.h"
 
+#if DEFER_INIT_CWD
+const char *_sysio_init_cwd = NULL;
+#endif
+
 struct pnode *_sysio_cwd = NULL;
 
 /*
@@ -90,15 +94,19 @@ _sysio_p_chdir(struct pnode *pno)
        int     err;
 
        /*
-        * Revalidate the pnode, and ensure it's a directory
+        * Revalidate the pnode, and ensure it's an accessable directory
         */
        err = _sysio_p_validate(pno, NULL, NULL);
        if (err)
                return err;
-
        if (!(pno->p_base->pb_ino &&
-             S_ISDIR(pno->p_base->pb_ino->i_mode)))
-               return -ENOTDIR;
+             S_ISDIR(pno->p_base->pb_ino->i_stbuf.st_mode)))
+               err = -ENOTDIR;
+       else
+               err = _sysio_permitted(pno->p_base->pb_ino, X_OK);
+       if (err)
+               return err;
+
        /*
         * Release old if set.
         */
@@ -154,6 +162,9 @@ _sysio_p_path(struct pnode *pno, char **buf, size_t size)
 
        cur = pno;
 
+       if (!size && buf && *buf)
+               return -EINVAL;
+
        /*
         * Walk up the tree to the root, summing the component name
         * lengths and counting the vertices.
@@ -231,6 +242,19 @@ SYSIO_INTERFACE_NAME(getcwd)(char *buf, size_t size)
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
+#if DEFER_INIT_CWD
+       if (!_sysio_cwd) {
+               struct pnode *pno;
+
+               /*
+                * Can no longer defer initialization of the current working
+                * directory. Force namei to make it happen now.
+                */
+               if (_sysio_namei(NULL, ".", 0, NULL, &pno) != 0)
+                       abort();
+               P_RELE(pno);
+       }
+#endif
        err = _sysio_p_path(_sysio_cwd, &buf, buf ? size : 0);
        SYSIO_INTERFACE_RETURN(err ? NULL : buf, err);
 }
index c8a801a..22e9382 100644 (file)
 
 #ifdef HAVE_LUSTRE_HACK
 #include <syscall.h>
+#include <native.h>
 
 static int
 _sysio_fcntl(int fd, int cmd, va_list ap, int *rtn)
 {
        long arg = va_arg(ap, long);
 
-       *rtn = syscall(SYS_fcntl, fd, cmd, arg);
+       *rtn = syscall(SYSIO_SYS_fcntl, fd, cmd, arg);
        return *rtn == -1 ? -errno : 0;
 }
 #endif
index bffc3fd..a346413 100644 (file)
@@ -45,6 +45,7 @@
 #include <assert.h>
 #include <errno.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 524fb55..13e5c5d 100644 (file)
@@ -46,6 +46,7 @@
 #include <assert.h>
 #include <errno.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 29abe4f..579ae01 100644 (file)
@@ -46,6 +46,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 988cb50..dda9904 100644 (file)
@@ -44,6 +44,7 @@
 #include <unistd.h>
 #include <errno.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 7e1a81f..d78f04e 100644 (file)
@@ -101,7 +101,7 @@ PREPEND(_, SYSIO_INTERFACE_NAME(getdirentries64))(int fd,
        if (!(fil && fil->f_ino))
                SYSIO_INTERFACE_RETURN(-1, -EBADF);
 
-       if (!S_ISDIR(fil->f_ino->i_mode))
+       if (!S_ISDIR(fil->f_ino->i_stbuf.st_mode))
                SYSIO_INTERFACE_RETURN(-1, -ENOTDIR);
 
        cc =
index 5e3e793..ce253cc 100644 (file)
 #endif
 
 /*
- * The namespace assembly buffer passes args with a `name'=`value'
- * syntax. We use the following to record that in various
- * routines below.
- */
-struct named_argument {
-       const char *name;                               /* arg name */
-       char    *value;                                 /* arg value */
-};
-
-/*
  * White space characters.
  */
 #define IGNORE_WHITE           " \t\r\n"
@@ -91,7 +81,7 @@ _sysio_init()
 {
        int     err;
 #ifdef WITH_SOCKETS
-       int     _sysio_sockets_init(void);
+        int     _sysio_sockets_init(void);
 #endif
 
        err = _sysio_ioctx_init();
@@ -113,9 +103,9 @@ _sysio_init()
                goto error;
 #endif
 #ifdef WITH_SOCKETS
-       err = _sysio_sockets_init();
-       if (err)
-               goto error;
+        err = _sysio_sockets_init();
+        if (err)
+                goto error;
 #endif
 
        goto out;
@@ -160,8 +150,8 @@ _sysio_shutdown()
  * or NUL character is success.
  *
  */
-static const char *
-get_token(const char *buf,
+const char *
+_sysio_get_token(const char *buf,
          int accepts,
          const char *delim,
          const char *ignore,
@@ -210,15 +200,20 @@ get_token(const char *buf,
  *
  * NB: Alters the passed buffer.
  */
-static char *
-get_args(char *buf, struct named_argument *vec)
+char *
+_sysio_get_args(char *buf, struct option_value_info *vec)
 {
        char    *nxt;
        char    *name, *value;
-       struct named_argument *v;
+       struct option_value_info *v;
 
        for (;;) {
-               nxt = (char *)get_token(buf, 1, "=,", IGNORE_WHITE, name = buf);
+               nxt =
+                   (char *)_sysio_get_token(buf,
+                                            1,
+                                            "=,",
+                                            IGNORE_WHITE,
+                                            name = buf);
                if (!nxt ||
                    (nxt != buf && *name == '\0' && buf + strlen(buf) == nxt)) {
                        buf = NULL;
@@ -226,15 +221,20 @@ get_args(char *buf, struct named_argument *vec)
                }
                if (*name == '\0')
                        break;
-               buf = (char *)get_token(nxt, 1, ",", IGNORE_WHITE, value = nxt);
+               buf =
+                   (char *)_sysio_get_token(nxt,
+                                            1,
+                                            ",",
+                                            IGNORE_WHITE,
+                                            value = nxt);
                if (*value == '\0')
                        value = NULL;
-               for (v = vec; v->name; v++)
-                       if (strcmp(v->name, name) == 0)
+               for (v = vec; v->ovi_name; v++)
+                       if (strcmp(v->ovi_name, name) == 0)
                                break;
-               if (!v->name)
+               if (!v->ovi_name)
                        return NULL;
-               v->value = value;
+               v->ovi_value = value;
        }
 
        return buf;
@@ -269,7 +269,7 @@ static int
 do_creat(char *args) 
 {
        size_t  len;
-       struct named_argument v[] = {
+       struct option_value_info v[] = {
                { "ft",         NULL },                 /* file type */
                { "nm",         NULL },                 /* name */
                { "pm",         NULL },                 /* permissions */
@@ -289,27 +289,27 @@ do_creat(char *args)
        int     err;
   
        len = strlen(args);
-       if (get_args(args, v) - args != (ssize_t )len ||
-           !(v[0].value &&
-             v[1].value &&
-             v[2].value))
+       if (_sysio_get_args(args, v) - args != (ssize_t )len ||
+           !(v[0].ovi_value &&
+             v[1].ovi_value &&
+             v[2].ovi_value))
                return -EINVAL;
-       perms = strtol(v[2].value, (char **)&cp, 0);
+       perms = strtol(v[2].ovi_value, (char **)&cp, 0);
        if (*cp ||
            perms < 0 ||
            (perms == LONG_MAX && errno == ERANGE) ||
            ((unsigned)perms & ~07777))
                return -EINVAL;
-       if (v[3].value) {
-               owner = strtol(v[3].value, (char **)&cp, 0);
+       if (v[3].ovi_value) {
+               owner = strtol(v[3].ovi_value, (char **)&cp, 0);
                if (*cp ||
                    ((owner == LONG_MIN || owner == LONG_MAX)
                     && errno == ERANGE))
                        return -EINVAL;
        } else
                owner = getuid();
-       if (v[4].value) {
-               group = strtol(v[4].value, (char **)&cp, 0);
+       if (v[4].ovi_value) {
+               group = strtol(v[4].ovi_value, (char **)&cp, 0);
                if (*cp ||
                    ((group == LONG_MIN || group == LONG_MAX) &&
                     errno == ERANGE))
@@ -321,9 +321,10 @@ do_creat(char *args)
                return -ENOENT;
        err = 0;
        mode = perms;
-       if (strcmp(v[0].value, "dir") == 0) {
+       if (strcmp(v[0].ovi_value, "dir") == 0) {
                INTENT_INIT(&intent, INT_CREAT, &mode, 0);
-               err = _sysio_namei(dir, v[1].value, ND_NEGOK, &intent, &pno);
+               err =
+                   _sysio_namei(dir, v[1].ovi_value, ND_NEGOK, &intent, &pno);
                if (err)
                        return err;
                if (pno->p_base->pb_ino)
@@ -338,12 +339,13 @@ do_creat(char *args)
                        err = (*ino->i_ops.inop_mkdir)(pno, mode);
                }
                P_RELE(pno);
-       } else if (strcmp(v[0].value, "chr") == 0) {
-               if (!(v[5].value && parse_mm(v[5].value, &dev) == 0))
+       } else if (strcmp(v[0].ovi_value, "chr") == 0) {
+               if (!(v[5].ovi_value && parse_mm(v[5].ovi_value, &dev) == 0))
                        return -EINVAL;
                mode |= S_IFCHR;
                INTENT_INIT(&intent, INT_CREAT, &mode, 0);
-               err = _sysio_namei(dir, v[1].value, ND_NEGOK, &intent, &pno);
+               err =
+                   _sysio_namei(dir, v[1].ovi_value, ND_NEGOK, &intent, &pno);
                if (err)
                        return err;
                if (pno->p_base->pb_ino)
@@ -358,18 +360,19 @@ do_creat(char *args)
                        err = (*ino->i_ops.inop_mknod)(pno, mode, dev);
                }
                P_RELE(pno);
-       } else if (strcmp(v[0].value, "blk") == 0) {
+       } else if (strcmp(v[0].ovi_value, "blk") == 0) {
                /*
                 * We don't support block special files yet.
                 */
                return -EINVAL;
-       } else if (strcmp(v[0].value, "file") == 0) {
+       } else if (strcmp(v[0].ovi_value, "file") == 0) {
                int     i;
                struct inode *ino;
 
                i = O_CREAT|O_EXCL;
                INTENT_INIT(&intent, INT_CREAT, &mode, &i);
-               err = _sysio_namei(dir, v[1].value, ND_NEGOK, &intent, &pno);
+               err =
+                   _sysio_namei(dir, v[1].ovi_value, ND_NEGOK, &intent, &pno);
                if (err)
                        return err;
                err = _sysio_open(pno, O_CREAT|O_EXCL, mode);
@@ -378,7 +381,7 @@ do_creat(char *args)
                        return err;
                }
                ino = pno->p_base->pb_ino;
-               if (!err && v[6].value) {
+               if (!err && v[6].ovi_value) {
                        struct iovec iovec;
                        struct intnl_xtvec xtvec;
                        struct ioctx io_context;
@@ -386,8 +389,8 @@ do_creat(char *args)
                        /*
                         * Deposit optional file content.
                         */
-                       iovec.iov_base = v[6].value;
-                       iovec.iov_len = strlen(v[6].value);
+                       iovec.iov_base = v[6].ovi_value;
+                       iovec.iov_len = strlen(v[6].ovi_value);
                        xtvec.xtv_off = 0;
                        xtvec.xtv_len = iovec.iov_len;
                        IOCTX_INIT(&io_context,
@@ -430,7 +433,7 @@ static int
 do_mnt(char *args) 
 {
        size_t  len;
-       struct named_argument v[] = {
+       struct option_value_info v[] = {
                { "dev",        NULL },                 /* source (type:dev) */
                { "dir",        NULL },                 /* target dir */
                { "fl",         NULL },                 /* flags */
@@ -442,35 +445,46 @@ do_mnt(char *args)
        struct pnode *dir;
   
        len = strlen(args);
-       if (get_args(args, v) - args != (ssize_t )len ||
-           !(v[0].value && v[1].value))
+       if (_sysio_get_args(args, v) - args != (ssize_t )len ||
+           !(v[0].ovi_value && v[1].ovi_value))
                return -EINVAL;
-       ty = (char *)get_token(v[0].value, 1, ":", "", name = v[0].value);
+       ty =
+           (char *)_sysio_get_token(v[0].ovi_value,
+                                    1,
+                                    ":",
+                                    "",
+                                    name = v[0].ovi_value);
        flags = 0;
-       if (v[2].value) {
+       if (v[2].ovi_value) {
                char    *cp;
 
                /*
                 * Optional flags.
                 */
-               flags = strtoul(v[2].value, &cp, 0);
+               flags = strtoul(v[2].ovi_value, &cp, 0);
                if (*cp || (flags == ULONG_MAX && errno == ERANGE))
                        return -EINVAL;
        }
 
-       if (strlen(v[1].value) == 1 && v[1].value[0] == PATH_SEPARATOR) {
+       if (strlen(v[1].ovi_value) == 1 && v[1].ovi_value[0] == PATH_SEPARATOR) {
                /*
                 * Aha! It's root they want. Have to do that special.
                 */
-               return _sysio_mount_root(ty, name, flags, v[3].value);
+               return _sysio_mount_root(ty, name, flags, v[3].ovi_value);
        }
 
        if (!(dir = _sysio_cwd) && !(dir = _sysio_root))
                return -ENOENT;
-       return _sysio_mount(dir, ty, v[1].value, name, flags, v[3].value);
+       return _sysio_mount(dir,
+                           ty,
+                           v[1].ovi_value,
+                           name,
+                           flags,
+                           v[3].ovi_value);
 }
 
 
+#if 0
 /*
  * Chdir
  *
@@ -480,7 +494,7 @@ static int
 do_cd(char *args) 
 {
        size_t  len;
-       struct named_argument v[] = {
+       struct option_value_info v[] = {
                { "dir",        NULL },                 /* directory */
                { NULL,         NULL }
        };
@@ -488,12 +502,12 @@ do_cd(char *args)
        struct pnode *dir, *pno;
 
        len = strlen(args);
-       if (get_args(args, v) - args != (ssize_t )len || !v[0].value)
+       if (_sysio_get_args(args, v) - args != (ssize_t )len || !v[0].ovi_value)
                return -EINVAL;
 
        if (!(dir = _sysio_cwd) && !(dir = _sysio_root))
                return -ENOENT;
-       err = _sysio_namei(dir, v[0].value, 0, NULL, &pno);
+       err = _sysio_namei(dir, v[0].ovi_value, 0, NULL, &pno);
        if (err)
                return err;
        err = _sysio_p_chdir(pno);
@@ -501,6 +515,7 @@ do_cd(char *args)
                P_RELE(pno);
        return err;
 }
+#endif
 
 /*
  * Does a chmod
@@ -511,7 +526,7 @@ static int
 do_chmd(char *args)
 {
        size_t  len;
-       struct named_argument v[] = {
+       struct option_value_info v[] = {
                { "src",        NULL },                 /* path */
                { "pm",         NULL },                 /* perms */
                { NULL,         NULL }
@@ -523,10 +538,10 @@ do_chmd(char *args)
        struct pnode *dir, *pno;
   
        len = strlen(args);
-       if (get_args(args, v) - args != (ssize_t )len ||
-           !(v[0].value && v[1].value))
+       if (_sysio_get_args(args, v) - args != (ssize_t )len ||
+           !(v[0].ovi_value && v[1].ovi_value))
                return -EINVAL;
-       perms = strtol(v[1].value, &cp, 0);
+       perms = strtol(v[1].ovi_value, &cp, 0);
        if (*cp ||
            perms < 0 ||
            (perms == LONG_MAX && errno == ERANGE) ||
@@ -537,7 +552,7 @@ do_chmd(char *args)
 
        if (!(dir = _sysio_cwd) && !(dir = _sysio_root))
                return -ENOENT;
-       err = _sysio_namei(dir, v[0].value, 0, NULL, &pno);
+       err = _sysio_namei(dir, v[0].ovi_value, 0, NULL, &pno);
        if (err)
                return err;
        err = _sysio_setattr(pno, pno->p_base->pb_ino, SETATTR_MODE, &stbuf);
@@ -550,40 +565,52 @@ static int
 do_open(char *args)
 {
        size_t  len;
-       struct named_argument v[] = {
-               { "nm", NULL },                 /* path */
+       struct option_value_info v[] = {
+               { "nm",         NULL },                 /* path */
                { "fd",         NULL },                 /* fildes */
                { "m",          NULL },                 /* mode */
                { NULL,         NULL }
        };
        char    *cp;
+       long    l;
        int     fd;
+       unsigned long ul;
        mode_t  m;
        struct pnode *dir, *pno;
        struct intent intent;
        int     err;
        struct file *fil;
 
+/*
+ * Check if long overflows integer range.
+ */
+#if LONG_MAX <= INT_MAX
+#define _irecheck(_l, _e) \
+       ((_l) == LONG_MAX && (_e) == ERANGE)
+#else
+#define _irecheck(_l, _e) \
+       ((_l) > INT_MAX)
+#endif
+
        len = strlen(args);
-       if (get_args(args, v) - args != (ssize_t )len ||
-           !(v[0].value && v[1].value && v[2].value))
+       if (_sysio_get_args(args, v) - args != (ssize_t )len ||
+           !(v[0].ovi_value && v[1].ovi_value && v[2].ovi_value))
                return -EINVAL;
-       fd = strtol(v[1].value, (char **)&cp, 0);
-       if (*cp ||
-           (((fd == LONG_MIN || fd == LONG_MAX) && errno == ERANGE)) ||
-            fd < 0)
+       l = strtol(v[1].ovi_value, (char **)&cp, 0);
+       if (*cp || l < 0 || _irecheck(l, errno))
                return -EINVAL;
-       m = strtoul(v[1].value, (char **)&cp, 0);
+       fd = (int )l;
+       ul = strtoul(v[1].ovi_value, (char **)&cp, 0);
        if (*cp ||
-           (m == LONG_MAX && errno == ERANGE))
+           (ul == ULONG_MAX && errno == ERANGE))
                return -EINVAL;
-       m &= O_RDONLY|O_WRONLY|O_RDWR;
+       m = (mode_t )ul & (O_RDONLY|O_WRONLY|O_RDWR);
 
        if (!(dir = _sysio_cwd) && !(dir = _sysio_root))
                return -ENOENT;
        INTENT_INIT(&intent, INT_OPEN, &m, NULL);
        pno = NULL;
-       err = _sysio_namei(dir, v[0].value, 0, &intent, &pno);
+       err = _sysio_namei(dir, v[0].ovi_value, 0, &intent, &pno);
        if (err)
                return err;
        fil = NULL;
@@ -607,6 +634,8 @@ do_open(char *args)
        if (pno)
                P_RELE(pno);
        return err;
+
+#undef _irecheck
 }
 
 /*
@@ -621,14 +650,16 @@ do_command(char *buf)
        char    *args, *cmd;
 
        len = strlen(buf);
-       args = (char *)get_token(buf, 1, ",", IGNORE_WHITE, cmd = buf);
+       args = (char *)_sysio_get_token(buf, 1, ",", IGNORE_WHITE, cmd = buf);
        if (args) {
                if (strcmp("creat", cmd) == 0)
                        return do_creat(args);
                if (strcmp("mnt", cmd) == 0)
                        return do_mnt(args);
+#if 0
                if (strcmp("cd", cmd) == 0)
                        return do_cd(args);
+#endif
                if (strcmp("chmd", cmd) == 0)
                        return do_chmd(args);
                if (strcmp("open", cmd) == 0)
@@ -642,15 +673,23 @@ do_command(char *buf)
  * commands 
  */
 int 
-_sysio_boot(const char *buf) 
+_sysio_boot(const char *buf
+#if DEFER_INIT_CWD
+           , const char *path
+#endif
+          )
 {
        char    c, *tok;
+       ssize_t len;
        int     err;
 
+       if (!buf)
+               buf = "";
        /*
         * Allocate token buffer.
         */
-       tok = malloc(strlen(buf));
+       len = strlen(buf);
+       tok = malloc(len ? len : 1);
        if (!tok)
                return -ENOMEM;
        err = 0;
@@ -670,7 +709,12 @@ _sysio_boot(const char *buf)
                /*
                 * Get the command.
                 */
-               buf = (char *)get_token(buf + 1, 0, "}", IGNORE_WHITE, tok);
+               buf =
+                   (char *)_sysio_get_token(buf + 1,
+                                            0,
+                                            "}",
+                                            IGNORE_WHITE,
+                                            tok);
                if (!buf) {
                        err = -EINVAL;
                        break;
@@ -683,5 +727,10 @@ _sysio_boot(const char *buf)
                        break;
        }
        free(tok);
+#if DEFER_INIT_CWD
+       if (err)
+               return err;
+       _sysio_init_cwd = path;
+#endif
        return err;
 }
index 0fa2cd0..3b4a1a4 100644 (file)
@@ -218,8 +218,7 @@ hash(struct file_identifier *fid)
 struct inode *
 _sysio_i_new(struct filesys *fs,
             struct file_identifier *fid,
-            mode_t type,
-            dev_t rdev,
+            struct intnl_stat *stat,
             unsigned immunity,
             struct inode_ops *ops,
             void *private)
@@ -240,24 +239,27 @@ _sysio_i_new(struct filesys *fs,
                return NULL;
        ino->i_ops = *ops;
        operations = *ops;
-       if (S_ISBLK(type) || S_ISCHR(type) || S_ISFIFO(type)) {
+       if (S_ISBLK(stat->st_mode) ||
+           S_ISCHR(stat->st_mode) ||
+           S_ISFIFO(stat->st_mode)) {
                struct inode_ops *o;
 
                /*
                 * Replace some operations sent with
                 * those from the device table.
                 */
-               o = _sysio_dev_lookup(type, rdev);
+               o = _sysio_dev_lookup(stat->st_mode, stat->st_rdev);
                operations.inop_open = o->inop_open;
                operations.inop_close = o->inop_close;
                operations.inop_read = o->inop_read;
                operations.inop_write = o->inop_write;
                operations.inop_pos = o->inop_pos;
                operations.inop_iodone = o->inop_iodone;
+               operations.inop_fcntl = o->inop_fcntl;
                operations.inop_datasync = o->inop_datasync;
                operations.inop_ioctl = o->inop_ioctl;
        }
-       I_INIT(ino, fs, type, rdev, &operations, fid, immunity, private);
+       I_INIT(ino, fs, stat, &operations, fid, immunity, private);
        ino->i_ref = 1;
        TAILQ_INSERT_TAIL(&_sysio_inodes, ino, i_nodes);
        head = &fs->fs_itbl[hash(fid) % FS_ITBLSIZ];
@@ -321,6 +323,8 @@ void
 _sysio_i_undead(struct inode *ino)
 {
        
+       if (ino->i_zombie)
+               return;
        LIST_REMOVE(ino, i_link);
        ino->i_zombie = 1;
 }
index d157c9b..b6934cb 100644 (file)
@@ -44,6 +44,7 @@
 #include <errno.h>
 #include <sys/ioctl.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 4daaf32..0bfd497 100644 (file)
 #include <assert.h>
 #include <sys/uio.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "xtio.h"
 #include "sysio.h"
 #include "inode.h"
 
-
 #if defined(REDSTORM)
 #include <catamount/do_iostats.h>
 #endif
  */
 
 /*
- * Arguments to IO vector enumerator callback when used by _sysio_doio().
- */
-struct doio_helper_args {
-       ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *);     /* base func */
-       void    *arg;                                           /* caller arg */
-};
-
-/*
  * List of all outstanding (in-flight) asynch IO requests tracked
  * by the system.
  */
@@ -259,293 +251,3 @@ _sysio_ioctx_complete(struct ioctx *ioctx)
 
        free(ioctx);
 }
-
-/*
- * General help validating strided-IO vectors.
- *
- * A driver may call this to make sure underflow/overflow of an off_t can't
- * occur and overflow of a ssize_t can't occur when writing. The sum
- * of the reconciled transfer length is returned or some appropriate
- * error depending on underflow/overflow.
- *
- * The following algorithm assumes:
- *
- * a) sizeof(size_t) >= sizeof(ssize_t)
- * b) 2's complement arithmetic
- * c) The compiler won't optimize away code because it's developers
- *     believed that something with an undefined result in `C' can't happen.
- */
-ssize_t
-_sysio_validx(const struct intnl_xtvec *xtv, size_t xtvlen,
-             const struct iovec *iov, size_t iovlen,
-             _SYSIO_OFF_T limit)
-{
-       ssize_t acc, cc;
-       struct iovec iovec;
-       struct intnl_xtvec xtvec;
-       _SYSIO_OFF_T off;
-
-       if (!(xtvlen && iovlen))
-               return -EINVAL;
-
-       acc = 0;
-       xtvec.xtv_len = iovec.iov_len = 0;
-       do {
-               while (!xtvec.xtv_len) {
-                       if (!xtvlen--)
-                               break;
-                       if (!xtv->xtv_len) {
-                               xtv++;
-                               continue;
-                       }
-                       xtvec = *xtv++;
-                       if (xtvec.xtv_off < 0)
-                               return -EINVAL;
-               }
-               if (!xtvec.xtv_len)
-                       break;
-               do {
-                       while (!iovec.iov_len) {
-                               if (!iovlen--)
-                                       break;
-                               if (!iov->iov_len) {
-                                       iov++;
-                                       continue;
-                               }
-                               iovec = *iov++;
-                       }
-                       if (!iovec.iov_len)
-                               break;
-                       cc = iovec.iov_len;
-                       if (cc < 0)
-                               return -EINVAL;
-                       if ((size_t )cc > xtvec.xtv_len)
-                               cc = xtvec.xtv_len;
-                       xtvec.xtv_len -= cc;
-                       iovec.iov_len -= cc;
-                       off = xtvec.xtv_off + cc;
-                       if (xtvec.xtv_off && off <= xtvec.xtv_off)
-                               return off < 0 ? -EINVAL : -EOVERFLOW;
-                       if (off > limit)
-                               return -EFBIG;
-                       xtvec.xtv_off = off;
-                       cc += acc;
-                       if (acc && (cc <= acc))
-                               return -EINVAL;
-                       acc = cc;
-               } while (xtvec.xtv_len && iovlen);
-       } while ((xtvlen || xtvec.xtv_len) && iovlen);
-       return acc;
-}
-
-/*
- */
-ssize_t
-_sysio_enumerate_extents(const struct intnl_xtvec *xtv, size_t xtvlen,
-                        const struct iovec *iov, size_t iovlen,
-                        ssize_t (*f)(const struct iovec *, int,
-                                     _SYSIO_OFF_T,
-                                     ssize_t,
-                                     void *),
-                        void *arg)
-{
-       ssize_t acc, tmp, cc;
-       struct iovec iovec;
-       struct intnl_xtvec xtvec;
-       const struct iovec *start;
-       _SYSIO_OFF_T off;
-       size_t  n;
-       size_t  remain;
-       
-       acc = 0;
-       iovec.iov_len = 0;
-       while (xtvlen) {
-               /*
-                * Coalesce contiguous extent vector entries.
-                */
-               off = xtvec.xtv_off = xtv->xtv_off;
-               off += xtvec.xtv_len = xtv->xtv_len;
-               while (++xtv, --xtvlen) {
-                       if (off != xtv->xtv_off) {
-                               /*
-                                * Not contiguous.
-                                */
-                               break;
-                       }
-                       if (!xtv->xtv_len) {
-                               /*
-                                * Zero length.
-                                */
-                               continue;
-                       }
-                       off += xtv->xtv_len;
-                       xtvec.xtv_len += xtv->xtv_len;
-               }
-               while (xtvec.xtv_len) {
-                       if (iovec.iov_len) {
-                               tmp = iovec.iov_len; 
-                               if (iovec.iov_len > xtvec.xtv_len)
-                                       iovec.iov_len = xtvec.xtv_len;
-                               cc =
-                                   (*f)(&iovec, 1,
-                                        xtvec.xtv_off,
-                                        xtvec.xtv_len,
-                                        arg);
-                               if (cc <= 0) {
-                                       if (acc)
-                                               return acc;
-                                       return cc;
-                               }
-                               iovec.iov_base = (char *)iovec.iov_base + cc;
-                               iovec.iov_len = tmp - cc; 
-                               tmp = cc + acc;
-                               if (acc && tmp <= acc)
-                                       abort();                /* paranoia */
-                               acc = tmp;
-                       } else if (iovlen) {
-                               start = iov;
-                               n = xtvec.xtv_len;
-                               do {
-                                       if (iov->iov_len > n) {
-                                               /*
-                                                * That'll do.
-                                                */
-                                               break;
-                                       }
-                                       n -= iov->iov_len;
-                                       iov++;
-                               } while (--iovlen);
-                               if (iov == start) {
-                                       iovec = *iov++;
-                                       iovlen--;
-                                       continue;
-                               }
-                               remain = xtvec.xtv_len - n;
-                               cc =
-                                   (*f)(start, iov - start,
-                                        xtvec.xtv_off,
-                                        remain,
-                                        arg);
-                               if (cc <= 0) {
-                                       if (acc)
-                                               return acc;
-                                       return cc;
-                               }
-                                                               
-                               tmp = cc + acc;
-                               if (acc && tmp <= acc)
-                                       abort();                /* paranoia */
-                               acc = tmp;
-
-                               remain -= cc;
-                               if (remain)
-                                       return acc;             /* short */
-                       } else
-                               return acc;                     /* short out */
-                       xtvec.xtv_off += cc;
-                       xtvec.xtv_len -= cc;
-               }
-       }
-       return acc;
-}
-
-ssize_t
-_sysio_enumerate_iovec(const struct iovec *iov, size_t count,
-                      _SYSIO_OFF_T off,
-                      ssize_t limit,
-                      ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
-                      void *arg)
-{
-       ssize_t acc, cc;
-       size_t  n;
-       unsigned indx;
-       size_t  remain;
-
-       if (!count)
-               return -EINVAL;
-       assert(limit >= 0);
-       acc = 0;
-       n = limit;
-       for (indx = 0; n && indx < count; indx++) {
-               if (iov[indx].iov_len < n) {
-                       cc = (ssize_t )iov[indx].iov_len;
-                       if (cc < 0)
-                               return -EINVAL;
-               } else
-                       cc = (ssize_t )n;
-               if (!cc)
-                       continue;
-               n -= cc;
-               cc += acc;
-               if (acc && cc <= acc)
-                       return -EINVAL;
-               acc = cc;
-       }
-       if (!acc)
-               return 0;
-       acc = 0;
-       do {
-               if (!iov->iov_len) {
-                       iov++;
-                       continue;
-               }
-               n =
-                   iov->iov_len < (size_t )limit
-                     ? iov->iov_len
-                     : (size_t )limit;
-               cc = (*f)(iov->iov_base, n, off, arg);
-               if (cc <= 0) {
-                       if (acc)
-                               return acc;
-                       return cc;
-               }
-               off += cc;
-               limit -= cc;
-               remain = iov->iov_len - cc;
-               cc += acc;
-               if (acc && cc <= acc)
-                       abort();                        /* bad driver! */
-               acc = cc;
-               if (remain || !limit)
-                       break;                          /* short/limited read */
-               iov++;
-       } while (--count);
-       return acc;
-}
-
-static ssize_t
-_sysio_doio_helper(const struct iovec *iov, int count,
-                  _SYSIO_OFF_T off,
-                  ssize_t limit,
-                  struct doio_helper_args *args)
-{
-
-       return _sysio_enumerate_iovec(iov, count,
-                                     off, limit,
-                                     args->f,
-                                     args->arg);
-}
-
-/*
- * A meta-driver for the whole strided-io process. Appropriate when
- * the driver can't handle anything but simple p{read,write}-like
- * interface.
- */
-ssize_t
-_sysio_doio(const struct intnl_xtvec *xtv, size_t xtvlen,
-           const struct iovec *iov, size_t iovlen,
-           ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
-           void *arg)
-{
-       struct doio_helper_args arguments;
-
-       arguments.f = f;
-       arguments.arg = arg;
-       return _sysio_enumerate_extents(xtv, xtvlen,
-                                       iov, iovlen,
-                                       (ssize_t (*)(const struct iovec *, int,
-                                                    _SYSIO_OFF_T,
-                                                    ssize_t,
-                                                    void *))_sysio_doio_helper,
-                                       &arguments);
-}
index e52ec2f..4ed52db 100644 (file)
@@ -43,6 +43,7 @@
 
 #include <errno.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 4c278b5..bf0907b 100644 (file)
@@ -67,7 +67,7 @@ SYSIO_INTERFACE_NAME(link)(const char *oldpath, const char *newpath)
        err = _sysio_namei(_sysio_cwd, oldpath, 0, &intent, &old);
        if (err)
                goto out;
-       if (S_ISDIR(old->p_base->pb_ino->i_mode)) {
+       if (S_ISDIR(old->p_base->pb_ino->i_stbuf.st_mode)) {
                err = -EPERM;
                goto error1;
        }
index b046ec4..3ab5a85 100644 (file)
@@ -78,6 +78,11 @@ _sysio_lseek(int fd, _SYSIO_OFF_T offset, int whence)
                {
                        int     err;
 
+                       /*
+                        * Don't blindly trust the attributes
+                        * in the inode record for this. Give the
+                        * driver a chance to refresh them.
+                        */
                        err =
                            (*fil->f_ino->i_ops.inop_getattr)(NULL,
                                                              fil->f_ino,
@@ -163,7 +168,6 @@ sysio_sym_weak_alias(SYSIO_INTERFACE_NAME(lseek),
                     PREPEND(__, SYSIO_INTERFACE_NAME(lseek)))
 #endif
 
-#if 0
 #ifdef __linux__
 #undef llseek
 int
@@ -173,17 +177,34 @@ SYSIO_INTERFACE_NAME(llseek)(unsigned int fd __IS_UNUSED,
        loff_t *result __IS_UNUSED,
        unsigned int whence __IS_UNUSED)
 {
+       loff_t  off;
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        /*
-        * Something is very wrong if this was called.
+        * This is just plain goofy.
         */
        SYSIO_INTERFACE_ENTER;
-       SYSIO_INTERFACE_RETURN(-1, -ENOTSUP);
+#if !_LARGEFILE64_SOURCE
+       if (offset_high) {
+               /*
+                * We are using 32-bit internals. This just isn't
+                * going to work.
+                */
+               SYSIO_INTERFACE_RETURN(-1, -EOVERFLOW);
+       }
+#else
+       off = offset_high;
+       off <<= 32;
+       off |= offset_low;
+#endif
+       off = _sysio_lseek(fd, off, whence);
+       if (off < 0)
+               SYSIO_INTERFACE_RETURN((off_t )-1, (int )off);
+       *result = off;
+       SYSIO_INTERFACE_RETURN(0, 0);
 }
 
 #undef __llseek
 sysio_sym_weak_alias(SYSIO_INTERFACE_NAME(llseek), 
                     PREPEND(__, SYSIO_INTERFACE_NAME(llseek)))
 #endif
-#endif
index c4c6cb5..1d89acd 100644 (file)
@@ -45,6 +45,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 4c947d2..288dcce 100644 (file)
 #undef mknod
 #undef __xmknod
 
-#if defined(BSD) || defined(REDSTORM)
-#define _MKNOD_VER     0
-#endif
-
 int
 PREPEND(__, SYSIO_INTERFACE_NAME(xmknod))(int __ver, 
                                          const char *path, 
index fc3208b..ffd0c54 100644 (file)
@@ -22,8 +22,9 @@ SRCDIR_SRCS = src/access.c src/chdir.c src/chmod.c \
        src/ioctl.c src/ioctx.c src/iowait.c \
        src/link.c src/lseek.c src/mkdir.c \
        src/mknod.c src/mount.c src/namei.c \
-       src/open.c src/rw.c src/rename.c \
+       src/open.c src/rw.c src/reconcile.c src/rename.c \
        src/rmdir.c src/stat64.c src/stat.c \
+       src/stddir.c src/readdir.c src/readdir64.c \
        src/symlink.c src/readlink.c \
        src/truncate.c src/unlink.c src/utime.c \
        $(FILE_SUPPORT) $(LUSTRE_SRCDIR_SRCS)
index 8785bb0..de46e08 100644 (file)
@@ -9,7 +9,7 @@
  *    terms of the GNU Lesser General Public License
  *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
  *
- *    Cplant(TM) Copyright 1998-2003 Sandia Corporation. 
+ *    Cplant(TM) Copyright 1998-2004 Sandia Corporation. 
  *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
  *    license for use of this work by or on behalf of the US Government.
  *    Export of this program may require a license from the United States
@@ -76,18 +76,36 @@ struct qstr _sysio_mount_file_name = { "", 0, 0 };
  */
 static LIST_HEAD(, mount) mounts;
 
+static int _sysio_sub_fsswop_mount(const char *source,
+                                  unsigned flags,
+                                  const void *data,
+                                  struct pnode *tocover,
+                                  struct mount **mntp);
+
+static struct fssw_ops _sysio_sub_fssw_ops = {
+       _sysio_sub_fsswop_mount
+};
+
 /*
  * Initialization. Must be called before any other routine in this module.
  */
 int
 _sysio_mount_init()
 {
+       int     err;
 
        LIST_INIT(&mounts);
 #ifdef AUTOMOUNT_FILE_NAME
        _sysio_next_component(AUTOMOUNT_FILE_NAME, &_sysio_mount_file_name);
 #endif
 
+       /*
+        * Register the sub-trees "file system" driver.
+        */
+       err = _sysio_fssw_register("sub", &_sysio_sub_fssw_ops);
+       if (err)
+               return err;
+
        return 0;
 }
 
@@ -155,7 +173,7 @@ _sysio_do_mount(struct filesys *fs,
        if (err)
                goto error;
 
-       if (!S_ISDIR(mnt->mnt_root->p_base->pb_ino->i_mode)) {
+       if (!S_ISDIR(mnt->mnt_root->p_base->pb_ino->i_stbuf.st_mode)) {
                err = -ENOTDIR;
                goto error;
        }
@@ -169,6 +187,7 @@ _sysio_do_mount(struct filesys *fs,
                 */
                mnt->mnt_covers = tocover = mnt->mnt_root;
        }
+       assert(!tocover->p_cover);
        tocover->p_cover = mnt->mnt_root;
 
        LIST_INSERT_HEAD(&mounts, mnt, mnt_link);
@@ -258,6 +277,7 @@ _sysio_mount_root(const char *source,
                return err;
 
        _sysio_root = mnt->mnt_root;
+#if !DEFER_INIT_CWD
        /*
         * It is very annoying to have to set the current working directory.
         * So... If it isn't set, make it the root now.
@@ -266,6 +286,7 @@ _sysio_mount_root(const char *source,
                _sysio_cwd = _sysio_root;
                P_REF(_sysio_cwd);
        }
+#endif
 
        return 0;
 }
@@ -419,6 +440,52 @@ _sysio_unmount_all()
        return err;
 }
 
+static int
+_sysio_sub_fsswop_mount(const char *source,
+                       unsigned flags,
+                       const void *data __IS_UNUSED,
+                       struct pnode *tocover,
+                       struct mount **mntp)
+{
+       int     err;
+       struct nameidata nameidata;
+       struct mount *mnt;
+
+       /*
+        * How can we make a sub-mount from nothing?
+        */
+       if (!_sysio_root)
+               return -EBUSY;
+
+       /*
+        * Lookup the source.
+        */
+       ND_INIT(&nameidata, 0, source, _sysio_root, NULL);
+       err = _sysio_path_walk(_sysio_root, &nameidata);
+       if (err)
+               return err;
+
+       /*
+        * Mount the rooted sub-tree at the given position.
+        */
+       err =
+           _sysio_do_mount(nameidata.nd_pno->p_mount->mnt_fs,
+                           nameidata.nd_pno->p_base,
+                           nameidata.nd_pno->p_mount->mnt_flags & flags,
+                           tocover,
+                           &mnt);
+
+       /*
+        * Clean up and return.
+        */
+       if (!err) {
+               FS_REF(nameidata.nd_pno->p_mount->mnt_fs);
+               *mntp = mnt;
+       }
+       P_RELE(nameidata.nd_pno);
+       return err;
+}
+
 #ifdef AUTOMOUNT_FILE_NAME
 /*
  * Parse automount specification formatted as:
@@ -575,7 +642,6 @@ _sysio_automount(struct pnode *mntpno)
 {
        int     err;
        struct inode *ino;
-       struct intnl_stat stbuf;
        struct iovec iovec;
        struct ioctx iocontext;
        struct intnl_xtvec xtvec;
@@ -596,24 +662,21 @@ _sysio_automount(struct pnode *mntpno)
         * Read file content.
         */
        ino = mntpno->p_base->pb_ino;
-       err = (*ino->i_ops.inop_getattr)(mntpno, ino, &stbuf);
-       if (err)
-               return err;
-       if (stbuf.st_size > 64 * 1024) {
+       if (ino->i_stbuf.st_size > 64 * 1024) {
                /*
                 * Let's be reasonable.
                 */
                return -EINVAL;
        }
-       iovec.iov_base = malloc(stbuf.st_size + 1);
+       iovec.iov_base = malloc(ino->i_stbuf.st_size + 1);
        if (!iovec.iov_base)
                return -ENOMEM;
-       iovec.iov_len = stbuf.st_size;
+       iovec.iov_len = ino->i_stbuf.st_size;
        err = _sysio_open(mntpno, O_RDONLY, 0);
        if (err)
                goto out;
        xtvec.xtv_off = 0;
-       xtvec.xtv_len = stbuf.st_size;
+       xtvec.xtv_len = ino->i_stbuf.st_size;
        IOCTX_INIT(&iocontext,
                   1,
                   0,
index b4d8569..c4b6072 100644 (file)
@@ -49,6 +49,7 @@
 #include <string.h>
 #include <errno.h>
 #include <assert.h>
+#include <unistd.h>
 #include <sys/param.h>
 #include <sys/types.h>
 #include <sys/stat.h>
@@ -89,12 +90,16 @@ lookup(struct pnode *parent,
        struct intent *intnt,
        const char *path)
 {
-       struct pnode *pno;
        int     err;
+       struct pnode *pno;
 
        if (!parent->p_base->pb_ino)
                return -ENOTDIR;
 
+       err = _sysio_permitted(parent->p_base->pb_ino, X_OK);
+       if (err)
+               return err;
+
        /*
         * Short-circuit `.' and `..'; We don't cache those.
         */
@@ -177,6 +182,27 @@ _sysio_path_walk(struct pnode *parent, struct nameidata *nd)
                parent = nd->nd_root;
        }
 
+#if DEFER_INIT_CWD
+       if (!parent) {
+               const char *icwd;
+
+               if (!_sysio_init_cwd)
+                       abort();
+
+               /*
+                * Finally have to set the curretn working directory. We can
+                * not tolerate errors here or else risk leaving the process
+                * in a very unexpected location. We abort then unless all goes
+                * well.
+                */
+               icwd = _sysio_init_cwd;
+               _sysio_init_cwd = NULL;
+               if (_sysio_namei(NULL, icwd, 0, NULL, &parent) != 0 ||
+                   _sysio_p_chdir(parent) != 0)
+                       abort();
+       }
+#endif
+
        /*
         * (Re)Validate the parent.
         */
@@ -200,7 +226,7 @@ _sysio_path_walk(struct pnode *parent, struct nameidata *nd)
         */
        for (;;) {
                ino = nd->nd_pno->p_base->pb_ino;
-               if (S_ISLNK(ino->i_mode) &&
+               if (S_ISLNK(ino->i_stbuf.st_mode) &&
                    (next.len || !(nd->nd_flags & ND_NOFOLLOW))) {
                        char    *lpath;
                        ssize_t cc;
@@ -249,10 +275,10 @@ _sysio_path_walk(struct pnode *parent, struct nameidata *nd)
                }
 #ifdef AUTOMOUNT_FILE_NAME
                else if (ino &&
-                        S_ISDIR(ino->i_mode) &&
+                        S_ISDIR(ino->i_stbuf.st_mode) &&
                         (nd->nd_pno->p_mount->mnt_flags & MOUNT_F_AUTO) &&
                         nd->nd_amcnt < MAX_MOUNT_DEPTH &&
-                        ino->i_mode & S_ISUID) {
+                        ino->i_stbuf.st_mode & S_ISUID) {
                        struct pnode *pno;
 
                        /*
@@ -336,7 +362,7 @@ _sysio_path_walk(struct pnode *parent, struct nameidata *nd)
                /*
                 * Parent must be a directory.
                 */
-               if (ino && !S_ISDIR(ino->i_mode)) {
+               if (ino && !S_ISDIR(ino->i_stbuf.st_mode)) {
                        err = -ENOTDIR;
                        break;
                }
@@ -415,7 +441,8 @@ _sysio_path_walk(struct pnode *parent, struct nameidata *nd)
                 * Make sure the last processed component was a directory. The
                 * trailing slashes are illegal behind anything else.
                 */
-               if (!(err || S_ISDIR(nd->nd_pno->p_base->pb_ino->i_mode)))
+               if (!(err ||
+                     S_ISDIR(nd->nd_pno->p_base->pb_ino->i_stbuf.st_mode)))
                        err = -ENOTDIR;
        }
 
diff --git a/libsysio/src/readdir.c b/libsysio/src/readdir.c
new file mode 100644 (file)
index 0000000..af21c16
--- /dev/null
@@ -0,0 +1,153 @@
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ */
+
+#ifdef __linux__
+#include <features.h>
+#if defined(__GLIBC__) && !defined(REDSTORM) 
+
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <dirent.h>
+#include <sysio.h>
+
+#include "sysio-symbols.h"
+
+#ifndef _READDIR
+#define _READDIR SYSIO_INTERFACE_NAME(readdir)
+#define _SCANDIR SYSIO_INTERFACE_NAME(scandir)
+#define _GETDIRENTRIES SYSIO_INTERFACE_NAME(getdirentries)
+#define _DIRENT_T struct dirent
+#define _OFF_T off_t
+#endif
+
+#include "stddir.h"
+
+_DIRENT_T *
+_READDIR(DIR *dir)
+{
+       _DIRENT_T *dp = NULL;
+       _OFF_T dbase;
+
+#ifndef BSD
+       ssize_t rc;
+#else
+       int rc;
+#endif
+       SYSIO_INTERFACE_DISPLAY_BLOCK;
+
+       SYSIO_INTERFACE_ENTER;
+
+       /* need to read new data? */
+       rc = 0;
+       if (dir->cur >= dir->effective) {
+               dir->cur = 0;
+               dbase = (_OFF_T )dir->base;
+               if (sizeof(dbase) != sizeof(dir->base) &&
+                   dbase != dir->base) {
+                       dir->effective = 0;
+                       SYSIO_INTERFACE_RETURN(NULL, -EOVERFLOW);
+               }
+               rc = _GETDIRENTRIES(dir->fd, 
+                                   dir->buf, 
+#ifndef BSD
+                                   (size_t )BUFSIZE, 
+                                   (_OFF_T *) &dbase);
+#else
+                                   (int )BUFSIZE, 
+                                   (long *) __restrict dbase);
+#endif
+               dir->base = (_SYSIO_OFF_T )dbase;
+
+               /* error or end-of-file */
+               if (rc == -ENOENT)
+                       rc = 0;
+               if (rc <= 0) {
+                       dir->effective = 0;
+                       SYSIO_INTERFACE_RETURN(NULL, rc);
+               }
+               dir->effective = rc;
+       }
+       dp = (_DIRENT_T *)(dir->buf + dir->cur);
+
+#ifdef _DIRENT_HAVE_D_RECLEN
+       dir->cur += dp->d_reclen;
+#else
+       dir->cur += sizeof(_DIRENT_T);
+#endif
+#ifdef _DIRENT_HAVE_D_OFF
+       dir->filepos = dp->d_off;
+#else
+       dir->filepos = dir->cur;
+#endif
+
+       SYSIO_INTERFACE_RETURN(dp, 0);
+}
+
+sysio_sym_weak_alias(_READDIR, PREPEND(__,_READDIR))
+
+int
+_SCANDIR(const char *dirname, 
+        _DIRENT_T ***namelist, 
+        int (*filter) (const _DIRENT_T *), 
+        int (*cmp) (const void *, const void *))
+{
+       DIR *dir = NULL;
+       _DIRENT_T *de     = NULL,
+                 *nextde = NULL,
+                 **s     = NULL;
+       int n = 32, i = 0;
+       size_t desize;
+       SYSIO_INTERFACE_DISPLAY_BLOCK;
+
+       SYSIO_INTERFACE_ENTER;
+
+       if ((dir = opendir(dirname)) == NULL)
+               SYSIO_INTERFACE_RETURN(-1, -errno);
+
+       while ((de = _READDIR(dir)) != NULL) {
+               if ((filter == NULL) || filter(de)) {
+                       if (i == 0 || i >= n) {
+                           n = MAX(n, 2*i);
+                           s = (_DIRENT_T **)realloc(s, 
+                               (size_t )(n * sizeof(_DIRENT_T *)));
+                           if (!s) 
+                               SYSIO_INTERFACE_RETURN(-1, -ENOMEM);
+                       }
+                       desize = &de->d_name[_D_ALLOC_NAMLEN(de)] - (char * )de;
+                       nextde = (_DIRENT_T *)malloc(desize); 
+                       if (!nextde)
+                               SYSIO_INTERFACE_RETURN(-1, -ENOMEM);
+
+                       s[i++] = (_DIRENT_T *)memcpy(nextde, de, desize);
+               }
+       }
+       if (cmp)
+               qsort (s, i, sizeof (*s), cmp);
+
+       *namelist = s;
+
+       closedir(dir);
+
+       SYSIO_INTERFACE_RETURN(i, 0);
+}
+
+sysio_sym_weak_alias(_SCANDIR, PREPEND(__,_SCANDIR))
+
+#endif
+#endif
diff --git a/libsysio/src/readdir64.c b/libsysio/src/readdir64.c
new file mode 100644 (file)
index 0000000..f6d54a8
--- /dev/null
@@ -0,0 +1,10 @@
+#ifdef _LARGEFILE64_SOURCE
+#define _SCANDIR SYSIO_INTERFACE_NAME(scandir64)
+#define _READDIR SYSIO_INTERFACE_NAME(readdir64)
+#define _GETDIRENTRIES SYSIO_INTERFACE_NAME(getdirentries64)
+#define _DIRENT_T struct dirent64
+#define _OFF_T _SYSIO_OFF_T
+
+#include "readdir.c"
+
+#endif
index 7053c62..8693dc3 100644 (file)
  * lee@sandia.gov
  */
 
+#if defined(__linux__)
+#define _BSD_SOURCE
+#endif
 #include <unistd.h>
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
@@ -66,14 +70,15 @@ SYSIO_INTERFACE_NAME(readlink)(const char *path, char *buf, size_t bufsiz)
        if (err)
                goto out;
        ino = pno->p_base->pb_ino;
-       err = (*ino->i_ops.inop_readlink)(pno, buf, bufsiz);
-       if (err)
+       if (!S_ISLNK(ino->i_stbuf.st_mode)) {
+               err = -EINVAL;
                goto error;
-
+       }
+       err = (*ino->i_ops.inop_readlink)(pno, buf, bufsiz);
 error:
        P_RELE(pno);
 out:
-       SYSIO_INTERFACE_RETURN(err, err >= 0 ? 0 : err);
+       SYSIO_INTERFACE_RETURN(err < 0 ? -1 : err, err >= 0 ? 0 : err);
 }
 
 #ifdef REDSTORM
diff --git a/libsysio/src/reconcile.c b/libsysio/src/reconcile.c
new file mode 100644 (file)
index 0000000..8fa01fd
--- /dev/null
@@ -0,0 +1,356 @@
+/*
+ *    This Cplant(TM) source code is the property of Sandia National
+ *    Laboratories.
+ *
+ *    This Cplant(TM) source code is copyrighted by Sandia National
+ *    Laboratories.
+ *
+ *    The redistribution of this Cplant(TM) source code is subject to the
+ *    terms of the GNU Lesser General Public License
+ *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
+ *
+ *    Cplant(TM) Copyright 1998-2004 Sandia Corporation. 
+ *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
+ *    license for use of this work by or on behalf of the US Government.
+ *    Export of this program may require a license from the United States
+ *    Government.
+ */
+
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ * Questions or comments about this library should be sent to:
+ *
+ * Lee Ward
+ * Sandia National Laboratories, New Mexico
+ * P.O. Box 5800
+ * Albuquerque, NM 87185-1110
+ *
+ * lee@sandia.gov
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+#include <assert.h>
+#include <sys/uio.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/queue.h>
+
+#include "sysio.h"
+#include "xtio.h"
+
+/*
+ * Extent-vector IO support.
+ */
+
+/*
+ * Arguments to IO vector enumerator callback when used by _sysio_doio().
+ */
+struct doio_helper_args {
+       ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *);     /* base func */
+       void    *arg;                                           /* caller arg */
+};
+
+/*
+ * General help validating strided-IO vectors.
+ *
+ * A driver may call this to make sure underflow/overflow of an off_t can't
+ * occur and overflow of a ssize_t can't occur when writing. The sum
+ * of the reconciled transfer length is returned or some appropriate
+ * error depending on underflow/overflow.
+ *
+ * The following algorithm assumes:
+ *
+ * a) sizeof(size_t) >= sizeof(ssize_t)
+ * b) 2's complement arithmetic
+ * c) The compiler won't optimize away code because it's developers
+ *     believed that something with an undefined result in `C' can't happen.
+ */
+ssize_t
+_sysio_validx(const struct intnl_xtvec *xtv, size_t xtvlen,
+             const struct iovec *iov, size_t iovlen,
+             _SYSIO_OFF_T limit)
+{
+       ssize_t acc, cc;
+       struct iovec iovec;
+       struct intnl_xtvec xtvec;
+       _SYSIO_OFF_T off;
+
+       if (!(xtvlen && iovlen))
+               return -EINVAL;
+
+       acc = 0;
+       xtvec.xtv_len = iovec.iov_len = 0;
+       do {
+               while (!xtvec.xtv_len) {
+                       if (!xtvlen--)
+                               break;
+                       if (!xtv->xtv_len) {
+                               xtv++;
+                               continue;
+                       }
+                       xtvec = *xtv++;
+                       if (xtvec.xtv_off < 0)
+                               return -EINVAL;
+               }
+               if (!xtvec.xtv_len)
+                       break;
+               do {
+                       while (!iovec.iov_len) {
+                               if (!iovlen--)
+                                       break;
+                               if (!iov->iov_len) {
+                                       iov++;
+                                       continue;
+                               }
+                               iovec = *iov++;
+                       }
+                       if (!iovec.iov_len)
+                               break;
+                       cc = iovec.iov_len;
+                       if (cc < 0)
+                               return -EINVAL;
+                       if ((size_t )cc > xtvec.xtv_len)
+                               cc = xtvec.xtv_len;
+                       xtvec.xtv_len -= cc;
+                       iovec.iov_len -= cc;
+                       off = xtvec.xtv_off + cc;
+                       if (xtvec.xtv_off && off <= xtvec.xtv_off)
+                               return off < 0 ? -EINVAL : -EOVERFLOW;
+                       if (off > limit)
+                               return -EFBIG;
+                       xtvec.xtv_off = off;
+                       cc += acc;
+                       if (acc && (cc <= acc))
+                               return -EINVAL;
+                       acc = cc;
+               } while (xtvec.xtv_len && iovlen);
+       } while ((xtvlen || xtvec.xtv_len) && iovlen);
+       return acc;
+}
+
+/*
+ */
+ssize_t
+_sysio_enumerate_extents(const struct intnl_xtvec *xtv, size_t xtvlen,
+                        const struct iovec *iov, size_t iovlen,
+                        ssize_t (*f)(const struct iovec *, int,
+                                     _SYSIO_OFF_T,
+                                     ssize_t,
+                                     void *),
+                        void *arg)
+{
+       ssize_t acc, tmp, cc;
+       struct iovec iovec;
+       struct intnl_xtvec xtvec;
+       const struct iovec *start;
+       _SYSIO_OFF_T off;
+       size_t  n;
+       size_t  remain;
+       
+       acc = 0;
+       iovec.iov_len = 0;
+       while (xtvlen) {
+               /*
+                * Coalesce contiguous extent vector entries.
+                */
+               off = xtvec.xtv_off = xtv->xtv_off;
+               off += xtvec.xtv_len = xtv->xtv_len;
+               while (++xtv, --xtvlen) {
+                       if (off != xtv->xtv_off) {
+                               /*
+                                * Not contiguous.
+                                */
+                               break;
+                       }
+                       if (!xtv->xtv_len) {
+                               /*
+                                * Zero length.
+                                */
+                               continue;
+                       }
+                       off += xtv->xtv_len;
+                       xtvec.xtv_len += xtv->xtv_len;
+               }
+               while (xtvec.xtv_len) {
+                       if (iovec.iov_len) {
+                               tmp = iovec.iov_len; 
+                               if (iovec.iov_len > xtvec.xtv_len)
+                                       iovec.iov_len = xtvec.xtv_len;
+                               cc =
+                                   (*f)(&iovec, 1,
+                                        xtvec.xtv_off,
+                                        xtvec.xtv_len,
+                                        arg);
+                               if (cc <= 0) {
+                                       if (acc)
+                                               return acc;
+                                       return cc;
+                               }
+                               iovec.iov_base = (char *)iovec.iov_base + cc;
+                               iovec.iov_len = tmp - cc; 
+                               tmp = cc + acc;
+                               if (acc && tmp <= acc)
+                                       abort();                /* paranoia */
+                               acc = tmp;
+                       } else if (iovlen) {
+                               start = iov;
+                               n = xtvec.xtv_len;
+                               do {
+                                       if (iov->iov_len > n) {
+                                               /*
+                                                * That'll do.
+                                                */
+                                               break;
+                                       }
+                                       n -= iov->iov_len;
+                                       iov++;
+                               } while (--iovlen);
+                               if (iov == start) {
+                                       iovec = *iov++;
+                                       iovlen--;
+                                       continue;
+                               }
+                               remain = xtvec.xtv_len - n;
+                               cc =
+                                   (*f)(start, iov - start,
+                                        xtvec.xtv_off,
+                                        remain,
+                                        arg);
+                               if (cc <= 0) {
+                                       if (acc)
+                                               return acc;
+                                       return cc;
+                               }
+                                                               
+                               tmp = cc + acc;
+                               if (acc && tmp <= acc)
+                                       abort();                /* paranoia */
+                               acc = tmp;
+
+                               remain -= cc;
+                               if (remain)
+                                       return acc;             /* short */
+                       } else
+                               return acc;                     /* short out */
+                       xtvec.xtv_off += cc;
+                       xtvec.xtv_len -= cc;
+               }
+       }
+       return acc;
+}
+
+ssize_t
+_sysio_enumerate_iovec(const struct iovec *iov, size_t count,
+                      _SYSIO_OFF_T off,
+                      ssize_t limit,
+                      ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
+                      void *arg)
+{
+       ssize_t acc, cc;
+       size_t  n;
+       unsigned indx;
+       size_t  remain;
+
+       if (!count)
+               return -EINVAL;
+       assert(limit >= 0);
+       acc = 0;
+       n = limit;
+       for (indx = 0; n && indx < count; indx++) {
+               if (iov[indx].iov_len < n) {
+                       cc = (ssize_t )iov[indx].iov_len;
+                       if (cc < 0)
+                               return -EINVAL;
+               } else
+                       cc = (ssize_t )n;
+               if (!cc)
+                       continue;
+               n -= cc;
+               cc += acc;
+               if (acc && cc <= acc)
+                       return -EINVAL;
+               acc = cc;
+       }
+       if (!acc)
+               return 0;
+       acc = 0;
+       do {
+               if (!iov->iov_len) {
+                       iov++;
+                       continue;
+               }
+               n =
+                   iov->iov_len < (size_t )limit
+                     ? iov->iov_len
+                     : (size_t )limit;
+               cc = (*f)(iov->iov_base, n, off, arg);
+               if (cc <= 0) {
+                       if (acc)
+                               return acc;
+                       return cc;
+               }
+               off += cc;
+               limit -= cc;
+               remain = iov->iov_len - cc;
+               cc += acc;
+               if (acc && cc <= acc)
+                       abort();                        /* bad driver! */
+               acc = cc;
+               if (remain || !limit)
+                       break;                          /* short/limited read */
+               iov++;
+       } while (--count);
+       return acc;
+}
+
+static ssize_t
+_sysio_doio_helper(const struct iovec *iov, int count,
+                  _SYSIO_OFF_T off,
+                  ssize_t limit,
+                  struct doio_helper_args *args)
+{
+
+       return _sysio_enumerate_iovec(iov, count,
+                                     off, limit,
+                                     args->f,
+                                     args->arg);
+}
+
+/*
+ * A meta-driver for the whole strided-io process. Appropriate when
+ * the driver can't handle anything but simple p{read,write}-like
+ * interface.
+ */
+ssize_t
+_sysio_doio(const struct intnl_xtvec *xtv, size_t xtvlen,
+           const struct iovec *iov, size_t iovlen,
+           ssize_t (*f)(void *, size_t, _SYSIO_OFF_T, void *),
+           void *arg)
+{
+       struct doio_helper_args arguments;
+
+       arguments.f = f;
+       arguments.arg = arg;
+       return _sysio_enumerate_extents(xtv, xtvlen,
+                                       iov, iovlen,
+                                       (ssize_t (*)(const struct iovec *, int,
+                                                    _SYSIO_OFF_T,
+                                                    ssize_t,
+                                                    void *))_sysio_doio_helper,
+                                       &arguments);
+}
index 23e97b1..bf8724c 100644 (file)
@@ -61,35 +61,49 @@ SYSIO_INTERFACE_NAME(rename)(const char *oldpath, const char *newpath)
        int     err;
        struct pnode *old, *new;
        struct pnode_base *nxtpb, *pb;
-       struct intnl_stat ostbuf, nstbuf;
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
+
+       /*
+        * Neither old nor new may be the empty string.
+        */
+       if (*oldpath == '\0' || *newpath == '\0')
+               SYSIO_INTERFACE_RETURN(-1, -ENOENT);
+
        /*
         * Resolve oldpath to a path node.
         */
        INTENT_INIT(&intent, INT_UPDPARENT, NULL, NULL);
-       err = _sysio_namei(_sysio_cwd, oldpath, 0, &intent, &old);
+       err = _sysio_namei(_sysio_cwd, oldpath, ND_NOFOLLOW, &intent, &old);
        if (err)
                goto error3;
        /*
         * Resolve newpath to a path node.
         */
        INTENT_INIT(&intent, INT_UPDPARENT, NULL, NULL);
-       err = _sysio_namei(_sysio_cwd, newpath, ND_NEGOK, &intent, &new);
+       err =
+           _sysio_namei(_sysio_cwd,
+                        newpath,
+                        ND_NOFOLLOW | ND_NEGOK,
+                        &intent,
+                        &new);
        if (err)
                goto error2;
 
+       /*
+        * Don't allow mount points to move.
+        */
        if (old->p_mount->mnt_root == old || old->p_cover ||
            new->p_mount->mnt_root == new) {
                err = -EBUSY;
                goto error1;
        }
 
+       /*
+        * No xdev renames either.
+        */
        if (old->p_mount->mnt_fs != new->p_mount->mnt_fs) {
-               /*
-                * Oops. They're trying to move it across file systems.
-                */
                err = -EXDEV;
                goto error1;
        }
@@ -109,40 +123,30 @@ SYSIO_INTERFACE_NAME(rename)(const char *oldpath, const char *newpath)
                }
        } while (nxtpb);
 
-       while (new->p_base->pb_ino) {
+       /*
+        * If old == new, we're done.
+        */
+       if (old->p_base->pb_ino == new->p_base->pb_ino)
+               goto out;
+
+       if (new->p_base->pb_ino) {
                /*
                 * Existing entry. We're replacing the new. Make sure that's
                 * ok.
                 */
-               err =
-                   old->p_base->pb_ino->i_ops.inop_getattr(old, NULL, &ostbuf);
-               if (err)
-                       goto error1;
-               err =
-                   new->p_base->pb_ino->i_ops.inop_getattr(new, NULL, &nstbuf);
-               if (err) {
-                       if (err != ENOENT)
-                               goto error1;
-                       /*
-                        * Rats! It disappeared beneath us.
-                        */
-                       (void )_sysio_p_validate(new, NULL, NULL);
-                       continue;
-               }
-               if (S_ISDIR(ostbuf.st_mode)) {
-                       if (!S_ISDIR(nstbuf.st_mode)) {
-                               err = -ENOTDIR;
+               if (S_ISDIR(new->p_base->pb_ino->i_stbuf.st_mode)) {
+                       if (!S_ISDIR(old->p_base->pb_ino->i_stbuf.st_mode)) {
+                               err = -EISDIR;
                                goto error1;
                        }
-                       if (nstbuf.st_nlink > 2) {
+                       if (new->p_base->pb_ino->i_stbuf.st_nlink > 2) {
                                err = -ENOTEMPTY;
                                goto error1;
                        }
-               } else if (S_ISDIR(nstbuf.st_mode)) {
-                       err = -EEXIST;
+               } else if (S_ISDIR(old->p_base->pb_ino->i_stbuf.st_mode)) {
+                       err = -ENOTDIR;
                        goto error1;
                }
-               break;
        }
 
        /*
@@ -151,7 +155,7 @@ SYSIO_INTERFACE_NAME(rename)(const char *oldpath, const char *newpath)
         * now. If it becomes an issue, we can do it later. For now, I've
         * elected to use the semantic that says, basically, the entire
         * sub-tree must be unreferenced. That's per POSIX, but it's a nasty
-        * this to do to the caller.
+        * thing to do to the caller.
         */
        if (_sysio_p_prune(new) != 1) {
                err = -EBUSY;
index cbc7632..b26b16b 100644 (file)
@@ -45,6 +45,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index edc308b..bd4ae6b 100644 (file)
@@ -682,9 +682,13 @@ PREPEND(_, SYSIO_INTERFACE_NAME(ireadx))(int fd,
 
        SYSIO_INTERFACE_ENTER;
        fil = _sysio_fd_find(fd);
-       if (!(fil && xtv_count))
+       if (!fil)
                SYSIO_INTERFACE_RETURN(IOID_FAIL, -EBADF);
 
+       /* Perform a check on the iov_count and xtv_count */
+       if ((iov_count == 0) || (xtv_count == 0))
+               SYSIO_INTERFACE_RETURN(IOID_FAIL, -EINVAL);
+
        err =
            _sysio_iiox(IIOXOP_READ(fil->f_ino),
                        fil,
@@ -717,9 +721,14 @@ SYSIO_INTERFACE_NAME(ireadx)(int fd,
 
        SYSIO_INTERFACE_ENTER;
        fil = _sysio_fd_find(fd);
-       if (!(fil && xtv_count))
+       if (!fil)
                SYSIO_INTERFACE_RETURN(IOID_FAIL, -EBADF);
 
+
+       /* Perform a check on the iov_count and xtv_count */
+       if ((iov_count == 0) || (xtv_count == 0))
+               SYSIO_INTERFACE_RETURN(IOID_FAIL, -EINVAL);
+
        ixtv = ixtvent = malloc(xtv_count * sizeof(struct intnl_xtvec));
        if (!ixtv)
                SYSIO_INTERFACE_RETURN(IOID_FAIL, -ENOMEM);
@@ -1236,9 +1245,13 @@ SYSIO_INTERFACE_NAME(iwritex)(int fd,
 
        SYSIO_INTERFACE_ENTER;
        fil = _sysio_fd_find(fd);
-       if (!(fil && xtv_count))
+       if (!fil)
                SYSIO_INTERFACE_RETURN(IOID_FAIL, -EBADF);
 
+       /* Perform a check on the iov_count and xtv_count */
+       if ((iov_count == 0) || (xtv_count == 0))
+               SYSIO_INTERFACE_RETURN(IOID_FAIL, -EINVAL);
+
        ixtv = ixtvent = malloc(xtv_count * sizeof(struct intnl_xtvec));
        if (!ixtv)
                SYSIO_INTERFACE_RETURN(IOID_FAIL, -ENOMEM);
index 4fec1f1..44a4b88 100644 (file)
@@ -119,6 +119,10 @@ PREPEND(__, SYSIO_INTERFACE_NAME(fxstat))(int __ver,
 #else
        buf = __stat_buf;
 #endif
+       /*
+        * Never use the attributes cached in the inode record. Give the
+        * driver a chance to refresh them.
+        */
        err =
            fil->f_ino->i_ops.inop_getattr(NULL, fil->f_ino, buf);
 #if _LARGEFILE64_SOURCE
@@ -164,10 +168,6 @@ PREPEND(__, SYSIO_INTERFACE_NAME(xstat))(int __ver,
        int     err;
        struct pnode *pno;
        struct inode *ino;
-       struct intnl_stat *buf;
-#if _LARGEFILE64_SOURCE
-       struct stat64 st64;
-#endif
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
@@ -180,22 +180,18 @@ PREPEND(__, SYSIO_INTERFACE_NAME(xstat))(int __ver,
        err = _sysio_namei(_sysio_cwd, __filename, 0, &intent, &pno);
        if (err)
                goto out;
+       /*
+        * Leverage the INT_GETATTR intent above. We are counting
+        * on the FS driver to either make sure the attributes cached in
+        * the inode are always correct or refresh them in the lookup, above.
+        */
        ino = pno->p_base->pb_ino;
 #if _LARGEFILE64_SOURCE
-       buf = &st64;
+       convstat(&ino->i_stbuf, __stat_buf);
 #else
-       buf = __stat_buf;
+       (void )memcpy(__stat_buf, &ino->i_stbuf, sizeof(struct intnl_stat));
 #endif
-       err =
-           ino->i_ops.inop_getattr(pno,
-                                   pno->p_base->pb_ino,
-                                   buf);
-
        P_RELE(pno);
-#if _LARGEFILE64_SOURCE
-       if (!err)
-               convstat(buf, __stat_buf);
-#endif
 out:
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
 }
@@ -236,10 +232,6 @@ PREPEND(__, SYSIO_INTERFACE_NAME(lxstat))(int __ver,
        int     err;
        struct pnode *pno;
        struct inode *ino;
-       struct intnl_stat *buf;
-#if _LARGEFILE64_SOURCE
-       struct stat64 st64;
-#endif
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
@@ -252,22 +244,18 @@ PREPEND(__, SYSIO_INTERFACE_NAME(lxstat))(int __ver,
        err = _sysio_namei(_sysio_cwd, __filename, ND_NOFOLLOW, &intent, &pno);
        if (err)
                goto out;
+       /*
+        * Leverage the INT_GETATTR intent above. We are counting
+        * on the FS driver to either make sure the attributes cached in
+        * the inode are always correct or refresh them in the lookup, above.
+        */
+       ino = pno->p_base->pb_ino;
 #if _LARGEFILE64_SOURCE
-       buf = &st64;
+       convstat(&ino->i_stbuf, __stat_buf);
 #else
-       buf = __stat_buf;
+       (void )memcpy(__stat_buf, &ino->i_stbuf, sizeof(struct intnl_stat));
 #endif
-       ino = pno->p_base->pb_ino;
-       err =
-           ino->i_ops.inop_getattr(pno,
-                                   pno->p_base->pb_ino,
-                                   buf);
-
        P_RELE(pno);
-#if _LARGEFILE64_SOURCE
-       if (!err)
-               convstat(buf, __stat_buf);
-#endif
 out:
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
 }
index 377e2dc..70bd43a 100644 (file)
@@ -43,6 +43,7 @@
 
 #ifdef _LARGEFILE64_SOURCE
 
+#include <string.h>
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
@@ -85,6 +86,10 @@ PREPEND(__, SYSIO_INTERFACE_NAME(fxstat64))(int __ver,
                err = -EBADF;
                goto out;
        }
+       /*
+        * Never use the attributes cached in the inode record. Give
+        * the driver a chance to refresh them.
+        */
        err = fil->f_ino->i_ops.inop_getattr(NULL, fil->f_ino, __stat_buf);
 out:
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
@@ -107,6 +112,7 @@ PREPEND(__, SYSIO_INTERFACE_NAME(xstat64))(int __ver,
        struct intent intent;
        int     err;
        struct pnode *pno;
+       struct inode *ino;
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
@@ -119,10 +125,13 @@ PREPEND(__, SYSIO_INTERFACE_NAME(xstat64))(int __ver,
        err = _sysio_namei(_sysio_cwd, __filename, 0, &intent, &pno);
        if (err)
                goto out;
-       err =
-           pno->p_base->pb_ino->i_ops.inop_getattr(pno,
-                                                   pno->p_base->pb_ino,
-                                                   __stat_buf);
+       /*
+        * Leverage the INT_GETATTR intent above. We are counting
+        * on the FS driver to either make sure the attributes cached in
+        * the inode are always correct or refresh them in the lookup, above.
+        */
+       ino = pno->p_base->pb_ino;
+       (void )memcpy(__stat_buf, &ino->i_stbuf, sizeof(struct intnl_stat));
        P_RELE(pno);
 out:
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
@@ -147,6 +156,7 @@ PREPEND(__, SYSIO_INTERFACE_NAME(lxstat64))(int __ver,
        struct intent intent;
        int     err;
        struct pnode *pno;
+       struct inode *ino;
        SYSIO_INTERFACE_DISPLAY_BLOCK;
 
        SYSIO_INTERFACE_ENTER;
@@ -159,10 +169,13 @@ PREPEND(__, SYSIO_INTERFACE_NAME(lxstat64))(int __ver,
        err = _sysio_namei(_sysio_cwd, __filename, ND_NOFOLLOW, &intent, &pno);
        if (err)
                goto out;
-       err =
-           pno->p_base->pb_ino->i_ops.inop_getattr(pno,
-                                                   pno->p_base->pb_ino,
-                                                   __stat_buf);
+       /*
+        * Leverage the INT_GETATTR intent above. We are counting
+        * on the FS driver to either make sure the attributes cached in
+        * the inode are always correct or refresh them in the lookup, above.
+        */
+       ino = pno->p_base->pb_ino;
+       (void )memcpy(__stat_buf, &ino->i_stbuf, sizeof(struct intnl_stat));
        P_RELE(pno);
 out:
        SYSIO_INTERFACE_RETURN(err ? -1 : 0, err);
diff --git a/libsysio/src/stddir.c b/libsysio/src/stddir.c
new file mode 100644 (file)
index 0000000..b41a9a1
--- /dev/null
@@ -0,0 +1,118 @@
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ */
+
+#ifdef __linux__
+#include <features.h>
+#if defined(__GLIBC__) && !defined(REDSTORM) 
+
+/*
+ * stddir.c
+ *
+ * As of glibc 2.3, the new capability to define functions with a 'hidden'
+ * attribute means that any time glibc decides to use that capability
+ * we will no longer be able to successfully intercept low level calls
+ * in a link against default system glibc. Thus the following imported 
+ * functions.
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <dirent.h>
+
+#include <sysio.h>
+
+#include "sysio-symbols.h"
+#include "stddir.h"
+
+/***********************************************************
+ * dir series functions                                    *
+ ***********************************************************/
+
+DIR* 
+SYSIO_INTERFACE_NAME(opendir)(const char *name)
+{
+       DIR *dir;
+
+       SYSIO_INTERFACE_DISPLAY_BLOCK;
+
+       SYSIO_INTERFACE_ENTER;
+
+       dir = (DIR * )calloc(1, sizeof(DIR));
+       if (!dir)
+               SYSIO_INTERFACE_RETURN(NULL, -ENOMEM);
+
+       dir->fd = open(name, O_RDONLY);
+       if (dir->fd < 0) {
+               free(dir);
+               SYSIO_INTERFACE_RETURN(NULL, -errno);
+       }
+       return dir;
+}
+
+sysio_sym_weak_alias(opendir, __opendir)
+
+int
+SYSIO_INTERFACE_NAME(closedir)(DIR *dir)
+{
+       int rc;
+       SYSIO_INTERFACE_DISPLAY_BLOCK;
+
+       SYSIO_INTERFACE_ENTER;
+
+       rc = SYSIO_INTERFACE_NAME(close)(dir->fd);
+       free(dir);
+
+       SYSIO_INTERFACE_RETURN(rc, 0);
+}
+
+sysio_sym_weak_alias(SYSIO_INTERFACE_NAME(closedir), 
+                    PREPEND(__, SYSIO_INTERFACE_NAME(closedir)))
+
+int 
+SYSIO_INTERFACE_NAME(dirfd)(DIR *dir)
+{
+       return(dir->fd);
+}
+
+long int
+SYSIO_INTERFACE_NAME(telldir)(DIR *dir)
+{
+       return(dir->filepos);
+}
+
+void 
+SYSIO_INTERFACE_NAME(seekdir)(DIR *dir, long int offset)
+{
+       dir->filepos = offset;
+       dir->base = offset;
+       dir->effective = 0;
+       dir->cur = 0;
+}
+
+void 
+SYSIO_INTERFACE_NAME(rewinddir)(DIR *dir)
+{
+       dir->base = 0;
+       dir->filepos = 0;
+       dir->cur = 0;
+       dir->effective = 0;
+}
+
+#endif
+#endif
index fcd463a..03bf1c7 100644 (file)
 
 #include "sysio-symbols.h"
 
-#if !defined(__USE_LARGEFILE64)
-#error "__LARGEFILE64_SOURCE must be defined"
-#endif
-
-
-/***********************************************************
- * dir series functions                                    *
- ***********************************************************/
-
-#undef  BUFSIZE
-#define BUFSIZE        4096
-
-struct __dirstream {
-       int               fd;
-       loff_t            base;
-       loff_t            filepos;       /* current pos in dir file stream */
-       struct dirent    *curent;        /* current dirent pointer */
-       struct dirent64  *curent64;      /* current dirent64 pointer */
-       struct dirent    *retent;        /* ent returned to caller */
-       struct dirent64  *retent64;      /* ent64 returned to caller */
-       unsigned int      effective;     /* effective data size in buffer */
-       char              buf[BUFSIZE];
-};
-
-DIR* opendir(const char *name)
-{
-       DIR *dir;
-
-       dir = (DIR *) malloc(sizeof(*dir));
-       if (!dir) {
-               errno = ENOMEM;
-               return NULL;
-       }
-
-#if __USE_LARGEFILE64
-       dir->fd = open64(name, O_RDONLY);
-#else
-       dir->fd = open(name, O_RDONLY);
-#endif
-       if (dir->fd < 0)
-               goto err_out;
-
-       dir->base = 0;
-       dir->filepos = 0;
-       dir->curent = (struct dirent *) dir->buf;
-       dir->curent64 = (struct dirent64 *) dir->buf;
-       dir->retent = NULL;
-       dir->retent64 = NULL;
-       dir->effective = 0;
-
-       return dir;
-err_out:
-       free(dir);
-       return NULL;
-}
-
-sysio_sym_weak_alias(opendir, __opendir);
-
-struct dirent64 *readdir64(DIR *dir)
-{
-       int rc, reclen;
-
-       /* need to read new data? */
-       if ((char*)dir->curent64 - dir->buf >= dir->effective) {
-               rc = getdirentries64(dir->fd, dir->buf, BUFSIZE, &dir->base);
-               /* error or end-of-file */
-               if (rc <= 0)
-                       return NULL;
-
-               dir->curent64 = (struct dirent64 *) dir->buf;
-               dir->effective = rc;
-       }
-
-       dir->retent64 = dir->curent64;
-       dir->curent64 = (struct dirent64*) ((char *)(dir->curent64) +
-                               dir->curent64->d_reclen);
-#ifdef _DIRENT_HAVE_D_OFF
-       dir->filepos = dir->curent64->d_off;
-#else
-       dir->filepos += dir->curent64->d_reclen;
-#endif
-       return dir->retent64;
-}
-
-sysio_sym_weak_alias(readdir64, __readdir64);
-
-/* XXX probably the following assumption is not true */
-#if __WORDSIZE == 64
-#define NATURAL_READDIR64
-#else
-#undef  NATURAL_READDIR64
-#endif
-
-#ifndef NATURAL_READDIR64
-
-struct dirent *readdir(DIR *dir)
-{
-       int rc, reclen;
-
-       /* need to read new data? */
-       if ((char*)dir->curent - dir->buf >= dir->effective) {
-               rc = getdirentries(dir->fd, dir->buf, BUFSIZE, (off_t*) &dir->base);
-               /* error or end-of-file */
-               if (rc <= 0)
-                       return NULL;
-
-               dir->curent = (struct dirent *) dir->buf;
-               dir->effective = rc;
-       }
-
-       dir->retent = dir->curent;
-       dir->curent = (struct dirent*) ((char *)(dir->curent) +
-                               dir->curent->d_reclen);
-#ifdef _DIRENT_HAVE_D_OFF
-       dir->filepos = dir->curent->d_off;
-#else
-       dir->filepos += dir->curent->d_reclen;
-#endif
-       return dir->retent;
-}
-sysio_sym_weak_alias(readdir, __readdir);
-
-#else /* NATURAL_READDIR64 */
-
-struct dirent *readdir(DIR *dir) {
-       return (struct dirent *) readdir64(dir);
-}
-sysio_sym_weak_alias(readdir, __readdir);
-
-#endif /* NATURAL_READDIR64 */
-
-int closedir(DIR *dir)
-{
-       int rc;
-
-       rc = close(dir->fd);
-
-       free(dir);
-       return rc;
-}
-
-sysio_sym_weak_alias(closedir, __closedir);
-
-int dirfd(DIR *dir)
-{
-       return dir->fd;
-}
-
-off_t telldir(DIR *dir)
-{
-       return (dir->filepos);
-}
-
-void seekdir(DIR *dir, off_t offset)
-{
-       dir->filepos = offset;
-
-       dir->base = offset;
-       dir->curent64 = (struct dirent64 *) dir->buf;
-       dir->retent64 = NULL;
-       dir->effective = 0;
-       dir->curent = (struct dirent *) dir->buf;
-       dir->retent = NULL;
-}
-
-void rewinddir(DIR *dir)
-{
-       dir->base = 0;
-       dir->filepos = 0;
-       dir->curent64 = (struct dirent64 *) dir->buf;
-       dir->retent64 = NULL;
-       dir->curent = (struct dirent *) dir->buf;
-       dir->retent = NULL;
-       dir->effective = 0;
-}
-
-#if 0
-int scandir(const char *dir, struct dirent ***namelist,
-            int(*select)(const struct dirent *),
-            int(*compar)(const void *, const void *))
-{
-       errno = ENOSYS;
-       return -1;
-}
-
-int scandir64(const char *dir, struct dirent64 ***namelist,
-              int(*select)(const struct dirent64 *),
-              int(*compar)(const void *, const void *))
-{
-       errno = ENOSYS;
-       return -1;
-}
-#endif
-
 /***********************************************************
  * FIXME workaround for linux only                         *
  ***********************************************************/
index 1142432..1925466 100644 (file)
@@ -45,6 +45,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 718f0af..abecb42 100644 (file)
@@ -71,9 +71,9 @@ do_truncate(struct pnode *pno, struct inode *ino, _SYSIO_OFF_T length)
                ino = pno->p_base->pb_ino;
        if (!ino)
                return -EBADF;
-       if (S_ISDIR(ino->i_mode))                       /* for others too? */
+       if (S_ISDIR(ino->i_stbuf.st_mode))              /* for others too? */
                return -EISDIR;
-       if (!S_ISREG(ino->i_mode))
+       if (!S_ISREG(ino->i_stbuf.st_mode))
                return -EINVAL;
 
        (void )memset(&stbuf, 0, sizeof(stbuf));
index c584fcc..197ddd6 100644 (file)
@@ -45,6 +45,7 @@
 #include <errno.h>
 #include <assert.h>
 #include <sys/types.h>
+#include <sys/stat.h>
 #include <sys/queue.h>
 
 #include "sysio.h"
index 1124663..d4f15cc 100644 (file)
@@ -41,6 +41,7 @@
  * lee@sandia.gov
  */
 
+#include <stdlib.h>
 #include <string.h>
 #include <errno.h>
 #include <time.h>
 #include <sys/stat.h>
 #include <unistd.h>
 #include <sys/queue.h>
+#include <sys/time.h>
 
 #include "sysio.h"
 #include "inode.h"
 #include "file.h"
 
+time_t
+_sysio_local_time()
+{
+       struct timeval tv;
+
+       if (gettimeofday(&tv, NULL) != 0)
+               abort();
+       return tv.tv_sec;
+}
+
 int
 SYSIO_INTERFACE_NAME(utime)(const char *path, const struct utimbuf *buf)
 {
@@ -69,7 +81,7 @@ SYSIO_INTERFACE_NAME(utime)(const char *path, const struct utimbuf *buf)
        if (err)
                goto out;
        if (!buf) {
-               _utbuffer.actime = _utbuffer.modtime = time(NULL);
+               _utbuffer.actime = _utbuffer.modtime = _SYSIO_LOCAL_TIME();
                buf = &_utbuffer;
        }
        (void )memset(&stbuf, 0, sizeof(struct intnl_stat));
index 85c4304..fcbadb1 100644 (file)
@@ -1,6 +1,6 @@
 noinst_PROGRAMS = test_copy test_stats test_path test_list \
        test_getcwd test_link test_unlink test_rename \
-       test_regions test_driver
+       test_regions test_driver test_stddir
 
 CLEANFILES=drv_data.c
 
@@ -28,16 +28,8 @@ YOD_DRIVER_NAME=
 YOD_DRIVER_CFLAGS=
 endif
 
-if WITH_SOCKETS_DRIVER
-SOCKETS_DRIVER_NAME=sockets
-SOCKETS_DRIVER_CFLAGS= -I$(top_srcdir)/drivers/sockets
-else
-SOCKETS_DRIVER_NAME=
-SOCKETS_DRIVER_CFLAGS=
-endif
-
 DRIVERS=$(NATIVE_DRIVER_NAME) $(INCORE_DRIVER_NAME) $(YOD_DRIVER_NAME) \
-       $(STFD_DEV_NAME) $(SOCKETS_DRIVER_NAME)
+       $(STFD_DEV_NAME)
 
 CMNSRC=startup.c drv_init_all.c drv_data.c
 
@@ -106,9 +98,18 @@ test_driver_CFLAGS=$(CFL)
 test_driver_LDADD=$(LIBS)
 test_driver_DEPENDENCIES=$(LIBS)
 
+test_stddir_SOURCES=test_stddir.c $(CMNSRC)
+test_stddir_CFLAGS=$(CFL)
+test_stddir_LDADD=$(LIBS)
+test_stddir_DEPENDENCIES=$(LIBS)
+
 drv_data.c: $(CONFIG_DEPENDENCIES) $(top_srcdir)/tests/gendrvdata.sh
        test -z "drv_data.c" && rm -f drv_data.c; \
        $(SHELL) $(top_srcdir)/tests/gendrvdata.sh $(DRIVERS) > drv_data.c
 
+lib_LIBRARIES=libruntime.a
+
+libruntime_a_SOURCES=sysio-run-start.c startup.c drv_init_all.c drv_data.c
+
 AM_CFLAGS = -L$(LIBBUILD_DIR)
 include $(top_srcdir)/Rules.make
index 82a92cb..fcb54d4 100644 (file)
@@ -13,6 +13,7 @@ int
 _test_sysio_startup()
 {
        int     err;
+       const char *cwd;
        const char *s;
 
        err = _sysio_init();
@@ -22,23 +23,28 @@ _test_sysio_startup()
        if (err)
                return err;
        s = getenv("SYSIO_NAMESPACE");
-       if (s)
-               err = _sysio_boot(s);
-       else if (!(s = getenv("SYSIO_MANUAL"))) {
+       if (!(s || (s = getenv("SYSIO_MANUAL")))) {
                /*
                 * Assume a native mount at root.
                 */
-               err = _sysio_boot("{mnt,dev=\"native:/\",dir=/,fl=0}");
+               s = "{mnt,dev=\"native:/\",dir=/,fl=0}";
        }
+       cwd = getenv("SYSIO_CWD");
+#if DEFER_INIT_CWD
+       err = _sysio_boot(s, cwd ? cwd : "/");
+#else
+       err = _sysio_boot(s);
+#endif
        if (err)
                return err;
 
-       s = getenv("SYSIO_CWD");
-       if (s) {
-               err = chdir(s);
-               if (err)
-                       return err;
-       }
+#if !DEFER_INIT_CWD
+       if (!cwd)
+               s = "/";
+       err = chdir(s);
+       if (err)
+               return err;
+#endif
 
        return 0;
 }
diff --git a/libsysio/tests/sysio-run-start.c b/libsysio/tests/sysio-run-start.c
new file mode 100644 (file)
index 0000000..409e94f
--- /dev/null
@@ -0,0 +1,26 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <sys/types.h>
+#include <sys/uio.h>
+#include <xtio.h>
+#include "test.h"
+
+void _sysio_startup(void) __attribute__ ((constructor));
+
+void
+_sysio_startup()
+{
+       int     err;
+
+       err = _test_sysio_startup();
+       if (err) {
+               errno = -err;
+               perror("sysio startup");
+               exit(1);
+       }
+       if (atexit(_test_sysio_shutdown) != 0) {
+               perror("atexit");
+               exit(1);
+       }
+}
index 65bf40e..b5f7b86 100755 (executable)
@@ -40,7 +40,7 @@ my $home = $ENV{"HOME"};
 my $auto_mount = $ENV{"SYSIO_AUTOMOUNT"};
 my $root_flags = "0";
 my $extras = "";
-if ((defined($auto_mount)) && ($auto_mount == "xyes")) {
+if ((defined($auto_mount)) && ($auto_mount eq "xyes")) {
        $root_flags = "2";
 
        #
@@ -73,6 +73,15 @@ $ENV{$namespace_env} = "\
 my $res;
 
 if ($use_system == 1) {
+       # Test for tmp_dir.  If it exists, fail 
+       # The tmp_dir should be removed after a successful
+       # test run, but is kept if anything fails
+       if (-e "$cwd/tmp_dir") {
+               print STDERR "ERROR! tmp_dir already exists.\n";
+               print STDERR "Need to remove tmp_dir for test to run properly\n";
+               exit 1;
+       } 
+
   # Will use this directory...
   system("mkdir -p $cwd/tmp_dir");
 
diff --git a/libsysio/tests/test_stddir.c b/libsysio/tests/test_stddir.c
new file mode 100644 (file)
index 0000000..941dea4
--- /dev/null
@@ -0,0 +1,168 @@
+/*
+ *    This Cplant(TM) source code is the property of Sandia National
+ *    Laboratories.
+ *
+ *    This Cplant(TM) source code is copyrighted by Sandia National
+ *    Laboratories.
+ *
+ *    The redistribution of this Cplant(TM) source code is subject to the
+ *    terms of the GNU Lesser General Public License
+ *    (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html)
+ *
+ *    Cplant(TM) Copyright 1998-2003 Sandia Corporation. 
+ *    Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive
+ *    license for use of this work by or on behalf of the US Government.
+ *    Export of this program may require a license from the United States
+ *    Government.
+ */
+
+/*
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ * 
+ * This library 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
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ * Questions or comments about this library should be sent to:
+ *
+ * Lee Ward
+ * Sandia National Laboratories, New Mexico
+ * P.O. Box 5800
+ * Albuquerque, NM 87185-1110
+ *
+ * lee@sandia.gov
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <errno.h>
+#include <string.h>
+#include <getopt.h>
+#include <dirent.h>
+#include <sys/types.h>
+
+#include "xtio.h"
+#include "test.h"
+
+/*
+ * Test {open, read, close}dir functions
+ * 
+ * Usage: test_stddir [path, ...]
+ */
+static int testit(const char *);
+static void usage(void);
+
+int 
+main (int argc, char** argv)
+{
+       int     err;
+       int     i;
+       int     n;
+       const char *path;
+
+       /*
+        * Parse command line arguments.
+        */
+       while ((i = getopt(argc, argv, "")) != -1)
+               switch (i) {
+
+               default:
+                       usage();
+               }
+
+       /*
+        * Init sysio lib.
+        */
+       err = _test_sysio_startup();
+       if (err) {
+               errno = -err;
+               perror("sysio startup");
+               exit(1);
+       }
+
+       /*
+        * If no command-line arguments, read from stdin until EOF.
+        */
+       n = argc - optind;
+       if (!n) {
+               int     doflush;
+               static char buf[4096];
+               size_t  len;
+               char    *cp;
+               char    c;
+
+               doflush = 0;
+               while (fgets(buf, sizeof(buf), stdin) != NULL) {
+                       len = strlen(buf);
+                       cp = buf + len - 1;
+                       c = *cp;
+                       *cp = '\0';
+                       if (!doflush)
+                               err = testit(buf);
+                       if (err)
+                               break;
+                       doflush = c == '\n' ? 0 : 1;
+               }
+       }
+
+       /*
+        * Try path(s) listed on command-line.
+        */
+       while (optind < argc) {
+               path = argv[optind++];
+               err = testit(path);
+               if (err)
+                       break;
+       }
+
+       /*
+        * Clean up.
+        */
+       _test_sysio_shutdown();
+
+       return err;
+}
+
+int
+testit(const char *path)
+{
+       DIR     *d;
+       struct dirent *de;
+
+       printf("testing directory functions on %s\n", path);
+
+       if ((d = opendir(path)) == NULL) {
+               perror(path);   
+               return errno;
+       }
+
+       while ((de = readdir(d)) != NULL)
+               printf("\t %s: ino %lu off %lu type %u\n",
+                       de->d_name, (unsigned long )de->d_ino, 
+                       (unsigned long )de->d_off, (int )de->d_type);
+
+       if (closedir(d)) {
+               perror("closedir");
+               return errno;
+       }
+
+       return 0;
+}
+
+static void
+usage()
+{
+
+       (void )fprintf(stderr,
+                      "Usage: test_stddir [<path> ...]\n");
+
+       exit(1);
+}