summaryrefslogtreecommitdiffstats
path: root/lib/libc/regex/engine.c
diff options
context:
space:
mode:
authormartijn <martijn@openbsd.org>2016-05-26 05:46:44 +0000
committermartijn <martijn@openbsd.org>2016-05-26 05:46:44 +0000
commite315dedff8d9cbbf64bc080d283f4c20ae7a136a (patch)
tree0156a7008083d58b5f7af6b389fe46d8057e304c /lib/libc/regex/engine.c
parentRemove superfluous loop counter to set alternate video interface since we (diff)
downloadwireguard-openbsd-e315dedff8d9cbbf64bc080d283f4c20ae7a136a.tar.xz
wireguard-openbsd-e315dedff8d9cbbf64bc080d283f4c20ae7a136a.zip
Change the way regexec handles REG_STARTEND combined with REG_NOTBOL.
The new code sees this combination as a continuation of string at offset pmatch[0].rm_so, instead of a new string which starts at that offset. This change fixes a search quirk in vi and is needed for upcoming fixes in ed/sed/vi. This new behaviour is also used in gnu regex. Lots of help from schwarze@ Manpage bits by schwarze@ OK schwarze@ and millert@
Diffstat (limited to 'lib/libc/regex/engine.c')
-rw-r--r--lib/libc/regex/engine.c16
1 files changed, 13 insertions, 3 deletions
diff --git a/lib/libc/regex/engine.c b/lib/libc/regex/engine.c
index 4acb80b0e33..261956bec96 100644
--- a/lib/libc/regex/engine.c
+++ b/lib/libc/regex/engine.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: engine.c,v 1.22 2016/05/25 21:01:11 schwarze Exp $ */
+/* $OpenBSD: engine.c,v 1.23 2016/05/26 05:46:44 martijn Exp $ */
/*-
* Copyright (c) 1992, 1993, 1994 Henry Spencer.
@@ -671,12 +671,17 @@ fast(struct match *m, char *start, char *stop, sopno startst, sopno stopst)
states fresh = m->fresh;
states tmp = m->tmp;
char *p = start;
- int c = (start == m->beginp) ? OUT : *(start-1);
+ int c;
int lastc; /* previous c */
int flagch;
int i;
char *coldp; /* last p after which no match was underway */
+ if (start == m->offp || (start == m->beginp && !(m->eflags&REG_NOTBOL)))
+ c = OUT;
+ else
+ c = *(start-1);
+
CLEAR(st);
SET1(st, startst);
st = step(m->g, startst, stopst, st, NOTHING, st);
@@ -754,12 +759,17 @@ slow(struct match *m, char *start, char *stop, sopno startst, sopno stopst)
states empty = m->empty;
states tmp = m->tmp;
char *p = start;
- int c = (start == m->beginp) ? OUT : *(start-1);
+ int c;
int lastc; /* previous c */
int flagch;
int i;
char *matchp; /* last p at which a match ended */
+ if (start == m->offp || (start == m->beginp && !(m->eflags&REG_NOTBOL)))
+ c = OUT;
+ else
+ c = *(start-1);
+
AT("slow", start, stop, startst, stopst);
CLEAR(st);
SET1(st, startst);