PSARC 2006/162 Extended FILE space for 32-bit Solaris processes
authorcraigm
Thu, 20 Apr 2006 08:17:22 -0700
changeset 1846 376b8b33ed65
parent 1845 178e04e5effe
child 1847 714d77cd8726
PSARC 2006/162 Extended FILE space for 32-bit Solaris processes 1085341 32-bit stdio routines should support file descriptors >255 6369408 fflush(NULL); will corrupt data written on files in multithreaded apps
usr/src/Makefile.lint
usr/src/cmd/fmtmsg/Makefile
usr/src/cmd/perl/5.8.4/distrib/patchlevel.h
usr/src/cmd/perl/5.8.4/distrib/perlio.c
usr/src/cmd/prtfru/Makefile
usr/src/cmd/streams/strcmd/Makefile
usr/src/cmd/tip/aculib/Makefile
usr/src/cmd/users/Makefile
usr/src/head/stdio_ext.h
usr/src/head/stdio_impl.h
usr/src/lib/Makefile
usr/src/lib/extendedFILE/Makefile
usr/src/lib/extendedFILE/Makefile.com
usr/src/lib/extendedFILE/common/extendedFILE.c
usr/src/lib/extendedFILE/i386/Makefile
usr/src/lib/extendedFILE/sparc/Makefile
usr/src/lib/extendedFILE/spec/Makefile
usr/src/lib/extendedFILE/spec/Makefile.targ
usr/src/lib/extendedFILE/spec/extendedFILE.spec
usr/src/lib/extendedFILE/spec/i386/Makefile
usr/src/lib/extendedFILE/spec/sparc/Makefile
usr/src/lib/extendedFILE/spec/versions
usr/src/lib/libc/inc/file64.h
usr/src/lib/libc/inc/stdiom.h
usr/src/lib/libc/port/llib-lc
usr/src/lib/libc/port/stdio/_endopen.c
usr/src/lib/libc/port/stdio/_filbuf.c
usr/src/lib/libc/port/stdio/_findbuf.c
usr/src/lib/libc/port/stdio/_flsbuf.c
usr/src/lib/libc/port/stdio/fdopen.c
usr/src/lib/libc/port/stdio/fileno.c
usr/src/lib/libc/port/stdio/flush.c
usr/src/lib/libc/port/stdio/fputs.c
usr/src/lib/libc/port/stdio/popen.c
usr/src/lib/libc/port/stdio/setbuf.c
usr/src/lib/libc/port/stdio/setvbuf.c
usr/src/lib/libc/port/stdio/vscanf.c
usr/src/lib/libc/port/stdio/vwscanf.c
usr/src/lib/libc/spec/private.spec
usr/src/lib/libc/spec/stdio.spec
usr/src/pkgdefs/SUNWcsl/prototype_com
usr/src/ucblib/libucb/inc/stdiom.h
usr/src/ucblib/libucb/port/gen/setbuffer.c
usr/src/ucblib/libucb/port/stdio/fopen.c
usr/src/uts/common/os/fio.c
usr/src/uts/common/sys/fcntl.h
usr/src/uts/common/sys/file.h
usr/src/uts/common/sys/user.h
usr/src/uts/common/syscall/fcntl.c
--- a/usr/src/Makefile.lint	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/Makefile.lint	Thu Apr 20 08:17:22 2006 -0700
@@ -286,6 +286,7 @@
 	lib/abi \
 	lib/auditd_plugins \
 	lib/crypt_modules \
+	lib/extendedFILE \
 	lib/libadt_jni \
 	lib/libaio \
 	lib/libavl \
--- a/usr/src/cmd/fmtmsg/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/fmtmsg/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -22,9 +21,12 @@
 #
 #ident	"%Z%%M%	%I%	%E% SMI"
 #
-# Copyright (c) 1989 by Sun Microsystems, Inc.
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
 #
 
+#ident	"%Z%%M%	%I%	%E% SMI"
+
 PROG= fmtmsg
 OBJS= main.o
 SRCS= $(OBJS:%.o=%.c)
@@ -33,7 +35,7 @@
 
 .KEEP_STATE:
 
-all: $(PROG) 
+all: $(PROG)
 
 $(PROG): $(OBJS)
 	$(LINK.c) $(OBJS) -o $@ $(LDLIBS)
@@ -44,7 +46,6 @@
 clean:
 	$(RM) $(OBJS)
 
-lint:
-	$(LINT.c) $(SRCS)
+lint: lint_SRCS
 
 include ../Makefile.targ
--- a/usr/src/cmd/perl/5.8.4/distrib/patchlevel.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/perl/5.8.4/distrib/patchlevel.h	Thu Apr 20 08:17:22 2006 -0700
@@ -147,6 +147,7 @@
 	"23106 Numeric comparison operators mustn't compare addresses of ...",
 	"23320 [perl #30066] Memory leak in nested shared data structures ...",
 	"23321 [perl #31459] Bug in read()",
+	"27722 perlio.c breaks on Solaris/gcc when > 256 FDs are available",
  	"SPRINTF0 - fixes for sprintf formatting issues - CVE-2005-3962",
 	NULL
 };
--- a/usr/src/cmd/perl/5.8.4/distrib/perlio.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/perl/5.8.4/distrib/perlio.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2831,31 +2831,7 @@
     f->_fileno = -1;
     return 1;
 #  elif defined(__sun__)
-#    if defined(_LP64)
-    /* On solaris, if _LP64 is defined, the FILE structure is this:
-     *
-     *  struct FILE {
-     *      long __pad[16];
-     *  };
-     *
-     * It turns out that the fd is stored in the top 32 bits of
-     * file->__pad[4]. The lower 32 bits contain flags. file->pad[5] appears
-     * to contain a pointer or offset into another structure. All the
-     * remaining fields are zero.
-     *
-     * We set the top bits to -1 (0xFFFFFFFF).
-     */
-    f->__pad[4] |= 0xffffffff00000000L;
-    assert(fileno(f) == 0xffffffff);
-#    else /* !defined(_LP64) */
-    /* _file is just a unsigned char :-(
-       Not clear why we dup() rather than using -1
-       even if that would be treated as 0xFF - so will
-       a dup fail ...
-     */
-    f->_file = PerlLIO_dup(fileno(f));
-#    endif /* defined(_LP64) */
-    return 1;
+    return 0;
 #  elif defined(__hpux)
     f->__fileH = 0xff;
     f->__fileL = 0xff;
--- a/usr/src/cmd/prtfru/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/prtfru/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
 # CDDL HEADER END
 #
 #
-# Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
 # Use is subject to license terms.
 #
 #pragma ident	"%Z%%M%	%I%	%E% SMI"
@@ -38,7 +37,7 @@
 CPPFLAGS  += -I$(SRC)/lib/libfru/include \
              -I$(SRC)/lib/libfruutils
 LINTFLAGS += -u
-LDLIBS    += -lfru -lfrureg -lfruutils
+EXTRA_LDLIBS    = -lfru -lfrureg -lfruutils
 
 FILEMODE = 755
 OWNER    = root
@@ -49,7 +48,7 @@
 all: $(PROG)
 
 $(PROG): $(OBJS)
-	$(LINK.c) -o $@ $(OBJS) $(LDLIBS)
+	$(LINK.c) -o $@ $(OBJS) $(LDLIBS) $(EXTRA_LDLIBS)
 	$(POST_PROCESS)
 
 install: all $(ROOTUSRSBIN) $(ROOTUSRSBINPROG)
@@ -57,7 +56,6 @@
 $(ROOTUSRSBIN):
 	$(INS.dir)
 
-lint := LDLIBS =
 lint: lint_SRCS
 
 POFILE  = $(PROG)_msg.po
--- a/usr/src/cmd/streams/strcmd/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/streams/strcmd/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -21,7 +20,7 @@
 #
 # ident	"%Z%%M%	%I%	%E% SMI"
 #
-# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
 # Use is subject to license terms.
 #
 
@@ -34,14 +33,14 @@
 
 .KEEP_STATE:
 
-all: $(PROG) 
+all: $(PROG)
 
 install: all $(ROOTPROG)
 
 clean:
 
 lint:
-	$(LINT.c) strchg.c
-	$(LINT.c) strconf.c
+	$(LINT.c) strchg.c $(LDLIBS)
+	$(LINT.c) strconf.c $(LDLIBS)
 
 include ../../Makefile.targ
--- a/usr/src/cmd/tip/aculib/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/tip/aculib/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -1,5 +1,5 @@
 #
-# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
 # Use is subject to license terms.
 #
 # Copyright (c) 1983 Regents of the University of California.
@@ -42,4 +42,4 @@
 	$(RM) $(ACULIB) $(OBJS) core errs
 
 lint:
-	$(LINT.c) $(OBJS:%.o=%.c)
+	$(LINT.c) $(OBJS:%.o=%.c) $(LDLIBS)
--- a/usr/src/cmd/users/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/cmd/users/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -23,7 +22,7 @@
 #ident	"%Z%%M%	%I%	%E% SMI"
 #
 #
-# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
 # Use is subject to license terms.
 #
 
@@ -46,7 +45,6 @@
 clean:
 	$(RM) $(OBJS)
 
-lint:
-	$(LINT.c) $(SRCS)
+lint: lint_SRCS
 
 include ../Makefile.targ
--- a/usr/src/head/stdio_ext.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/head/stdio_ext.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,9 +18,10 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright (c) 1998, by Sun Microsystems, Inc.
- * All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+ * Use is subject to license terms.
  */
 
 /*
@@ -72,6 +72,15 @@
 extern void _flushlbf(void);
 extern int __fsetlocking(FILE *stream, int type);
 
+/*
+ * Extended FILE enabling function.
+ */
+#if defined(_LP64) && !defined(__lint)
+#define	enable_extended_FILE_stdio(fd, act)		(255)
+#else
+extern int enable_extended_FILE_stdio(int, int);
+#endif
+
 #ifdef	__cplusplus
 }
 #endif
--- a/usr/src/head/stdio_impl.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/head/stdio_impl.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,8 +18,9 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -58,11 +58,14 @@
 #endif
 	unsigned char	*_base;	/* the buffer */
 	unsigned char	_flag;	/* the state of the stream */
-	unsigned char	_file;	/* UNIX System file descriptor */
+	unsigned char	_magic; /* Old home of the file descriptor */
+				/* Only fileno(3C) can retrieve the value now */
 	unsigned	__orientation:2; /* the orientation of the stream */
 	unsigned	__ionolock:1;	/* turn off implicit locking */
 	unsigned	__seekable:1;	/* is file seekable? */
-	unsigned	__filler:4;
+	unsigned	__extendedfd:1;	/* enable extended FILE */
+	unsigned	__xf_nocheck:1;	/* no extended FILE runtime check */
+	unsigned	__filler:10;
 };
 
 #endif	/*	_LP64	*/
--- a/usr/src/lib/Makefile	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -177,6 +177,7 @@
 	libpctx		.WAIT	\
 	libcpc		\
 	watchmalloc	\
+	extendedFILE	\
 	madv		\
 	mpss		\
 	libdisasm	\
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,48 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/Makefile
+
+include	../Makefile.lib
+
+SUBDIRS=	spec .WAIT $(MACH)
+
+LIBRARY=	extendedFILE.a
+
+all :=		TARGET= all
+install :=	TARGET= install
+clean :=	TARGET= clean
+clobber :=	TARGET= clobber
+lint :=		TARGET= lint
+
+.KEEP_STATE:
+
+all install clean clobber lint: $(SUBDIRS)
+
+$(SUBDIRS):	FRC
+	@cd $@; pwd; $(MAKE) $(TARGET)
+
+FRC:
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/Makefile.com	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,67 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+# ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/Makefile.com
+
+LIBRARY = extendedFILE.a
+VERS = .1
+
+OBJECTS = extendedFILE.o
+
+# include library definitions
+include ../../Makefile.lib
+
+MAPFILE = $(MAPDIR)/mapfile
+CLOBBERFILES +=	$(MAPFILE)
+
+SRCS = $(OBJECTS:%.o=../common/%.c)
+
+LIBS = $(DYNLIB)
+LDLIBS += -lc
+CFLAGS += $(CCVERBOSE)
+CPPFLAGS += -D_REENTRANT -I../common
+DYNFLAGS += -M$(MAPFILE) $(ZINTERPOSE)
+
+CPPFLAGS += -I../../common/inc
+
+.KEEP_STATE:
+
+all: $(LIBS)
+
+lint:
+	$(LINT.c) $(SRCS) $(LDLIBS)
+
+$(DYNLIB): $(MAPFILE)
+
+$(MAPFILE):
+	@cd $(MAPDIR); $(MAKE) mapfile
+
+# include library targets
+include ../../Makefile.targ
+
+pics/%.o: ../common/%.c
+	$(COMPILE.c) -o $@ $<
+	$(POST_PROCESS_O)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/common/extendedFILE.c	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,90 @@
+/*
+ * CDDL HEADER START
+ *
+ * The contents of this file are subject to the terms of the
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
+ *
+ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+ * or http://www.opensolaris.org/os/licensing.
+ * See the License for the specific language governing permissions
+ * and limitations under the License.
+ *
+ * When distributing Covered Code, include this CDDL HEADER in each
+ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+ * If applicable, add the following below this CDDL HEADER, with the
+ * fields enclosed by brackets "[]" replaced with your own identifying
+ * information: Portions Copyright [yyyy] [name of copyright owner]
+ *
+ * CDDL HEADER END
+ */
+
+/*
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+ * Use is subject to license terms.
+ */
+
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
+#include "c_synonyms.h"
+#include <sys/types.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <limits.h>
+#include <signal.h>
+#include <stdio.h>
+#include <stdio_ext.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#define	_FILE_FD_MAX 255
+
+/*
+ * This 32-bit only preloadable library enables extended fd FILE's.
+ */
+
+#pragma	init(init_STDIO_bad_fd)
+
+void
+init_STDIO_bad_fd(void)
+{
+	int action = -1;	/* default signal */
+	int closed_fd = -1;	/* default fd */
+	char *ptr;
+	int signal;
+	int retval;
+
+	/*
+	 * user specified badfd
+	 */
+	if ((ptr = getenv("_STDIO_BADFD")) != NULL) {
+		closed_fd = atoi(ptr);
+		if (closed_fd < 3 || closed_fd > _FILE_FD_MAX) {
+			(void) fprintf(stderr, "File descriptor must be"
+			    " in the range 3-%d inclusive.\n", _FILE_FD_MAX);
+			exit(1);
+		}
+	}
+
+	/*
+	 * user specified action
+	 */
+	if ((ptr = getenv("_STDIO_BADFD_SIGNAL")) != NULL) {
+		/* accept numbers or symbolic names */
+		if (strncmp(ptr, "SIG", 3) == 0)	/* begins with "SIG"? */
+			ptr = ptr + 3;
+		retval = str2sig(ptr, &signal);
+		if (retval == -1) {
+			(void) fprintf(stderr,
+			    "Invalid signal name or number.\n");
+			exit(1);
+		}
+		action = signal;
+	}
+
+	if ((closed_fd = enable_extended_FILE_stdio(closed_fd, action)) == -1) {
+		perror("enable_extended_FILE_stdio(3C)");
+		exit(1);
+	}
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/i386/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,34 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/i386/Makefile
+
+MAPDIR=	../spec/i386
+include ../Makefile.com
+
+.KEEP_STATE:
+
+install: all $(ROOTLIBS)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/sparc/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,34 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/sparc/Makefile
+
+MAPDIR=	../spec/sparc
+include ../Makefile.com
+
+.KEEP_STATE:
+
+install: all $(ROOTLIBS)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,59 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+# ident	"%Z%%M%	%I%	%E% SMI"
+#
+
+i386_ARCHITECTURES =	i386
+sparc_ARCHITECTURES =	sparc
+
+all		:=	TARGET= all
+install		:=	TARGET= install
+clean		:=	TARGET= clean
+clobber		:=	TARGET= clobber
+lint		:=	TARGET= lint
+
+.KEEP_STATE:
+
+all install clean clobber: $($(MACH)_ARCHITECTURES)
+
+$($(MACH)_ARCHITECTURES): FRC
+	@cd $@; pwd; $(MAKE) $(TARGET)
+
+#
+# This will make sure that any target not
+# explicitly defined will not break the build.
+#
+# XXX pmake on intel does not like the following rules
+# %: ignore_and_exit_quietly
+# ignore_and_exit_quietly:
+#
+# So here it is manually
+#
+IGNORE=		_msg catalog install_h delete \
+		package tcov debug private_h \
+		check analyse test dynamic lint
+$(IGNORE):
+
+FRC:
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/Makefile.targ	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,35 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/libplot/plot/spec/Makefile.targ
+
+LIBRARY	=	extendedFILE.a
+VERS	=	.1
+
+OBJECTS	=	extendedFILE.o
+
+TRANSCPP =
+SPECCPP =
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/extendedFILE.spec	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,26 @@
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+# ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/spec/extendedFILE.spec
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/i386/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,41 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/spec/i386/Makefile
+
+include	../Makefile.targ
+
+# Add arch specific objects here
+OBJECTS	+=
+
+include	$(SRC)/lib/Makefile.lib
+
+# Uncomment the following if the linker complains
+#i386_C_PICFLAGS  = -K PIC
+
+include	$(SRC)/lib/Makefile.spec
+
+install: $(ROOTABILIB)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/sparc/Makefile	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,43 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+#
+# lib/extendedFILE/spec/sparc/Makefile
+
+.KEEP_STATE:
+
+include	../Makefile.targ
+
+# Add arch specific objects here
+OBJECTS	+=
+
+include	$(SRC)/lib/Makefile.lib
+
+# Uncomment the following if the linker complains
+#sparc_C_PICFLAGS  = -K PIC
+
+include	$(SRC)/lib/Makefile.spec
+
+install: $(ROOTABILIB)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/usr/src/lib/extendedFILE/spec/versions	Thu Apr 20 08:17:22 2006 -0700
@@ -0,0 +1,25 @@
+#
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+# ident	"%Z%%M%	%I%	%E% SMI"
+#
--- a/usr/src/lib/libc/inc/file64.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/inc/file64.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,8 +18,9 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 1997-2003 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -82,6 +82,7 @@
 	unsigned char	*_end;	/* the end of the buffer */
 	rmutex_t	_lock;	/* lock for this structure */
 	mbstate_t	_state;	/* mbstate_t */
+	int		_altfd;	/* alternate fd if > 255 */
 };
 
 #define	XFILEINITIALIZER	{ 0, NULL, RECURSIVEMUTEX, DEFAULTMBSTATE }
--- a/usr/src/lib/libc/inc/stdiom.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/inc/stdiom.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -170,6 +169,36 @@
 #endif	/*	_LP64	*/
 
 /*
+ * Internal routines from flush.c
+ */
+extern int _file_get(FILE *);
+extern int _file_set(FILE *, int, const char *);
+
+/*
+ * Macros to aid the extended fd FILE work.
+ * This helps isolate the changes to only the 32-bit code
+ * since 64-bit Solaris is not affected by this.
+ */
+#ifdef  _LP64
+#define	GET_FD(iop)		((iop)->_file)
+#define	SET_FILE(iop, fd)	((iop)->_file = (fd))
+#else
+#define	GET_FD(iop)		\
+		(((iop)->__extendedfd) ? _file_get(iop) : (iop)->_magic)
+#define	SET_FILE(iop, fd)	(iop)->_magic = (fd); (iop)->__extendedfd = 0
+#endif
+
+/*
+ * Maximum size of the file descriptor stored in the FILE structure.
+ */
+
+#ifdef _LP64
+#define	_FILE_FD_MAX	INT_MAX
+#else
+#define	_FILE_FD_MAX	255
+#endif
+
+/*
  * Internal routines from fileno.c
  */
 extern int _fileno(FILE *iop);
--- a/usr/src/lib/libc/port/llib-lc	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/llib-lc	Thu Apr 20 08:17:22 2006 -0700
@@ -145,6 +145,7 @@
 #include <spawn.h>
 #include <inttypes.h>
 #include <getopt.h>
+#include <stdio_ext.h>
 #if defined(__i386)
 #include <sys/sysi86.h>
 #endif
@@ -1709,16 +1710,6 @@
 
 extern long pcsample(uintptr_t [], long);
 
-extern size_t __fbufsize(FILE *stream);
-extern int __freading(FILE *stream);
-extern int __fwriting(FILE *stream);
-extern int __freadable(FILE *stream);
-extern int __fwritable(FILE *stream);
-extern int __flbf(FILE *stream);
-extern void __fpurge(FILE *stream);
-extern size_t __fpending(FILE *stream);
-extern void _flushlbf(void);
-
 int fstat(int, struct stat *);
 int stat(const char *_RESTRICT_KYWD, struct stat *_RESTRICT_KYWD);
 int lstat(const char *_RESTRICT_KYWD, struct stat *_RESTRICT_KYWD);
--- a/usr/src/lib/libc/port/stdio/_endopen.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/_endopen.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -66,9 +65,8 @@
 FILE *
 _endopen(const char *name, const char *type, FILE *iop, int largefile)
 {
-	int oflag, fd;
+	int oflag, fd, fflag;
 	char plus;
-	rmutex_t *lk;
 
 	if (iop == NULL)
 		return (NULL);
@@ -78,19 +76,24 @@
 		return (NULL);
 	case 'r':
 		oflag = O_RDONLY;
+		fflag = _IOREAD;
 		break;
 	case 'w':
 		oflag = O_WRONLY | O_TRUNC | O_CREAT;
+		fflag = _IOWRT;
 		break;
 	case 'a':
 		oflag = O_WRONLY | O_APPEND | O_CREAT;
+		fflag = _IOWRT;
 		break;
 	}
 	/* UNIX ignores 'b' and treats text and binary the same */
 	if ((plus = type[1]) == 'b')
 		plus = type[2];
-	if (plus == '+')
+	if (plus == '+') {
 		oflag = (oflag & ~(O_RDONLY | O_WRONLY)) | O_RDWR;
+		fflag = _IORW;
+	}
 
 	/* select small or large file open based on flag */
 	if (largefile) {
@@ -101,36 +104,21 @@
 	if (fd < 0)
 		return (NULL);
 
+	/* As long as we make sure _flag stays != 0, we don't need to lock */
 #ifdef	_LP64
 	iop->_file = fd;
+	iop->_flag = (iop->_flag & ~0377) | fflag;
 #else
-	if (fd > UCHAR_MAX) {
+	if (fd <= _FILE_FD_MAX) {
+		SET_FILE(iop, fd);
+	} else if (_file_set(iop, fd, type) != 0) {
+		/* errno set in _file_set() */
 		(void) close(fd);
-		errno = EMFILE;
 		return (NULL);
 	}
-	iop->_file = (unsigned char)fd; /* assume fits in unsigned char */
+	iop->_flag = fflag;
 #endif	/*	_LP64	*/
 
-	FLOCKFILE(lk, iop);		/* this lock may be unnecessary */
-
-#ifdef	_LP64
-	iop->_flag &= ~0377;	/* clear lower 8-bits */
-	if (plus == '+')
-		iop->_flag |= _IORW;
-	else if (type[0] == 'r')
-		iop->_flag |= _IOREAD;
-	else
-		iop->_flag |= _IOWRT;
-#else
-	if (plus == '+')
-		iop->_flag = _IORW;
-	else if (type[0] == 'r')
-		iop->_flag = _IOREAD;
-	else
-		iop->_flag = _IOWRT;
-#endif	/*	_LP64	*/
-	FUNLOCKFILE(lk);
 	if (oflag == (O_WRONLY | O_APPEND | O_CREAT)) {	/* type == "a" */
 		if (lseek64(fd, (off64_t)0, SEEK_END) < (off64_t)0) {
 			(void) close(fd);
--- a/usr/src/lib/libc/port/stdio/_filbuf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/_filbuf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #pragma weak _filbuf = __filbuf
 
@@ -117,7 +117,7 @@
 		nbyte = 1;
 	else
 		nbyte = endbuf - iop->_base;
-	if ((res = read(iop->_file, (char *)iop->_base, nbyte)) > 0) {
+	if ((res = read(GET_FD(iop), (char *)iop->_base, nbyte)) > 0) {
 		iop->_cnt = res - 1;
 		return (*iop->_ptr++);
 	}
--- a/usr/src/lib/libc/port/stdio/_findbuf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/_findbuf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #define	_LARGEFILE64_SOURCE	1
 
@@ -51,7 +51,7 @@
 Uchar *
 _findbuf(FILE *iop)
 {
-	int fd = iop->_file;
+	int fd = GET_FD(iop);
 	Uchar *buf;
 	int size = BUFSIZ;
 	Uchar *endbuf;
--- a/usr/src/lib/libc/port/stdio/_flsbuf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/_flsbuf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #pragma weak _flsbuf = __flsbuf
 #include "synonyms.h"
@@ -71,7 +71,7 @@
 		case _IONBF | _IOWRT:	/* okay to do no-buffered case */
 			iop->_cnt = 0;
 			uch = (unsigned char)ch;
-			if (write(iop->_file, (char *)&uch, 1) != 1)
+			if (write(GET_FD(iop), (char *)&uch, 1) != 1)
 				iop->_flag |= _IOERR;
 			goto out;
 		}
--- a/usr/src/lib/libc/port/stdio/fdopen.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/fdopen.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -25,11 +24,10 @@
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
 
 /*
  * Unix routine to do an "fopen" on file descriptor
@@ -62,28 +60,14 @@
 	char plus;
 	unsigned char flag;
 
-
 	/* Sets EBADF for bad fds */
 	if (fcntl(fd, F_GETFD) == -1)
 		return (NULL);
 
-#ifdef	_LP64
 	if ((iop = _findiop()) == 0) {
 		errno = ENOMEM;
 		return (NULL);
 	}
-	iop->_file = fd;
-#else
-	if (fd > UCHAR_MAX) {
-		errno = EMFILE;
-		return (NULL);
-	}
-	if ((iop = _findiop()) == 0) {
-		errno = ENOMEM;
-		return (NULL);
-	}
-	iop->_file = (unsigned char)fd;
-#endif	/*	_LP64	*/
 
 	switch (type[0]) {
 	default:
@@ -106,5 +90,17 @@
 		flag = _IORW;
 	iop->_flag = flag;
 
+#ifdef	_LP64
+	iop->_file = fd;
+#else
+	if (fd <= _FILE_FD_MAX) {
+		SET_FILE(iop, fd);
+	} else if (_file_set(iop, fd, type) != 0) {
+		/* errno set by _file_set () */
+		iop->_flag = 0;		/* release iop */
+		return (NULL);
+	}
+#endif	/*	_LP64	*/
+
 	return (iop);
 }
--- a/usr/src/lib/libc/port/stdio/fileno.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/fileno.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -44,5 +43,5 @@
 int
 _fileno(FILE *iop)
 {
-	return (iop->_file);
+	return (GET_FD(iop));
 }
--- a/usr/src/lib/libc/port/stdio/flush.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/flush.c	Thu Apr 20 08:17:22 2006 -0700
@@ -33,6 +33,7 @@
 #include "synonyms.h"
 #include "mtlib.h"
 #include "file64.h"
+#include "../gen/_libc_gettext.h"
 
 #define	_iob	__iob
 
@@ -48,6 +49,7 @@
 #include <sys/stat.h>
 #include <stddef.h>
 #include <errno.h>
+#include <fcntl.h>
 
 #undef end
 
@@ -63,6 +65,8 @@
 #define	FPDECL(fp)		FILE *fp
 #define	FIRSTFP(lp, fp)		fp = lp->iobp
 #define	NEXTFP(fp)		fp++
+#define	FPLOCK(fp)		&fp->_lock
+#define	FPSTATE(fp)		&fp->_state
 
 #define	xFILE			FILE
 
@@ -72,6 +76,10 @@
 #define	FIRSTFP(lp, fp)		x##fp = lp->iobp; \
 				fp = x##fp ? &x##fp->_iob : &_iob[0]
 #define	NEXTFP(fp)		(x##fp ? fp = &(++x##fp)->_iob : ++fp)
+#define	FPLOCK(fp)		x##fp ? \
+				    &x##fp->xlock : &_xftab[IOPIND(fp)]._lock
+#define	FPSTATE(fp)		x##fp ? \
+				    &x##fp->xstate : &_xftab[IOPIND(fp)]._state
 
 /* The extended 32-bit file structure for use in link buffers */
 typedef struct xFILE {
@@ -135,18 +143,10 @@
 static int fcloses;
 static int nchunks;
 
-static rwlock_t _first_link_lock = DEFAULTRWLOCK;
-
-static int _fflush_u_iops(void);
-static FILE *getiop(FILE *, rmutex_t *, mbstate_t *);
+static mutex_t _first_link_lock = DEFAULTMUTEX;
 
-#define	GETIOP(fp, lk, mb)	{FILE *ret; \
-	if ((ret = getiop((fp), __libc_threaded? (lk): NULL, (mb))) != NULL) { \
-		if (__libc_threaded) \
-			(void) __rw_unlock(&_first_link_lock); \
-		return (ret); \
-	}; \
-	}
+static int _fflush_l_iops(void);
+static FILE *getiop(FILE *, rmutex_t *, mbstate_t *);
 
 /*
  * All functions that understand the linked list of iob's follow.
@@ -164,7 +164,7 @@
 void
 stdio_locks()
 {
-	(void) __rw_wrlock(&_first_link_lock);
+	(void) __mutex_lock(&_first_link_lock);
 	/*
 	 * XXX: We should acquire all of the iob locks here.
 	 */
@@ -176,7 +176,7 @@
 	/*
 	 * XXX: We should release all of the iob locks here.
 	 */
-	(void) __rw_unlock(&_first_link_lock);
+	(void) __mutex_unlock(&_first_link_lock);
 }
 
 void
@@ -185,22 +185,43 @@
 	FPDECL(fp);
 	int i;
 	struct _link_ *lp;
+	/* Allow compiler to optimize the loop */
+	int threaded = __libc_threaded;
 
-	if (__libc_threaded)
-		(void) __rw_rdlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_lock(&_first_link_lock);
 
 	lp = &__first_link;
 	do {
 		FIRSTFP(lp, fp);
 		for (i = lp->niob; --i >= 0; NEXTFP(fp)) {
-			if ((fp->_flag & (_IOLBF | _IOWRT)) ==
-			    (_IOLBF | _IOWRT))
-				(void) _fflush_u(fp);
+			/*
+			 * The additional _IONBF check guards againsts
+			 * allocated but uninitialized iops (see _findiop).
+			 * We also automatically skip non allocated iop's.
+			 * Don't block on locks.
+			 */
+			if ((fp->_flag & (_IOLBF | _IOWRT | _IONBF)) ==
+			    (_IOLBF | _IOWRT)) {
+				if (threaded) {
+					rmutex_t *lk = FPLOCK(fp);
+					if (rmutex_trylock(lk) != 0)
+						continue;
+					/* Recheck after locking */
+					if ((fp->_flag & (_IOLBF | _IOWRT)) ==
+					    (_IOLBF | _IOWRT)) {
+						(void) _fflush_u(fp);
+					}
+					(void) rmutex_unlock(lk);
+				} else {
+					(void) _fflush_u(fp);
+				}
+			}
 		}
 	} while ((lp = lp->next) != NULL);
 
-	if (__libc_threaded)
-		(void) __rw_unlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_unlock(&_first_link_lock);
 }
 
 /* allocate an unused stream; NULL if cannot */
@@ -232,9 +253,10 @@
 	struct _link_ *hdr;
 	FPDECL(fp);
 	int i;
+	int threaded = __libc_threaded;
 
-	if (__libc_threaded)
-		(void) __rw_wrlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_lock(&_first_link_lock);
 
 	if (lastlink == NULL) {
 rescan:
@@ -258,13 +280,18 @@
 		FIRSTFP(lp, fp);
 
 		for (i = lp->niob; --i >= 0; NEXTFP(fp)) {
-#ifdef	_LP64
-			GETIOP(fp, &fp->_lock, &fp->_state);
-#else
-			GETIOP(fp,
-			    xfp ? &xfp->xlock : &_xftab[IOPIND(fp)]._lock,
-			    xfp ? &xfp->xstate : &_xftab[IOPIND(fp)]._state);
-#endif	/*	_LP64	*/
+			FILE *ret;
+			if (threaded) {
+				ret = getiop(fp, FPLOCK(fp), FPSTATE(fp));
+				if (ret != NULL) {
+				    (void) __mutex_unlock(&_first_link_lock);
+				    return (ret);
+				}
+			} else {
+				ret = getiop(fp, NULL, FPSTATE(fp));
+				if (ret != NULL)
+					return (ret);
+			}
 		}
 	} while ((lastlink = lp = lp->next) != NULL);
 
@@ -288,8 +315,8 @@
 	 * Need to allocate another and put it in the linked list.
 	 */
 	if ((pkgp = malloc(sizeof (Pkg))) == NULL) {
-		if (__libc_threaded)
-			(void) __rw_unlock(&_first_link_lock);
+		if (threaded)
+			(void) __mutex_unlock(&_first_link_lock);
 		return (NULL);
 	}
 
@@ -355,8 +382,8 @@
 	fp->_ptr = 0;
 	fp->_base = 0;
 	fp->_flag = 0377; /* claim the fp by setting low 8 bits */
-	if (__libc_threaded)
-		(void) __rw_unlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_unlock(&_first_link_lock);
 
 	return (fp);
 }
@@ -369,7 +396,7 @@
 
 	save_errno = errno;
 
-	if (fstat64(iop->_file, &fstatbuf) != 0) {
+	if (fstat64(GET_FD(iop), &fstatbuf) != 0) {
 		/*
 		 * when we don't know what it is we'll
 		 * do the old behaviour and flush
@@ -452,8 +479,8 @@
 	 * old _bufend macro.  This is *so* broken, fileno()
 	 * is not the proper index.
 	 */
-	if (iop->_file < _NFILE)
-		_bufendtab[iop->_file] = end;
+	if (iop->_magic < _NFILE)
+		_bufendtab[iop->_magic] = end;
 
 }
 
@@ -523,8 +550,9 @@
 		_bufsync(iop, bufend);
 
 	if (n > 0) {
+		int fd = GET_FD(iop);
 		while ((num_wrote =
-			write(iop->_file, base, (size_t)n)) != n) {
+			write(fd, base, (size_t)n)) != n) {
 			if (num_wrote <= 0) {
 				iop->_flag |= _IOERR;
 				return (EOF);
@@ -548,56 +576,86 @@
 		res = _fflush_u(iop);
 		FUNLOCKFILE(lk);
 	} else {
-		res = _fflush_u_iops();		/* flush all iops */
+		res = _fflush_l_iops();		/* flush all iops */
 	}
 	return (res);
 }
 
 static int
-_fflush_u_iops(void)		/* flush all buffers */
+_fflush_l_iops(void)		/* flush all buffers */
 {
 	FPDECL(iop);
 
 	int i;
 	struct _link_ *lp;
 	int res = 0;
+	rmutex_t *lk;
+	/* Allow the compiler to optimize the load out of the loop */
+	int threaded = __libc_threaded;
 
-	if (__libc_threaded)
-		(void) __rw_rdlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_lock(&_first_link_lock);
 
 	lp = &__first_link;
 
 	do {
 		/*
-		 * Don't grab the locks for these file pointers
-		 * since they are supposed to be flushed anyway
-		 * It could also be the case in which the 2nd
-		 * portion (base and lock) are not initialized
+		 * We need to grab the file locks or file corruption
+		 * will happen.  But we first check the flags field
+		 * knowing that when it is 0, it isn't allocated and
+		 * cannot be allocated while we're holding the
+		 * _first_link_lock.  And when _IONBF is set (also the
+		 * case when _flag is 0377, or alloc in progress), we
+		 * also ignore it.
+		 *
+		 * Ignore locked streams; it will appear as if
+		 * concurrent updates happened after fflush(NULL).  Note
+		 * that we even attempt to lock if the locking is set to
+		 * "by caller".  We don't want to penalize callers of
+		 * __fsetlocking() by not flushing their files.  Note: if
+		 * __fsetlocking() callers don't employ any locking, they
+		 * may still face corruption in fflush(NULL); but that's
+		 * no change from earlier releases.
 		 */
 		FIRSTFP(lp, iop);
 		for (i = lp->niob; --i >= 0; NEXTFP(iop)) {
-		    if (!(iop->_flag & _IONBF)) {
-			/*
-			 * don't need to worry about the _IORW case
-			 * since the iop will also marked with _IOREAD
-			 * or _IOWRT whichever we are really doing
-			 */
-			if (iop->_flag & _IOWRT) {    /* flush write buffers */
-			    res |= _fflush_u(iop);
-			} else if (iop->_flag & _IOREAD) {
+			unsigned int flag = iop->_flag;
+
+			/* flag 0, flag 0377, or _IONBF set */
+			if (flag == 0 || (flag & _IONBF) != 0)
+				continue;
+
+			if (threaded) {
+				lk = FPLOCK(iop);
+				if (rmutex_trylock(lk) != 0)
+					continue;
+			}
+
+			if (!(iop->_flag & _IONBF)) {
 				/*
-				 * flush seekable read buffers
-				 * don't flush non-seekable read buffers
+				 * don't need to worry about the _IORW case
+				 * since the iop will also marked with _IOREAD
+				 * or _IOWRT whichever we are really doing
 				 */
-			    if (GET_SEEKABLE(iop)) {
-				res |= _fflush_u(iop);
-			    }
+				if (iop->_flag & _IOWRT) {
+					/* Flush write buffers */
+					res |= _fflush_u(iop);
+				} else if (iop->_flag & _IOREAD) {
+					/*
+					 * flush seekable read buffers
+					 * don't flush non-seekable read buffers
+					 */
+					if (GET_SEEKABLE(iop)) {
+						res |= _fflush_u(iop);
+					}
+				}
 			}
-		    }
+			if (threaded)
+				(void) rmutex_unlock(lk);
 		}
 	} while ((lp = lp->next) != NULL);
-	if (__libc_threaded)
-		(void) __rw_unlock(&_first_link_lock);
+	if (threaded)
+		(void) __mutex_unlock(&_first_link_lock);
 	return (res);
 }
 
@@ -609,7 +667,7 @@
 
 	/* this portion is always assumed locked */
 	if (!(iop->_flag & _IOWRT)) {
-		(void) lseek64(iop->_file, -iop->_cnt, SEEK_CUR);
+		(void) lseek64(GET_FD(iop), -iop->_cnt, SEEK_CUR);
 		iop->_cnt = 0;
 		/* needed for ungetc & multibyte pushbacks */
 		iop->_ptr = iop->_base;
@@ -647,7 +705,7 @@
 	/* Is not unbuffered and opened for read and/or write ? */
 	if (!(iop->_flag & _IONBF) && (iop->_flag & (_IOWRT | _IOREAD | _IORW)))
 		res = _fflush_u(iop);
-	if (close(iop->_file) < 0)
+	if (close(GET_FD(iop)) < 0)
 		res = EOF;
 	if (iop->_flag & _IOMYBUF) {
 		(void) free((char *)iop->_base - PUSHBACK);
@@ -659,10 +717,10 @@
 	FUNLOCKFILE(lk);
 
 	if (__libc_threaded)
-		(void) __rw_wrlock(&_first_link_lock);
+		(void) __mutex_lock(&_first_link_lock);
 	fcloses++;
 	if (__libc_threaded)
-		(void) __rw_unlock(&_first_link_lock);
+		(void) __mutex_unlock(&_first_link_lock);
 
 	return (res);
 }
@@ -679,7 +737,7 @@
 	/* Is not unbuffered and opened for read and/or write ? */
 	if (!(iop->_flag & _IONBF) && (iop->_flag & (_IOWRT | _IOREAD | _IORW)))
 		res = _fflush_u(iop);
-	if (close(iop->_file) < 0)
+	if (close(GET_FD(iop)) < 0)
 		res = EOF;
 	if (iop->_flag & _IOMYBUF) {
 		(void) free((char *)iop->_base - PUSHBACK);
@@ -736,4 +794,109 @@
 
 	return (NULL);
 }
+
+/*
+ * More 32-bit only functions.
+ * They lookup/set large fd's for extended FILE support.
+ */
+
+/*
+ * The negative value indicates that Extended fd FILE's has not
+ * been enabled by the user.
+ */
+static int bad_fd = -1;
+
+int
+_file_get(FILE *iop)
+{
+	int altfd;
+
+	/*
+	 * Failure indicates a FILE * not allocated through stdio;
+	 * it means the flag values are probably bogus and that if
+	 * a file descriptor is set, it's in _magic.
+	 * Inline getxfdat() for performance reasons.
+	 */
+	if (STDIOP(iop))
+		altfd = _xftab[IOPIND(iop)]._altfd;
+	else if (VALIDXFILE(FILEx(iop)))
+		altfd = FILEx(iop)->_xdat._altfd;
+	else
+		return (iop->_magic);
+	/*
+	 * if this is not an internal extended FILE then check
+	 * if _file is being changed from underneath us.
+	 * It should not be because if
+	 * it is then then we lose our ability to guard against
+	 * silent data corruption.
+	 */
+	if (!iop->__xf_nocheck && bad_fd > -1 && iop->_magic != bad_fd) {
+		/* LINTED: variable format specifier */
+		(void) fprintf(stderr, _libc_gettext(
+		    "Application violated extended FILE safety mechanism.\n"
+		    "Please read the man page for extendedFILE.\nAborting\n"));
+		abort();
+	}
+	return (altfd);
+}
+
+int
+_file_set(FILE *iop, int fd, const char *type)
+{
+	struct xFILEdata *dat;
+	int Fflag;
+
+	/* Already known to contain at least one byte */
+	while (*++type != '\0')
+		;
+
+	Fflag = type[-1] == 'F';
+	if (!Fflag && bad_fd < 0) {
+		errno = EMFILE;
+		return (-1);
+	}
+
+	dat = getxfdat(iop);
+	iop->__extendedfd = 1;
+	iop->__xf_nocheck = Fflag;
+	dat->_altfd = fd;
+	iop->_magic = (unsigned char)bad_fd;
+	return (0);
+}
+
+/*
+ * Activates extended fd's in FILE's
+ */
+
+static const int tries[] = {196, 120, 60, 3};
+#define	NTRIES	(sizeof (tries)/sizeof (int))
+
+int
+enable_extended_FILE_stdio(int fd, int action)
+{
+	int i;
+
+	if (action < 0)
+		action = SIGABRT;	/* default signal */
+
+	if (fd < 0) {
+		/*
+		 * search for an available fd and make it the badfd
+		 */
+		for (i = 0; i < NTRIES; i++) {
+			fd = fcntl(tries[i], F_BADFD, action);
+			if (fd >= 0)
+				break;
+		}
+		if (fd < 0)	/* failed to find an available fd */
+			return (-1);
+	} else {
+		/* caller requests that fd be the chosen badfd */
+		int nfd = fcntl(fd, F_BADFD, action);
+		if (nfd < 0 || nfd != fd)
+			return (-1);
+	}
+	bad_fd = fd;
+	return (0);
+}
 #endif
--- a/usr/src/lib/libc/port/stdio/fputs.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/fputs.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 /*
  * Ptr args aren't checked for NULL because the program would be a
@@ -118,9 +118,9 @@
 		/* write out to an unbuffered file */
 		ssize_t num_wrote;
 		ssize_t count = (ssize_t)ptrlen;
+		int fd = GET_FD(iop);
 
-		while ((num_wrote = write(iop->_file, ptr,
-			(size_t)count)) != count) {
+		while ((num_wrote = write(fd, ptr, (size_t)count)) != count) {
 				if (num_wrote <= 0) {
 					iop->_flag |= _IOERR;
 					FUNLOCKFILE(lk);
--- a/usr/src/lib/libc/port/stdio/popen.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/popen.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #pragma weak pclose = _pclose
 #pragma weak popen = _popen
@@ -55,10 +55,6 @@
 #define	RDR	0
 #define	WTR	1
 
-#ifndef	_LP64
-#define	MAX_FD (1 << (NBBY * (unsigned)sizeof (_lastbuf->_file))) /* now 256 */
-#endif	/*	_LP64	*/
-
 static int _insert_nolock(pid_t, int);
 
 extern	int __xpg4;	/* defined in _xpg4.c; 0 if not xpg4-compiled program */
@@ -96,16 +92,6 @@
 	if (pipe(p) < 0)
 		return (NULL);
 
-#ifndef	_LP64
-	/* check that the fd's are in range for a struct FILE */
-	if ((p[WTR] >= MAX_FD) || (p[RDR] >= MAX_FD)) {
-		(void) close(p[WTR]);
-		(void) close(p[RDR]);
-		errno = EMFILE;
-		return (NULL);
-	}
-#endif	/* _LP64 */
-
 	shpath = __xpg4? xpg4_path : sun_path;
 	if (access(shpath, X_OK))	/* XPG4 Requirement: */
 		shpath = "";		/* force child to fail immediately */
@@ -115,12 +101,19 @@
 	/* myside and yourside reverse roles in child */
 	stdio = tst(0, 1);
 
+	/* This will fail more quickly if we run out of fds */
+	if ((iop = fdopen(myside, mode)) == NULL) {
+		(void) close(yourside);
+		(void) close(myside);
+		return (NULL);
+	}
+
 	lmutex_lock(&popen_lock);
 
 	/* in the child, close all pipes from other popen's */
 	if ((error = posix_spawn_file_actions_init(&fact)) != 0) {
 		lmutex_unlock(&popen_lock);
-		(void) close(myside);
+		(void) fclose(iop);
 		(void) close(yourside);
 		errno = error;
 		return (NULL);
@@ -140,7 +133,7 @@
 	if (error) {
 		lmutex_unlock(&popen_lock);
 		(void) posix_spawn_file_actions_destroy(&fact);
-		(void) close(myside);
+		(void) fclose(iop);
 		(void) close(yourside);
 		errno = error;
 		return (NULL);
@@ -156,17 +149,12 @@
 	(void) close(yourside);
 	if ((errno = error) != 0 || _insert_nolock(pid, myside) == -1) {
 		lmutex_unlock(&popen_lock);
-		(void) close(myside);
+		(void) fclose(iop);
 		return (NULL);
 	}
 
 	lmutex_unlock(&popen_lock);
 
-	if ((iop = fdopen(myside, mode)) == NULL) {
-		(void) _delete(myside);
-		(void) close(myside);
-		return (NULL);
-	}
 	_SET_ORIENTATION_BYTE(iop);
 
 	return (iop);
--- a/usr/src/lib/libc/port/stdio/setbuf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/setbuf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #include "synonyms.h"
 #include "file64.h"
@@ -45,7 +45,7 @@
 setbuf(FILE *iop, char *abuf)
 {
 	Uchar *buf = (Uchar *)abuf;
-	int fno = iop->_file;  /* file number */
+	int fno = GET_FD(iop);  /* file number */
 	int size = BUFSIZ - _SMBFSZ;
 	Uchar *temp;
 	rmutex_t *lk;
--- a/usr/src/lib/libc/port/stdio/setvbuf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/setvbuf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #include "synonyms.h"
 #include "file64.h"
@@ -48,6 +48,7 @@
 	Uchar *temp;
 	int	sflag = iop->_flag & _IOMYBUF;
 	rmutex_t *lk;
+	int fd = GET_FD(iop);
 
 	FLOCKFILE(lk, iop);
 	iop->_flag &= ~(_IOMYBUF | _IONBF | _IOLBF);
@@ -56,14 +57,14 @@
 	case _IONBF:
 		iop->_flag |= _IONBF;	 /* file is unbuffered */
 #ifndef _STDIO_ALLOCATE
-		if (iop->_file < 2) {
+		if (fd < 2) {
 			/* use special buffer for std{in,out} */
-			buf = (iop->_file == 0) ? _sibuf : _sobuf;
+			buf = (fd == 0) ? _sibuf : _sobuf;
 			size = BUFSIZ;
 		} else /* needed for ifdef */
 #endif
-		if (iop->_file < _NFILE) {
-			buf = _smbuf[iop->_file];
+		if (fd < _NFILE) {
+			buf = _smbuf[fd];
 			size = _SMBFSZ - PUSHBACK;
 		} else
 			if ((buf = malloc(_SMBFSZ * sizeof (Uchar))) != NULL) {
--- a/usr/src/lib/libc/port/stdio/vscanf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/vscanf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,16 +18,17 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 /*	Copyright (c) 1988 AT&T	*/
 /*	  All Rights Reserved  	*/
 
+#pragma ident	"%Z%%M%	%I%	%E% SMI"
+
 
 #ifndef _C89_INTMAX32
 #pragma weak vscanf = _vscanf
@@ -125,7 +125,7 @@
 	strbuf._flag = _IOREAD | _IOWRT;
 	strbuf._ptr = strbuf._base = (unsigned char *)str;
 	strbuf._cnt = strlen(str);
-	strbuf._file = _NFILE;
+	SET_FILE(&strbuf, _NFILE);
 
 	/*
 	 * Mark the stream so that routines called by __doscan_u()
--- a/usr/src/lib/libc/port/stdio/vwscanf.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/port/stdio/vwscanf.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,8 +18,9 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -132,7 +132,8 @@
 	strbuf._flag = _IOREAD | _IOWRT;
 	strbuf._ptr = strbuf._base = (unsigned char *)tmp_buf;
 	strbuf._cnt = strlen(tmp_buf);
-	strbuf._file = _NFILE;
+	SET_FILE(&strbuf, _NFILE);
+
 	/* Probably the following is not required. */
 	/* _setorientation(&strbuf, _WC_MODE); */
 
--- a/usr/src/lib/libc/spec/private.spec	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/spec/private.spec	Thu Apr 20 08:17:22 2006 -0700
@@ -1,13 +1,8 @@
-#
-# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
-# Use is subject to license terms.
-#
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -22,6 +17,9 @@
 #
 # CDDL HEADER END
 #
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
 # ident	"%Z%%M%	%I%	%E% SMI"
 #
 # lib/libc/spec/private.spec
@@ -3346,7 +3344,7 @@
 end
 
 # PSARC/2000/492 UNIX03 project
-# Bugid 4850735, functions needed to support printf/scanf variable 
+# Bugid 4850735, functions needed to support printf/scanf variable
 # sized u/intmax_t for 32-bit libc
 
 function	_fprintf_c89
@@ -3483,3 +3481,7 @@
 version		SUNWprivate_1.1
 end
 
+function	_file_set
+arch		sparc i386
+version		SUNWprivate_1.1
+end
--- a/usr/src/lib/libc/spec/stdio.spec	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/lib/libc/spec/stdio.spec	Thu Apr 20 08:17:22 2006 -0700
@@ -1,13 +1,8 @@
-#
-# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
-# Use is subject to license terms.
-#
 # CDDL HEADER START
 #
 # The contents of this file are subject to the terms of the
-# Common Development and Distribution License, Version 1.0 only
-# (the "License").  You may not use this file except in compliance
-# with the License.
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
 #
 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 # or http://www.opensolaris.org/os/licensing.
@@ -22,6 +17,9 @@
 #
 # CDDL HEADER END
 #
+# Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+# Use is subject to license terms.
+#
 # ident	"%Z%%M%	%I%	%E% SMI"
 #
 
@@ -60,6 +58,11 @@
 		amd64=SUNW_0.7
 end
 
+function	enable_extended_FILE_stdio
+arch		sparc i386
+version		sparc=SUNW_1.23 i386=SUNW_1.23
+end
+
 function	fclose
 include		<stdio.h>
 declaration	int fclose(FILE *stream)
--- a/usr/src/pkgdefs/SUNWcsl/prototype_com	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/pkgdefs/SUNWcsl/prototype_com	Thu Apr 20 08:17:22 2006 -0700
@@ -67,6 +67,7 @@
 f none usr/lib/dns/dnssafe.so.1 755 root bin
 # EXPORT DELETE END
 f none usr/lib/dns/irs.so.1 755 root bin
+f none usr/lib/extendedFILE.so.1 755 root bin
 f none usr/lib/lib.b 444 root bin
 s none usr/lib/libadm.so=../../lib/libadm.so.1
 s none usr/lib/libadm.so.1=../../lib/libadm.so.1
@@ -152,8 +153,8 @@
 f none usr/lib/libldap.so.5 755 root bin
 f none usr/lib/libldap.so.4 755 root bin
 s none usr/lib/liblddbg.so.4=../../lib/liblddbg.so.4
-s none usr/lib/liblgrp.so=./liblgrp.so.1 
-f none usr/lib/liblgrp.so.1 755 root bin 
+s none usr/lib/liblgrp.so=./liblgrp.so.1
+f none usr/lib/liblgrp.so.1 755 root bin
 s none usr/lib/liblm.so=./liblm.so.1
 f none usr/lib/liblm.so.1 755 root bin
 f none usr/lib/libmail.so.1 755 root bin
--- a/usr/src/ucblib/libucb/inc/stdiom.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/ucblib/libucb/inc/stdiom.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 1997 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -98,6 +97,12 @@
 	 */
 extern Uchar 	*_findbuf(FILE *iop);
 
+#ifndef _LP64
+extern int _file_set(FILE *, int, const char *);
+#define	SET_FILE(iop, fd)	(iop)->_magic = (fd); (iop)->__extendedfd = 0
+#define	_FILE_FD_MAX		255
+#endif
+
 /*
  * The following macros improve performance of the stdio by reducing the
  * number of calls to _bufsync and _wrtchk.  _needsync checks whether
--- a/usr/src/ucblib/libucb/port/gen/setbuffer.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/ucblib/libucb/port/gen/setbuffer.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,11 +18,6 @@
  *
  * CDDL HEADER END
  */
-/*
- * Copyright 2003 Sun Microsystems, Inc.  All rights reserved.
- * Use is subject to license terms.
- */
-
 /*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
 /*	  All Rights Reserved  	*/
 
@@ -37,6 +31,11 @@
  * contributors.
  */
 
+/*
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+ * Use is subject to license terms.
+ */
+
 #pragma ident	"%Z%%M%	%I%	%E% SMI"
 
 /*LINTLIBRARY*/
@@ -53,7 +52,7 @@
 setbuffer(FILE *iop, char *abuf, int asize)
 {
 	Uchar *buf = (Uchar *)abuf;
-	int fno = iop->_file;  /* file number */
+	int fno = fileno(iop);  /* file number */
 	int size = asize - _SMBFSZ;
 	Uchar *temp;
 
--- a/usr/src/ucblib/libucb/port/stdio/fopen.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/ucblib/libucb/port/stdio/fopen.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,8 +18,9 @@
  *
  * CDDL HEADER END
  */
+
 /*
- * Copyright 1998 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -74,6 +74,7 @@
 	default:
 		return (NULL);
 	}
+
 	if (largefile) {
 		fd = open64(file, oflag, 0666);	/* mapped to open() for V9 */
 	} else {
@@ -82,7 +83,17 @@
 	if (fd < 0)
 		return (NULL);
 	iop->_cnt = 0;
-	iop->_file = (unsigned char) fd;
+#ifdef _LP64
+	iop->_file = fd;
+#else
+	if (fd <= _FILE_FD_MAX) {
+		SET_FILE(iop, fd);
+	} else if (_file_set(iop, fd, mode) != 0) {
+		/* errno set in _file_set() */
+		(void) close(fd);
+		return (NULL);
+	}
+#endif
 	iop->_flag = plus ? _IORW : (mode[0] == 'r') ? _IOREAD : _IOWRT;
 	if (mode[0] == 'a')   {
 		if ((lseek64(fd, 0L, SEEK_END)) < 0)  {
--- a/usr/src/uts/common/os/fio.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/uts/common/os/fio.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -19,14 +18,15 @@
  *
  * CDDL HEADER END
  */
+
+/*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
+/*	All Rights Reserved */
+
 /*
  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-/*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
-/*	All Rights Reserved */
-
 #pragma ident	"%Z%%M%	%I%	%E% SMI"
 
 #include <sys/types.h>
@@ -577,6 +577,10 @@
 	UF_ENTER(ufp, fip, fd);
 	if ((fp = ufp->uf_file) == NULL) {
 		UF_EXIT(ufp);
+
+		if (fd == fip->fi_badfd && fip->fi_action > 0)
+			tsignal(curthread, fip->fi_action);
+
 		return (NULL);
 	}
 	ufp->uf_refcnt++;
@@ -599,7 +603,9 @@
  * Close whatever file currently occupies the file descriptor slot
  * and install the new file, usually NULL, in the file descriptor slot.
  * The close must complete before we release the file descriptor slot.
- * We return the error number from closef().
+ * If newfp != NULL we only return an error if we can't allocate the
+ * slot so the caller knows that it needs to free the filep;
+ * in the other cases we return the error number from closef().
  */
 int
 closeandsetf(int fd, file_t *newfp)
@@ -626,6 +632,12 @@
 		 * new non-NULL file pointer.
 		 */
 		mutex_enter(&fip->fi_lock);
+		if (fd == fip->fi_badfd) {
+			mutex_exit(&fip->fi_lock);
+			if (fip->fi_action > 0)
+				tsignal(curthread, fip->fi_action);
+			return (EBADF);
+		}
 		UF_ENTER(ufp, fip, fd);
 		while (ufp->uf_busy && ufp->uf_file == NULL) {
 			mutex_exit(&fip->fi_lock);
@@ -755,7 +767,8 @@
 
 	setf(fd, newfp);
 
-	return (error);
+	/* Only return closef() error when closing is all we do */
+	return (newfp == NULL ? error : 0);
 }
 
 /*
@@ -950,6 +963,11 @@
 	for (;;) {
 		mutex_enter(&fip->fi_lock);
 		fd = fd_find(fip, start);
+		if (fd >= 0 && fd == fip->fi_badfd) {
+			start = fd + 1;
+			mutex_exit(&fip->fi_lock);
+			continue;
+		}
 		if ((uint_t)fd < filelimit)
 			break;
 		if (fd >= filelimit) {
@@ -1255,6 +1273,66 @@
 	(void) f_setfd_error(fd, flags);
 }
 
+#define	BADFD_MIN	3
+#define	BADFD_MAX	255
+
+/*
+ * Attempt to allocate a file descriptor which is bad and which
+ * is "poison" to the application.  It cannot be closed (except
+ * on exec), allocated for a different use, etc.
+ */
+int
+f_badfd(int start, int *fdp, int action)
+{
+	int fdr;
+	int badfd;
+	uf_info_t *fip = P_FINFO(curproc);
+
+#ifdef _LP64
+	/* No restrictions on 64 bit _file */
+	if (get_udatamodel() != DATAMODEL_ILP32)
+		return (EINVAL);
+#endif
+
+	if (start > BADFD_MAX || start < BADFD_MIN)
+		return (EINVAL);
+
+	if (action >= NSIG || action < 0)
+		return (EINVAL);
+
+	mutex_enter(&fip->fi_lock);
+	badfd = fip->fi_badfd;
+	mutex_exit(&fip->fi_lock);
+
+	if (badfd != -1)
+		return (EAGAIN);
+
+	fdr = ufalloc(start);
+
+	if (fdr > BADFD_MAX) {
+		setf(fdr, NULL);
+		return (EMFILE);
+	}
+	if (fdr < 0)
+		return (EMFILE);
+
+	mutex_enter(&fip->fi_lock);
+	if (fip->fi_badfd != -1) {
+		/* Lost race */
+		mutex_exit(&fip->fi_lock);
+		setf(fdr, NULL);
+		return (EAGAIN);
+	}
+	fip->fi_action = action;
+	fip->fi_badfd = fdr;
+	mutex_exit(&fip->fi_lock);
+	setf(fdr, NULL);
+
+	*fdp = fdr;
+
+	return (0);
+}
+
 /*
  * Allocate a file descriptor and assign it to the vnode "*vpp",
  * performing the usual open protocol upon it and returning the
@@ -1360,6 +1438,10 @@
 			(void) closef(fp);
 		}
 	}
+
+	/* Reset bad fd */
+	fip->fi_badfd = -1;
+	fip->fi_action = -1;
 }
 
 /*
--- a/usr/src/uts/common/sys/fcntl.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/uts/common/sys/fcntl.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -196,6 +195,8 @@
 #define	F_UNSHARE	41	/* Remove a file share reservation */
 #define	F_SHARE_NBMAND	43	/* private */
 
+#define	F_BADFD		46	/* Create Poison FD */
+
 /*
  * File segment locking set data type - information passed to system by user.
  */
--- a/usr/src/uts/common/sys/file.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/uts/common/sys/file.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -24,7 +23,7 @@
 
 
 /*
- * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -193,6 +192,7 @@
 extern int f_setfd_error(int, int);
 extern void f_setfd(int, char);
 extern int f_getfl(int, int *);
+extern int f_badfd(int, int *, int);
 extern int fassign(struct vnode **, int, int *);
 extern void fcnt_add(uf_info_t *, int);
 extern void close_exec(uf_info_t *);
--- a/usr/src/uts/common/sys/user.h	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/uts/common/sys/user.h	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -117,7 +116,8 @@
  */
 typedef struct uf_info {
 	kmutex_t	fi_lock;	/* see below */
-	kmutex_t	fi_pad;		/* unused -- remove in next release */
+	int		fi_badfd;	/* bad file descriptor # */
+	int		fi_action;	/* action to take on bad fd use */
 	int		fi_nfiles;	/* number of entries in fi_list[] */
 	uf_entry_t *volatile fi_list;	/* current file list */
 	uf_rlist_t	*fi_rlist;	/* retired file lists */
--- a/usr/src/uts/common/syscall/fcntl.c	Thu Apr 20 00:16:01 2006 -0700
+++ b/usr/src/uts/common/syscall/fcntl.c	Thu Apr 20 08:17:22 2006 -0700
@@ -2,9 +2,8 @@
  * CDDL HEADER START
  *
  * The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License").  You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
  *
  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  * or http://www.opensolaris.org/os/licensing.
@@ -21,7 +20,7 @@
  */
 /* ONC_PLUS EXTRACT START */
 /*
- * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -89,6 +88,7 @@
 	struct shr_locowner shr_own;
 	offset_t maxoffset;
 	model_t datamodel;
+	int fdres;
 
 #if defined(_ILP32) && !defined(lint) && defined(_SYSCALL32)
 	ASSERT(sizeof (struct flock) == sizeof (struct flock32));
@@ -123,6 +123,11 @@
 		if ((error = f_getfl(fdes, &flag)) == 0)
 			retval = flag + FOPEN;
 		goto out;
+
+	case F_BADFD:
+		if ((error = f_badfd(fdes, &fdres, (int)arg)) == 0)
+			retval = fdres;
+		goto out;
 	}
 
 	/*
@@ -172,13 +177,25 @@
 			 * (which we have to do anyway), then releasef(fdes),
 			 * then closeandsetf().  Incrementing f_count ensures
 			 * that fp won't disappear after we call releasef().
+			 * When closeandsetf() fails, we try avoid calling
+			 * closef() because of all the side effects.
 			 */
 			mutex_enter(&fp->f_tlock);
 			fp->f_count++;
 			mutex_exit(&fp->f_tlock);
 			releasef(fdes);
-			(void) closeandsetf(iarg, fp);
-			retval = iarg;
+			if ((error = closeandsetf(iarg, fp)) == 0) {
+				retval = iarg;
+			} else {
+				mutex_enter(&fp->f_tlock);
+				if (fp->f_count > 1) {
+					fp->f_count--;
+					mutex_exit(&fp->f_tlock);
+				} else {
+					mutex_exit(&fp->f_tlock);
+					(void) closef(fp);
+				}
+			}
 			goto out;
 		}
 		goto done;