diff options
| author | christos <christos@NetBSD.org> | 2015-07-30 21:47:51 +0000 |
|---|---|---|
| committer | christos <christos@NetBSD.org> | 2015-07-30 21:47:51 +0000 |
| commit | 39275d4eabce7266b68ebdfca95e6a46b5a0ca4a (patch) | |
| tree | b77e0ff6306433397568eae8f2b5f6274604261e /usr.bin/patch | |
| parent | 53796b1872dc053e4f8f64d728ee555a60d0fb5c (diff) | |
from bitrieg:
Substitution commands might contain a newline in the replacement pattern
(escaped with a backslash before it), causing patch's understanding of
the state the ed child process is in to diverge from reality. This can
lead to patch unwillingly feeding '!' (execute shell command) lines to
ed. Finding out how to do this is left as an exercise to the reader.
XXX: pullup-7
Diffstat (limited to 'usr.bin/patch')
| -rw-r--r-- | usr.bin/patch/pch.c | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/usr.bin/patch/pch.c b/usr.bin/patch/pch.c index 1ef322fb7d9..7ffb0cc76a7 100644 --- a/usr.bin/patch/pch.c +++ b/usr.bin/patch/pch.c @@ -1,7 +1,7 @@ /* * $OpenBSD: pch.c,v 1.37 2007/09/02 15:19:33 deraadt Exp $ * $DragonFly: src/usr.bin/patch/pch.c,v 1.6 2008/08/10 23:35:40 joerg Exp $ - * $NetBSD: pch.c,v 1.27 2014/11/27 15:07:23 christos Exp $ + * $NetBSD: pch.c,v 1.28 2015/07/30 21:47:51 christos Exp $ */ /* @@ -31,7 +31,7 @@ */ #include <sys/cdefs.h> -__RCSID("$NetBSD: pch.c,v 1.27 2014/11/27 15:07:23 christos Exp $"); +__RCSID("$NetBSD: pch.c,v 1.28 2015/07/30 21:47:51 christos Exp $"); #include <sys/types.h> #include <sys/stat.h> @@ -1407,6 +1407,7 @@ do_ed_script(void) char *t; long beginning_of_this_line; FILE *pipefp = NULL; + int continuation; if (!skip_rest_of_patch) { if (copy_file(filearg[0], TMPOUTNAME) < 0) { @@ -1431,7 +1432,19 @@ do_ed_script(void) *t == 'd' || *t == 'i' || *t == 's')) { if (pipefp != NULL) fputs(buf, pipefp); - if (*t != 'd') { + if (*t == 's') { + for (;;) { + continuation = 0; + t = strchr(buf, '\0') - 1; + while (--t >= buf && *t == '\\') + continuation = !continuation; + if (!continuation || + pgets(buf, sizeof buf, pfp) == NULL) + break; + if (pipefp != NULL) + fputs(buf, pipefp); + } + } else if (*t != 'd') { while (pgets(buf, buf_len, pfp) != NULL) { p_input_line++; if (pipefp != NULL) |
