summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorjtc <jtc@NetBSD.org>1993-11-11 03:21:21 +0000
committerjtc <jtc@NetBSD.org>1993-11-11 03:21:21 +0000
commitbc692825eebdadeecddbbaf6f23cb2637d5a28ca (patch)
tree2107445007138a35945d6ae0eb91488379066f57
parent5e1b956859931f4f0bebdaf749121c117dc766c2 (diff)
Implement the FNM_PERIOD flag.
-rw-r--r--lib/libc/gen/fnmatch.37
-rw-r--r--lib/libc/gen/fnmatch.c26
2 files changed, 20 insertions, 13 deletions
diff --git a/lib/libc/gen/fnmatch.3 b/lib/libc/gen/fnmatch.3
index abb6cf24c47..28fcda65f7d 100644
--- a/lib/libc/gen/fnmatch.3
+++ b/lib/libc/gen/fnmatch.3
@@ -32,7 +32,7 @@
.\" SUCH DAMAGE.
.\"
.\" from: @(#)fnmatch.3 8.1 (Berkeley) 6/9/93
-.\" $Id: fnmatch.3,v 1.6 1993/11/09 18:22:05 jtc Exp $
+.\" $Id: fnmatch.3,v 1.7 1993/11/11 03:21:21 jtc Exp $
.\"
.Dd June 9, 1993
.Dt FNMATCH 3
@@ -95,7 +95,6 @@ Additionally, if
.Dv FNM_PATHNAME
is set,
a period is ``leading'' if it immediately follows a slash.
-.Em "This flag is not currently implemented."
.El
.Sh RETURN VALUES
The
@@ -121,10 +120,6 @@ The
.Fn fnmatch
function first appeared in 4.4BSD.
.Sh BUGS
-The
-.Dv FNM_PERIOD
-flag is not implemented.
-.Pp
The pattern
.Ql *
matches the empty string, even if
diff --git a/lib/libc/gen/fnmatch.c b/lib/libc/gen/fnmatch.c
index d8d600cdf43..af6b4fdb127 100644
--- a/lib/libc/gen/fnmatch.c
+++ b/lib/libc/gen/fnmatch.c
@@ -36,7 +36,7 @@
#if defined(LIBC_SCCS) && !defined(lint)
/* from: static char sccsid[] = "@(#)fnmatch.c 8.1 (Berkeley) 6/4/93"; */
-static char *rcsid = "$Id: fnmatch.c,v 1.7 1993/11/09 18:22:09 jtc Exp $";
+static char *rcsid = "$Id: fnmatch.c,v 1.8 1993/11/11 03:21:24 jtc Exp $";
#endif /* LIBC_SCCS and not lint */
/*
@@ -55,6 +55,7 @@ fnmatch(pattern, string, flags)
register const char *pattern, *string;
int flags;
{
+ const char *stringstart = string;
register char c;
char test;
@@ -63,9 +64,14 @@ fnmatch(pattern, string, flags)
case EOS:
return (*string == EOS ? 0 : FNM_NOMATCH);
case '?':
- if ((test = *string++) == EOS ||
- test == '/' && flags & FNM_PATHNAME)
+ if (*string == EOS)
return (FNM_NOMATCH);
+ if (*string == '/' && (flags & FNM_PATHNAME))
+ return (FNM_NOMATCH);
+ if (*string == '.' && (flags & FNM_PERIOD) &&
+ (string == stringstart || ((flags & FNM_PATHNAME) && *(string - 1) == '/')))
+ return (FNM_NOMATCH);
+ ++string;
break;
case '*':
c = *pattern;
@@ -73,6 +79,10 @@ fnmatch(pattern, string, flags)
while (c == '*')
c = *++pattern;
+ if (*string == '.' && (flags & FNM_PERIOD) &&
+ (string == stringstart || ((flags & FNM_PATHNAME) && *(string - 1) == '/')))
+ return (FNM_NOMATCH);
+
/* Optimize for pattern with * at end or before /. */
if (c == EOS)
if (flags & FNM_PATHNAME)
@@ -88,7 +98,7 @@ fnmatch(pattern, string, flags)
/* General case, use recursion. */
while ((test = *string) != EOS) {
- if (!fnmatch(pattern, string, flags))
+ if (!fnmatch(pattern, string, flags & ~FNM_PERIOD))
return (0);
if (test == '/' && flags & FNM_PATHNAME)
break;
@@ -96,11 +106,13 @@ fnmatch(pattern, string, flags)
}
return (FNM_NOMATCH);
case '[':
- if ((test = *string++) == EOS ||
- test == '/' && flags & FNM_PATHNAME)
+ if (*string == EOS)
+ return (FNM_NOMATCH);
+ if (*string == '/' && flags & FNM_PATHNAME)
return (FNM_NOMATCH);
- if ((pattern = rangematch(pattern, test, flags)) == NULL)
+ if ((pattern = rangematch(pattern, *string, flags)) == NULL)
return (FNM_NOMATCH);
+ ++string;
break;
case '\\':
if (!(flags & FNM_NOESCAPE)) {