Create a small library function, check_utility_compat(3), to determine
whether a named utility should behave in FreeBSD 4.x-compatible mode or in a standard mode (default standard). The configuration is done malloc(3)-style, with either an environment variable or a symlink. Update expr(1) to use this new interface.
This commit is contained in:
parent
092b51aeec
commit
d47f5a7e94
@ -121,9 +121,23 @@ otherwise 0.
|
||||
.Pp
|
||||
Parentheses are used for grouping in the usual manner.
|
||||
.Pp
|
||||
Unless the
|
||||
.Ev EXPR_COMPAT
|
||||
variable is defined in the process environment, this version of
|
||||
The
|
||||
.Nm
|
||||
utility makes no lexical distinction between arguments which may be
|
||||
operators and arguments which may be operands.
|
||||
An operand which is lexically identical to an operator will be considered a
|
||||
syntax error.
|
||||
See the examples below for a work-around.
|
||||
.Pp
|
||||
The syntax of the
|
||||
.Nm
|
||||
command in general is historic and inconvenient.
|
||||
New applications are advised to use shell arithmetic rather than
|
||||
.Nm .
|
||||
.Ss Compatibility with previous implementations
|
||||
Unless
|
||||
.Fx 4.x
|
||||
compatibility is enabled, this version of
|
||||
.Nm
|
||||
adheres to the
|
||||
\*[Px]
|
||||
@ -140,43 +154,31 @@ will not permit this syntax.
|
||||
See the examples below for portable ways to guarantee the correct
|
||||
interpretation.
|
||||
The
|
||||
.Ev EXPR_COMPAT
|
||||
variable is intended for use as a transition and debugging aid, when
|
||||
.Xr check_utility_compat 3
|
||||
function (with a
|
||||
.Fa utility
|
||||
argument of
|
||||
.Dq Li expr )
|
||||
is used to determine whether compatibility mode should be enabled.
|
||||
This feature is intended for use as a transition and debugging aid, when
|
||||
.Nm
|
||||
is used in complex scripts which cannot easily be recast to avoid the
|
||||
non-portable usage.
|
||||
Defining
|
||||
.Ev EXPR_COMPAT
|
||||
Enabling compatibility mode
|
||||
also implicitly enables the
|
||||
.Fl e
|
||||
option, since this matches the historic behavior of
|
||||
.Nm
|
||||
in
|
||||
.Fx .
|
||||
For historical reasons, defining the environment variable
|
||||
.Ev EXPR_COMPAT
|
||||
also enables compatibility mode.
|
||||
.Pp
|
||||
The
|
||||
.Nm
|
||||
utility makes no lexical distinction between arguments which may be
|
||||
operators and arguments which may be operands.
|
||||
An operand which is lexically identical to an operator will be considered a
|
||||
syntax error.
|
||||
See the examples below for a work-around.
|
||||
.Pp
|
||||
The syntax of the
|
||||
.Nm
|
||||
command in general is historic and inconvenient.
|
||||
New applications are advised to use shell arithmetic rather than
|
||||
.Nm .
|
||||
.Sh ENVIRONMENT
|
||||
.Bl -tag -width ".Ev EXPR_COMPAT"
|
||||
.It Ev EXPR_COMPAT
|
||||
If set,
|
||||
.Nm
|
||||
will emulate historic
|
||||
.Nm
|
||||
implementations which did not obey the Utility Syntax Guidelines.
|
||||
Implies
|
||||
.Fl e .
|
||||
If set, enables compatibility mode.
|
||||
.El
|
||||
.Sh EXAMPLES
|
||||
.Bl -bullet
|
||||
@ -248,15 +250,14 @@ the expression is invalid.
|
||||
.El
|
||||
.Sh SEE ALSO
|
||||
.Xr sh 1 ,
|
||||
.Xr test 1
|
||||
.Xr test 1 ,
|
||||
.Xr check_utility_compat 3
|
||||
.Sh STANDARDS
|
||||
The
|
||||
.Nm
|
||||
utility conforms to
|
||||
.St -p1003.1-2001 ,
|
||||
provided that the
|
||||
.Ev EXPR_COMPAT
|
||||
environment variable is not defined.
|
||||
provided that compatibility mode is not enabled.
|
||||
The
|
||||
.Fl e
|
||||
flag is an extension.
|
||||
|
@ -278,7 +278,8 @@ main(int argc, char *argv[])
|
||||
int c;
|
||||
|
||||
setlocale (LC_ALL, "");
|
||||
if (getenv("EXPR_COMPAT") != NULL) {
|
||||
if (getenv("EXPR_COMPAT") != NULL
|
||||
|| check_utility_compat("expr")) {
|
||||
av = argv + 1;
|
||||
eflag = 1;
|
||||
} else {
|
||||
|
@ -437,6 +437,7 @@ struct timeval; /* select(2) */
|
||||
int acct(const char *);
|
||||
int async_daemon(void);
|
||||
int brk(const void *);
|
||||
int check_utility_compat(const char *);
|
||||
int chroot(const char *);
|
||||
const char *
|
||||
crypt_get_format(void);
|
||||
|
@ -5,7 +5,7 @@
|
||||
.PATH: ${.CURDIR}/../libc/${MACHINE_ARCH}/gen ${.CURDIR}/../libc/gen
|
||||
|
||||
SRCS+= __xuname.c _pthread_stubs.c _rand48.c _spinlock_stub.c _thread_init.c \
|
||||
alarm.c arc4random.c assert.c basename.c \
|
||||
alarm.c arc4random.c assert.c basename.c check_utility_compat.c \
|
||||
clock.c closedir.c confstr.c \
|
||||
crypt.c ctermid.c daemon.c devname.c dirname.c disklabel.c \
|
||||
dlfcn.c dlfunc.c drand48.c erand48.c err.c errlst.c errno.c \
|
||||
@ -38,7 +38,7 @@ SRCS+= __xuname.c _pthread_stubs.c _rand48.c _spinlock_stub.c _thread_init.c \
|
||||
|
||||
.if ${LIB} == "c"
|
||||
MAN+= alarm.3 arc4random.3 \
|
||||
basename.3 clock.3 \
|
||||
basename.3 check_utility_compat.3 clock.3 \
|
||||
confstr.3 ctermid.3 daemon.3 \
|
||||
devname.3 directory.3 dirname.3 dladdr.3 dllockinit.3 dlopen.3 \
|
||||
err.3 exec.3 fmtcheck.3 fmtmsg.3 fnmatch.3 frexp.3 ftok.3 fts.3 \
|
||||
|
89
lib/libc/gen/check_utility_compat.3
Normal file
89
lib/libc/gen/check_utility_compat.3
Normal file
@ -0,0 +1,89 @@
|
||||
.\"
|
||||
.\" Copyright 2002 Massachusetts Institute of Technology
|
||||
.\"
|
||||
.\" Permission to use, copy, modify, and distribute this software and
|
||||
.\" its documentation for any purpose and without fee is hereby
|
||||
.\" granted, provided that both the above copyright notice and this
|
||||
.\" permission notice appear in all copies, that both the above
|
||||
.\" copyright notice and this permission notice appear in all
|
||||
.\" supporting documentation, and that the name of M.I.T. not be used
|
||||
.\" in advertising or publicity pertaining to distribution of the
|
||||
.\" software without specific, written prior permission. M.I.T. makes
|
||||
.\" no representations about the suitability of this software for any
|
||||
.\" purpose. It is provided "as is" without express or implied
|
||||
.\" warranty.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY M.I.T. ``AS IS''. M.I.T. DISCLAIMS
|
||||
.\" ALL EXPRESS OR IMPLIED WARRANTIES WITH REGARD TO THIS SOFTWARE,
|
||||
.\" INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT
|
||||
.\" SHALL M.I.T. BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
.\" SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
.\" LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
|
||||
.\" USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
.\" ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
.\" OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
|
||||
.\" OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.\" $FreeBSD$
|
||||
.\"
|
||||
.Dd October 27, 2002
|
||||
.Dt CHECK_UTILITY_COMPAT 3
|
||||
.Os
|
||||
.Sh MAME
|
||||
.Nm check_utility_compat
|
||||
.Nd "determine whether a utility should be compatible"
|
||||
.Sh LIBRARY
|
||||
.Lb libc
|
||||
.Sh SYNOPSIS
|
||||
.In unistd.h
|
||||
.Ft int
|
||||
.Fn check_utility_compat "const char *utility"
|
||||
.Sh DESCRIPTION
|
||||
The
|
||||
.Nm
|
||||
function checks whether
|
||||
.Fa utility
|
||||
should behave in a traditional
|
||||
.Pq Fx 4.7 -compatible
|
||||
manner, or in accordance with
|
||||
.St -p1003.1-2001 .
|
||||
The configuration is given as a comma-separated list of utility names;
|
||||
if the list is present but empty, all supported utilities assume their
|
||||
most compatible mode.
|
||||
The
|
||||
.Nm
|
||||
function first checks for an environment variable named
|
||||
.Ev _COMPAT_FreeBSD_4 .
|
||||
If that environment variable does not exist, then
|
||||
.Nm
|
||||
will attempt to read the contents of a symbolic link named
|
||||
.Pa /etc/compat-FreeBSD-4-util .
|
||||
If no configuration is found, compatibility mode is disabled.
|
||||
.Sh RETURN VALUES
|
||||
The
|
||||
.Nm
|
||||
function returns zero if
|
||||
.Fa utility
|
||||
should implement strict
|
||||
.St -p1003.1-2001
|
||||
behavior, and nonzero otherwise.
|
||||
.Sh ERRORS
|
||||
No errors are detected.
|
||||
.Sh FILES
|
||||
.Bl -tag -offset indent -width Pa
|
||||
.It Pa /etc/compat-FreeBSD-4-util
|
||||
If present, a symbolic link whose expansion gives system-wide default settings
|
||||
for the
|
||||
.Nm
|
||||
function.
|
||||
.El
|
||||
.Sh HISTORY
|
||||
The
|
||||
.Nm
|
||||
function first appeared in
|
||||
.Fx 5.0 .
|
||||
.Sh AUTHOR
|
||||
This manual page was written by
|
||||
.An Garrett Wollman Aq wollman@FreeBSD.org .
|
75
lib/libc/gen/check_utility_compat.c
Normal file
75
lib/libc/gen/check_utility_compat.c
Normal file
@ -0,0 +1,75 @@
|
||||
/*
|
||||
* Copyright 2002 Massachusetts Institute of Technology
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software and
|
||||
* its documentation for any purpose and without fee is hereby
|
||||
* granted, provided that both the above copyright notice and this
|
||||
* permission notice appear in all copies, that both the above
|
||||
* copyright notice and this permission notice appear in all
|
||||
* supporting documentation, and that the name of M.I.T. not be used
|
||||
* in advertising or publicity pertaining to distribution of the
|
||||
* software without specific, written prior permission. M.I.T. makes
|
||||
* no representations about the suitability of this software for any
|
||||
* purpose. It is provided "as is" without express or implied
|
||||
* warranty.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY M.I.T. ``AS IS''. M.I.T. DISCLAIMS
|
||||
* ALL EXPRESS OR IMPLIED WARRANTIES WITH REGARD TO THIS SOFTWARE,
|
||||
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT
|
||||
* SHALL M.I.T. BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
|
||||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
|
||||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD$");
|
||||
|
||||
/*
|
||||
* I din't use "namespace.h" here because none of the relevant utilities
|
||||
* are threaded, so I'm not concerned about cancellation points or other
|
||||
* niceties.
|
||||
*/
|
||||
#include <limits.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#ifndef LINE_MAX
|
||||
#define LINE_MAX _POSIX2_LINE_MAX
|
||||
#endif
|
||||
|
||||
#define _PATH_UTIL_COMPAT "/etc/compat-FreeBSD-4-util"
|
||||
#define _ENV_UTIL_COMPAT "_COMPAT_FreeBSD_4"
|
||||
|
||||
int
|
||||
check_utility_compat(const char *utility)
|
||||
{
|
||||
char buf[LINE_MAX];
|
||||
char *p, *bp;
|
||||
int len;
|
||||
|
||||
if ((p = getenv(_ENV_UTIL_COMPAT)) != NULL) {
|
||||
strlcpy(buf, p, sizeof buf);
|
||||
} else {
|
||||
if ((len = readlink(_PATH_UTIL_COMPAT, buf, sizeof buf)) < 0)
|
||||
return 0;
|
||||
if (len > sizeof buf)
|
||||
len = sizeof buf;
|
||||
buf[len] = '\0';
|
||||
}
|
||||
if (buf[0] == '\0')
|
||||
return 1;
|
||||
|
||||
bp = buf;
|
||||
while ((p = strsep(&bp, ",")) != NULL) {
|
||||
if (strcmp(p, utility) == 0)
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
Loading…
Reference in New Issue
Block a user