NetBSD Problem Report #50484

From www@NetBSD.org  Sat Nov 28 05:57:41 2015
Return-Path: <www@NetBSD.org>
Received: from mail.netbsd.org (mail.netbsd.org [149.20.53.66])
	(using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits))
	(Client CN "mail.netbsd.org", Issuer "Postmaster NetBSD.org" (verified OK))
	by mollari.NetBSD.org (Postfix) with ESMTPS id 52149A57FE
	for <gnats-bugs@gnats.NetBSD.org>; Sat, 28 Nov 2015 05:57:41 +0000 (UTC)
Message-Id: <20151128055739.12080A65B7@mollari.NetBSD.org>
Date: Sat, 28 Nov 2015 05:57:39 +0000 (UTC)
From: okuyama@flex.phys.tohoku.ac.jp
Reply-To: okuyama@flex.phys.tohoku.ac.jp
To: gnats-bugs@NetBSD.org
Subject: script command of vi(1) is broken
X-Send-Pr-Version: www-1.0

>Number:         50484
>Category:       bin
>Synopsis:       script command of vi(1) is broken
>Confidential:   no
>Severity:       non-critical
>Priority:       medium
>Responsible:    bin-bug-people
>State:          closed
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Sat Nov 28 06:00:00 +0000 2015
>Closed-Date:    Sun Dec 18 21:16:32 +0000 2016
>Last-Modified:  Sun Dec 18 21:16:32 +0000 2016
>Originator:     Rin Okuyama
>Release:        7.99.22
>Organization:
Department of Physics, Tohoku University
>Environment:
NetBSD XXX 7.99.22 NetBSD 7.99.22 (GENERIC) #0: Fri Nov 27 15:30:56 JST 2015  root@XXX:XXX amd64
>Description:
Vi(1) has undocumented script command, that is similar to shell-mode in
Emacs. However, unfortunately, it is completely broken. If you invoke
the command, you will receive the following error message.

  % vi
  :script
  Error: pty: No such file or directory.

This is because we don't have old-fashioned pty devices by default (and
COMPAT_BSDPTY is disabled in GENERIC kernels on some arch). After making
old pty devices, shell starts on vi(1), but its output becomes corrupted
terribly:

  https://twitter.com/LabDrunker/status/670460802927849477
>How-To-Repeat:
Make old pty devices, then invoke script command in vi(1).

  % cd /dev; sudo ./MAKEDEV opty
  % vi
  :script

Then you obtain corrupted outputs from shell.
>Fix:
I've fixed the command:

* convert character encoding appropriately (taken from nvi2)
* use openpty(3) to remove dependency on old pty devices
* avoid buffer overflow in sscr_insert()
* other minor changes
  - constify CHAR_T* argument of db_set()
  - avoid double run of script command
  - simplify sscr_getprompt(); remove duplicate code and use sscr_input()
  - replace sscr_matchprompt() with strnstr(3)

Please apply the attached patch below, then it works fine:

  https://twitter.com/LabDrunker/status/670463156897083393

Alternatively, if you feel it unpleasant to have such an undocumented
and non-standard command in vi(1), I will provide another patch to
remove it.

======
--- src/external/bsd/nvi/Makefile.inc.orig	2015-11-28 14:05:28.000000000 +0900
+++ src/external/bsd/nvi/Makefile.inc	2015-11-28 14:13:24.000000000 +0900
@@ -7,4 +7,4 @@
 BINDIR=/usr/bin

 CWARNFLAGS.clang+=	-Wno-error=unused-const-variable
-VERSION=1.81.6-2013-11-20nb1
+VERSION=1.81.6-2013-11-20nb2
--- src/external/bsd/nvi/dist/common/vi_db1.c.orig	2015-11-28 14:05:10.000000000 +0900
+++ src/external/bsd/nvi/dist/common/vi_db1.c	2015-11-28 14:13:24.000000000 +0900
@@ -421,10 +421,10 @@
  * db_set --
  *	Store a line in the file.
  *
- * PUBLIC: int db_set __P((SCR *, db_recno_t, CHAR_T *, size_t));
+ * PUBLIC: int db_set __P((SCR *, db_recno_t, const CHAR_T *, size_t));
  */
 int
-db_set(SCR *sp, db_recno_t lno, CHAR_T *p, size_t len)
+db_set(SCR *sp, db_recno_t lno, const CHAR_T *p, size_t len)
 {
 	DBT data, key;
 	EXF *ep;
--- src/external/bsd/nvi/dist/ex/ex_script.c.orig	2015-11-28 14:04:45.000000000 +0900
+++ src/external/bsd/nvi/dist/ex/ex_script.c	2015-11-28 14:13:24.000000000 +0900
@@ -29,7 +29,7 @@
 #include <sys/select.h>
 #endif
 #include <sys/stat.h>
-#if defined(HAVE_SYS5_PTY) && !defined(__NetBSD__)
+#if defined(HAVE_SYS5_PTY)
 #include <sys/stropts.h>
 #endif
 #include <sys/time.h>
@@ -45,6 +45,9 @@
 #include <string.h>
 #include <termios.h>
 #include <unistd.h>
+#ifdef __NetBSD__
+#include <util.h>
+#endif

 #include "../common/common.h"
 #include "../vi/vi.h"
@@ -55,9 +58,12 @@
 static int	sscr_getprompt __P((SCR *));
 static int	sscr_init __P((SCR *));
 static int	sscr_insert __P((SCR *));
-static int	sscr_matchprompt __P((SCR *, CHAR_T *, size_t, size_t *));
+#ifdef __NetBSD__
+#define	sscr_pty openpty
+#else
 static int	sscr_pty __P((int *, int *, char *, struct termios *, void *));
-static int	sscr_setprompt __P((SCR *, CHAR_T *, size_t));
+#endif
+static int	sscr_setprompt __P((SCR *, char *, size_t));

 /*
  * ex_script -- : sc[ript][!] [file]
@@ -75,6 +81,17 @@
 		return (1);
 	}

+	/* Avoid double run. */
+	if (F_ISSET(sp, SC_SCRIPT)) {
+		msgq(sp, M_ERR,
+		    "The script command is already runninng");
+		return (1);
+	}
+
+	/* We're going to need a shell. */
+	if (opts_empty(sp, O_SHELL, 0))
+		return (1);
+
 	/* Switch to the new file. */
 	if (cmdp->argc != 0 && ex_edit(sp, cmdp))
 		return (1);
@@ -96,10 +113,6 @@
 	SCRIPT *sc;
 	const char *sh, *sh_path;

-	/* We're going to need a shell. */
-	if (opts_empty(sp, O_SHELL, 0))
-		return (1);
-
 	MALLOC_RET(sp, sc, SCRIPT *, sizeof(SCRIPT));
 	sp->script = sc;
 	sc->sh_prompt = NULL;
@@ -209,89 +222,28 @@
 sscr_getprompt(SCR *sp)
 {
 	struct timeval tv;
-	CHAR_T *endp, *p, *t, buf[1024];
-	SCRIPT *sc;
 	fd_set fdset;
-	db_recno_t lline;
-	size_t llen, len;
-	e_key_t value;
-	int nr;
-
-	FD_ZERO(&fdset);
-	endp = buf;
-	len = sizeof(buf);
+	int master;

 	/* Wait up to a second for characters to read. */
 	tv.tv_sec = 5;
 	tv.tv_usec = 0;
-	sc = sp->script;
-	FD_SET(sc->sh_master, &fdset);
-	switch (select(sc->sh_master + 1, &fdset, NULL, NULL, &tv)) {
+	master = sp->script->sh_master;
+	FD_ZERO(&fdset);
+	FD_SET(master, &fdset);
+	switch (select(master + 1, &fdset, NULL, NULL, &tv)) {
 	case -1:		/* Error or interrupt. */
 		msgq(sp, M_SYSERR, "select");
-		goto prompterr;
-	case  0:		/* Timeout */
-		msgq(sp, M_ERR, "Error: timed out");
-		goto prompterr;
-	case  1:		/* Characters to read. */
 		break;
-	}
-
-	/* Read the characters. */
-more:	len = sizeof(buf) - (endp - buf);
-	switch (nr = read(sc->sh_master, endp, len)) {
-	case  0:			/* EOF. */
-		msgq(sp, M_ERR, "Error: shell: EOF");
-		goto prompterr;
-	case -1:			/* Error or interrupt. */
-		msgq(sp, M_SYSERR, "shell");
-		goto prompterr;
-	default:
-		endp += nr;
-		break;
-	}
-
-	/* If any complete lines, push them into the file. */
-	for (p = t = buf; p < endp; ++p) {
-		value = KEY_VAL(sp, *p);
-		if (value == K_CR || value == K_NL) {
-			if (db_last(sp, &lline) ||
-			    db_append(sp, 0, lline, t, p - t))
-				goto prompterr;
-			t = p + 1;
-		}
-	}
-	if (p > buf) {
-		MEMMOVE(buf, t, endp - t);
-		endp = buf + (endp - t);
-	}
-	if (endp == buf)
-		goto more;
-
-	/* Wait up 1/10 of a second to make sure that we got it all. */
-	tv.tv_sec = 0;
-	tv.tv_usec = 100000;
-	switch (select(sc->sh_master + 1, &fdset, NULL, NULL, &tv)) {
-	case -1:		/* Error or interrupt. */
-		msgq(sp, M_SYSERR, "select");
-		goto prompterr;
 	case  0:		/* Timeout */
+		msgq(sp, M_ERR, "Error: timed out");
 		break;
 	case  1:		/* Characters to read. */
-		goto more;
-	}
-
-	/* Timed out, so theoretically we have a prompt. */
-	llen = endp - buf;
-	endp = buf;
-
-	/* Append the line into the file. */
-	if (db_last(sp, &lline) || db_append(sp, 0, lline, buf, llen)) {
-prompterr:	sscr_end(sp);
-		return (1);
+		return (sscr_insert(sp) || sp->script == NULL);
 	}

-	return (sscr_setprompt(sp, buf, llen));
+	sscr_end(sp);
+	return (1);
 }

 /*
@@ -305,47 +257,53 @@
 {
 	SCRIPT *sc;
 	db_recno_t last_lno;
-	size_t blen, len, last_len, tlen;
+	size_t blen, len, last_len;
 	int isempty, matchprompt, rval;
 	ssize_t nw;
-	CHAR_T *bp = NULL;
-	CHAR_T *p;
+	char *bp = NULL;
+	const char *p;
+	const CHAR_T *ip;
+	size_t ilen;
+
+	sc = sp->script;

 	/* If there's a prompt on the last line, append the command. */
 	if (db_last(sp, &last_lno))
 		return (1);
-	if (db_get(sp, last_lno, DBG_FATAL, &p, &last_len))
+	if (db_get(sp, last_lno, DBG_FATAL, __UNCONST(&ip), &ilen))
 		return (1);
-	if (sscr_matchprompt(sp, p, last_len, &tlen) && tlen == 0) {
+	INT2CHAR(sp, ip, ilen, p, last_len);
+	if (last_len == sc->sh_prompt_len &&
+	    strnstr(p, sc->sh_prompt, last_len) == p) {
 		matchprompt = 1;
-		GET_SPACE_RETW(sp, bp, blen, last_len + 128);
-		MEMMOVEW(bp, p, last_len);
+		GET_SPACE_RETC(sp, bp, blen, last_len + 128);
+		memmove(bp, p, last_len);
 	} else
 		matchprompt = 0;

 	/* Get something to execute. */
-	if (db_eget(sp, lno, &p, &len, &isempty)) {
+	if (db_eget(sp, lno, __UNCONST(&ip), &ilen, &isempty)) {
 		if (isempty)
 			goto empty;
 		goto err1;
 	}

 	/* Empty lines aren't interesting. */
-	if (len == 0)
+	if (ilen == 0)
 		goto empty;
+	INT2CHAR(sp, ip, ilen, p, len);

 	/* Delete any prompt. */
-	if (sscr_matchprompt(sp, p, len, &tlen)) {
-		if (tlen == len) {
+	if (sc->sh_prompt != NULL && strnstr(p, sc->sh_prompt, len) == p) {
+		len -= sc->sh_prompt_len;
+		if (len == 0) {
 empty:			msgq(sp, M_BERR, "151|No command to execute");
 			goto err1;
 		}
-		p += (len - tlen);
-		len = tlen;
+		p += sc->sh_prompt_len;
 	}

 	/* Push the line to the shell. */
-	sc = sp->script;
 	if ((size_t)(nw = write(sc->sh_master, p, len)) != len)
 		goto err2;
 	rval = 0;
@@ -357,13 +315,14 @@
 	}

 	if (matchprompt) {
-		ADD_SPACE_RETW(sp, bp, blen, last_len + len);
-		MEMMOVEW(bp + last_len, p, len);
-		if (db_set(sp, last_lno, bp, last_len + len))
+		ADD_SPACE_GOTO(sp, char, bp, blen, last_len + len);
+		memmove(bp + last_len, p, len);
+		CHAR2INT(sp, bp, last_len + len, ip, ilen);
+		if (db_set(sp, last_lno, ip, ilen))
 err1:			rval = 1;
 	}
 	if (matchprompt)
-		FREE_SPACEW(sp, bp, blen);
+alloc_err:	FREE_SPACE(sp, bp, blen);
 	return (rval);
 }

@@ -465,34 +424,31 @@
 sscr_insert(SCR *sp)
 {
 	struct timeval tv;
-	CHAR_T *endp, *p, *t;
+	char *endp, *p, *t;
 	SCRIPT *sc;
 	fd_set rdfd;
 	db_recno_t lno;
-	size_t blen, len = 0, tlen;
-	e_key_t value;
-	int nr, rval;
-	CHAR_T *bp;
+	size_t len;
+	ssize_t nr;
+	char bp[1024];
+	const CHAR_T *ip;
+	size_t ilen = 0;

 	/* Find out where the end of the file is. */
 	if (db_last(sp, &lno))
 		return (1);

-#define	MINREAD	1024
-	GET_SPACE_RETW(sp, bp, blen, MINREAD);
 	endp = bp;

 	/* Read the characters. */
-	rval = 1;
 	sc = sp->script;
-more:	switch (nr = read(sc->sh_master, endp, MINREAD)) {
+more:	switch (nr = read(sc->sh_master, endp, bp + sizeof(bp) - endp)) {
 	case  0:			/* EOF; shell just exited. */
 		sscr_end(sp);
-		rval = 0;
-		goto ret;
+		return (0);
 	case -1:			/* Error or interrupt. */
 		msgq(sp, M_SYSERR, "shell");
-		goto ret;
+		return (1);
 	default:
 		endp += nr;
 		break;
@@ -500,11 +456,11 @@

 	/* Append the lines into the file. */
 	for (p = t = bp; p < endp; ++p) {
-		value = KEY_VAL(sp, *p);
-		if (value == K_CR || value == K_NL) {
+		if (p == bp + sizeof(bp) - 1 || *p == '\r' || *p == '\n') {
 			len = p - t;
-			if (db_append(sp, 1, lno++, t, len))
-				goto ret;
+			if (CHAR2INT(sp, t, len, ip, ilen) ||
+			    db_append(sp, 1, lno++, ip, ilen))
+				return (1);
 			t = p + 1;
 		}
 	}
@@ -517,31 +473,29 @@
 		 * want to hang indefinitely because some program is hanging,
 		 * confused the shell, or whatever.
 		 */
-		if (!sscr_matchprompt(sp, t, len, &tlen) || tlen != 0) {
+		if (len != sc->sh_prompt_len ||
+		    strnstr(t, sc->sh_prompt, len) == NULL) {
 			tv.tv_sec = 0;
 			tv.tv_usec = 100000;
 			FD_ZERO(&rdfd);
 			FD_SET(sc->sh_master, &rdfd);
 			if (select(sc->sh_master + 1,
 			    &rdfd, NULL, NULL, &tv) == 1) {
-				MEMMOVE(bp, t, len);
+				memmove(bp, t, len);
 				endp = bp + len;
 				goto more;
 			}
 		}
-		if (sscr_setprompt(sp, t, len))
+		if (sscr_setprompt(sp, t, len) ||
+		    CHAR2INT(sp, t, len, ip, ilen) ||
+		    db_append(sp, 1, lno++, ip, ilen))
 			return (1);
-		if (db_append(sp, 1, lno++, t, len))
-			goto ret;
 	}

 	/* The cursor moves to EOF. */
 	sp->lno = lno;
-	sp->cno = len ? len - 1 : 0;
-	rval = vs_refresh(sp, 1);
-
-ret:	FREE_SPACEW(sp, bp, blen);
-	return (rval);
+	sp->cno = ilen ? ilen - 1 : 0;
+	return (vs_refresh(sp, 1));
 }

 /*
@@ -551,11 +505,9 @@
  *
  */
 static int
-sscr_setprompt(SCR *sp, CHAR_T *buf, size_t len)
+sscr_setprompt(SCR *sp, char *buf, size_t len)
 {
 	SCRIPT *sc;
-	const char *np;
-	size_t nlen;

 	sc = sp->script;
 	if (sc->sh_prompt)
@@ -565,51 +517,13 @@
 		sscr_end(sp);
 		return (1);
 	}
-	INT2CHAR(sp, buf, len, np, nlen);
-	memmove(sc->sh_prompt, np, nlen);
+	memmove(sc->sh_prompt, buf, len);
 	sc->sh_prompt_len = len;
 	sc->sh_prompt[len] = '\0';
 	return (0);
 }

 /*
- * sscr_matchprompt --
- *	Check to see if a line matches the prompt.  Nul's indicate
- *	parts that can change, in both content and size.
- */
-static int
-sscr_matchprompt(SCR *sp, CHAR_T *lp, size_t line_len, size_t *lenp)
-{
-	SCRIPT *sc;
-	size_t prompt_len;
-	char *pp;
-
-	sc = sp->script;
-	if (line_len < (prompt_len = sc->sh_prompt_len))
-		return (0);
-
-	for (pp = sc->sh_prompt;
-	    prompt_len && line_len; --prompt_len, --line_len) {
-		if (*pp == '\0') {
-			for (; prompt_len && *pp == '\0'; --prompt_len, ++pp);
-			if (!prompt_len)
-				return (0);
-			for (; line_len && *lp != *pp; --line_len, ++lp);
-			if (!line_len)
-				return (0);
-		}
-		if (*pp++ != *lp++)
-			break;
-	}
-
-	if (prompt_len)
-		return (0);
-	if (lenp != NULL)
-		*lenp = line_len;
-	return (1);
-}
-
-/*
  * sscr_end --
  *	End the pipe to a shell.
  *
@@ -664,6 +578,7 @@
 	F_CLR(gp, G_SCRWIN);
 }

+#ifndef __NetBSD__
 #ifdef HAVE_SYS5_PTY
 static int ptys_open __P((int, char *));
 static int ptym_open __P((char *));
@@ -829,4 +744,6 @@
 	errno = ENOENT;	/* out of ptys */
 	return (-1);
 }
+
 #endif /* HAVE_SYS5_PTY */
+#endif /* !__NetBSD__ */
--- src/external/bsd/nvi/usr.bin/nvi/Makefile.orig	2015-11-28 14:05:41.000000000 +0900
+++ src/external/bsd/nvi/usr.bin/nvi/Makefile	2015-11-28 14:13:24.000000000 +0900
@@ -18,8 +18,8 @@
 #COPTS+=-fno-strict-aliasing
 #.endif

-LDADD+=	-lcurses -lterminfo
-DPADD+=	${LIBCURSES} ${LIBTERMINFO}
+LDADD+=	-lcurses -lterminfo -lutil
+DPADD+=	${LIBCURSES} ${LIBTERMINFO} ${LIBUTIL}
 PROG=	vi
 SRCS=	api.c cl_bsd.c cl_funcs.c cl_main.c cl_read.c cl_screen.c cl_term.c \
 	conv.c cut.c delete.c ex.c ex_abbrev.c ex_append.c \

>Release-Note:

>Audit-Trail:
From: "Christos Zoulas" <christos@netbsd.org>
To: gnats-bugs@gnats.NetBSD.org
Cc: 
Subject: PR/50484 CVS commit: src/external/bsd/nvi
Date: Sat, 28 Nov 2015 08:20:03 -0500

 Module Name:	src
 Committed By:	christos
 Date:		Sat Nov 28 13:20:03 UTC 2015

 Modified Files:
 	src/external/bsd/nvi: Makefile.inc
 	src/external/bsd/nvi/dist/common: vi_db1.c
 	src/external/bsd/nvi/dist/ex: ex_script.c
 	src/external/bsd/nvi/usr.bin/nvi: Makefile

 Log Message:
 PR/50484: Rin Okuyama: fix the script command of vi(1)


 To generate a diff of this commit:
 cvs rdiff -u -r1.2 -r1.3 src/external/bsd/nvi/Makefile.inc
 cvs rdiff -u -r1.7 -r1.8 src/external/bsd/nvi/dist/common/vi_db1.c
 cvs rdiff -u -r1.4 -r1.5 src/external/bsd/nvi/dist/ex/ex_script.c
 cvs rdiff -u -r1.6 -r1.7 src/external/bsd/nvi/usr.bin/nvi/Makefile

 Please note that diffs are not public domain; they are subject to the
 copyright notices on the relevant files.

From: Rin Okuyama <okuyama@flex.phys.tohoku.ac.jp>
To: gnats-bugs@NetBSD.org, christos@netbsd.org
Cc: 
Subject: Re: PR/50484 CVS commit: src/external/bsd/nvi
Date: Mon, 30 Nov 2015 01:30:31 +0900

 Thank you for your commit.

 I'm sorry, however, the previous version still has a problem when
 output is long; although segmentation faults are safely avoided,
 every 1024th characters are replaced by line breaks.

   https://twitter.com/LabDrunker/status/670999814516121600

 Here, I attached the revised version. I'm sorry for taking your
 time, but please apply the patch below.

 Thanks,
 Rin

 --- src/external/bsd/nvi/Makefile.inc.orig	2015-11-29 00:34:51.000000000 +0900
 +++ src/external/bsd/nvi/Makefile.inc	2015-11-29 00:34:57.000000000 +0900
 @@ -7,4 +7,4 @@
  BINDIR=/usr/bin

  CWARNFLAGS.clang+=	-Wno-error=unused-const-variable
 -VERSION=1.81.6-2013-11-20nb2
 +VERSION=1.81.6-2013-11-20nb3
 --- src/external/bsd/nvi/dist/ex/ex_script.c.orig	2015-11-29 00:03:55.000000000 +0900
 +++ src/external/bsd/nvi/dist/ex/ex_script.c	2015-11-29 05:17:24.000000000 +0900
 @@ -294,7 +294,7 @@
  	INT2CHAR(sp, ip, ilen, p, len);

  	/* Delete any prompt. */
 -	if (sc->sh_prompt != NULL && strnstr(p, sc->sh_prompt, len) == p) {
 +	if (strnstr(p, sc->sh_prompt, len) == p) {
  		len -= sc->sh_prompt_len;
  		if (len == 0) {
  empty:			msgq(sp, M_BERR, "151|No command to execute");
 @@ -456,7 +456,7 @@

  	/* Append the lines into the file. */
  	for (p = t = bp; p < endp; ++p) {
 -		if (p == bp + sizeof(bp) - 1 || *p == '\r' || *p == '\n') {
 +		if (*p == '\r' || *p == '\n') {
  			len = p - t;
  			if (CHAR2INT(sp, t, len, ip, ilen) ||
  			    db_append(sp, 1, lno++, ip, ilen))
 @@ -464,37 +464,45 @@
  			t = p + 1;
  		}
  	}
 -	if (p > t) {
 -		len = p - t;
 -		/*
 -		 * If the last thing from the shell isn't another prompt, wait
 -		 * up to 1/10 of a second for more stuff to show up, so that
 -		 * we don't break the output into two separate lines.  Don't
 -		 * want to hang indefinitely because some program is hanging,
 -		 * confused the shell, or whatever.
 -		 */
 -		if (len != sc->sh_prompt_len ||
 -		    strnstr(t, sc->sh_prompt, len) == NULL) {
 -			tv.tv_sec = 0;
 -			tv.tv_usec = 100000;
 -			FD_ZERO(&rdfd);
 -			FD_SET(sc->sh_master, &rdfd);
 -			if (select(sc->sh_master + 1,
 -			    &rdfd, NULL, NULL, &tv) == 1) {
 +	/*
 +	 * If the last thing from the shell isn't another prompt, wait up to
 +	 * 1/10 of a second for more stuff to show up, so that we don't break
 +	 * the output into two separate lines.  Don't want to hang indefinitely
 +	 * because some program is hanging, confused the shell, or whatever.
 +	 * Note that sc->sh_prompt can be NULL here.
 +	 */
 +	len = p - t;
 +	if (sc->sh_prompt == NULL || len != sc->sh_prompt_len ||
 +	    strnstr(p, sc->sh_prompt, len) == NULL) {
 +		tv.tv_sec = 0;
 +		tv.tv_usec = 100000;
 +		FD_ZERO(&rdfd);
 +		FD_SET(sc->sh_master, &rdfd);
 +		if (select(sc->sh_master + 1, &rdfd, NULL, NULL, &tv) == 1) {
 +			if (len == sizeof(bp)) {
 +				if (CHAR2INT(sp, t, len, ip, ilen) ||
 +				    db_append(sp, 1, lno++, ip, ilen))
 +					return (1);
 +				endp = bp;
 +			} else {
  				memmove(bp, t, len);
  				endp = bp + len;
 -				goto more;
  			}
 +			goto more;
  		}
 -		if (sscr_setprompt(sp, t, len) ||
 -		    CHAR2INT(sp, t, len, ip, ilen) ||
 -		    db_append(sp, 1, lno++, ip, ilen))
 +		if (sscr_setprompt(sp, t, len))
  			return (1);
  	}

 -	/* The cursor moves to EOF. */
 +	/* Append the remains into the file, and the cursor moves to EOF. */
 +	if (len > 0) {
 +		if (CHAR2INT(sp, t, len, ip, ilen) ||
 +		    db_append(sp, 1, lno++, ip, ilen))
 +			return (1);
 +		sp->cno = ilen - 1;
 +	} else
 +		sp->cno = 0;
  	sp->lno = lno;
 -	sp->cno = ilen ? ilen - 1 : 0;
  	return (vs_refresh(sp, 1));
  }


From: Rin Okuyama <okuyama@flex.phys.tohoku.ac.jp>
To: Christos Zoulas <christos@netbsd.org>, gnats-bugs@NetBSD.org
Cc: 
Subject: Re: PR/50484 (CVS commit: src/external/bsd/nvi)
Date: Mon, 30 Nov 2015 03:02:09 +0900

 On 2015/11/30 2:09, Christos Zoulas wrote:
 > Module Name:	src
 > Committed By:	christos
 > Date:		Sun Nov 29 17:09:33 UTC 2015
 >
 > Modified Files:
 > 	src/external/bsd/nvi: Makefile.inc
 > 	src/external/bsd/nvi/dist/ex: ex_script.c
 >
 > Log Message:
 > Fix > 1024 char lines in script. (Rin Okuyama)
 >
 >
 > To generate a diff of this commit:
 > cvs rdiff -u -r1.3 -r1.4 src/external/bsd/nvi/Makefile.inc
 > cvs rdiff -u -r1.5 -r1.6 src/external/bsd/nvi/dist/ex/ex_script.c
 >
 > Please note that diffs are not public domain; they are subject to the
 > copyright notices on the relevant files.

 Fix confirmed. Thank you for helping me many times.

From: christos@zoulas.com (Christos Zoulas)
To: Rin Okuyama <okuyama@flex.phys.tohoku.ac.jp>, gnats-bugs@NetBSD.org
Cc: 
Subject: Re: PR/50484 (CVS commit: src/external/bsd/nvi)
Date: Sun, 29 Nov 2015 13:53:47 -0500

 On Nov 30,  3:02am, okuyama@flex.phys.tohoku.ac.jp (Rin Okuyama) wrote:
 -- Subject: Re: PR/50484 (CVS commit: src/external/bsd/nvi)

 | Fix confirmed. Thank you for helping me many times.


 No problem, keep the patches coming!

 christos

From: "Soren Jacobsen" <snj@netbsd.org>
To: gnats-bugs@gnats.NetBSD.org
Cc: 
Subject: PR/50484 CVS commit: [netbsd-7] src/external/bsd/nvi
Date: Sun, 18 Dec 2016 06:37:31 +0000

 Module Name:	src
 Committed By:	snj
 Date:		Sun Dec 18 06:37:30 UTC 2016

 Modified Files:
 	src/external/bsd/nvi [netbsd-7]: Makefile.inc
 	src/external/bsd/nvi/dist/cl [netbsd-7]: cl.h cl_main.c cl_screen.c
 	    cl_term.c
 	src/external/bsd/nvi/dist/common [netbsd-7]: key.h vi_db1.c
 	src/external/bsd/nvi/dist/docs/vi.man [netbsd-7]: vi.1
 	src/external/bsd/nvi/dist/ex [netbsd-7]: ex_map.c ex_script.c
 	src/external/bsd/nvi/usr.bin/nvi [netbsd-7]: Makefile

 Log Message:
 Pull up following revision(s) (requested by riastradh in ticket #1312):
 	external/bsd/nvi/Makefile.inc: revisions 1.2-1.4
 	external/bsd/nvi/dist/cl/cl.h: revision 1.3
 	external/bsd/nvi/dist/cl/cl_main.c: revision 1.5
 	external/bsd/nvi/dist/cl/cl_screen.c: revision 1.5
 	external/bsd/nvi/dist/cl/cl_term.c: revision 1.5
 	external/bsd/nvi/dist/common/key.h: revision 1.3
 	external/bsd/nvi/dist/common/vi_db1.c: revision 1.8
 	external/bsd/nvi/dist/docs/vi.man/vi.1: revisions 1.3, 1.4
 	external/bsd/nvi/dist/ex/ex_map.c: revision 1.4
 	external/bsd/nvi/dist/ex/ex_script.c: revisions 1.5, 1.6
 	external/bsd/nvi/usr.bin/nvi/Makefile: revision 1.7
 PR/50092: Rin Okuyama: Fix memory leaks in vi when resizing.
 --
 PR/50484: Rin Okuyama: fix the script command of vi(1)
 --
 Fix > 1024 char lines in script. (Rin Okuyama)
 --
 remove CONST; it is unused from Brad Harder
 --
 add default: to appease gcc.
 --
 Restore the first line of the copyright header, which accidentally got
 zapped in -r1.2.
 --
 PR 51446 Brad Harder: fix synopsis for :tagprev


 To generate a diff of this commit:
 cvs rdiff -u -r1.1 -r1.1.6.1 src/external/bsd/nvi/Makefile.inc
 cvs rdiff -u -r1.2 -r1.2.6.1 src/external/bsd/nvi/dist/cl/cl.h
 cvs rdiff -u -r1.4 -r1.4.6.1 src/external/bsd/nvi/dist/cl/cl_main.c \
     src/external/bsd/nvi/dist/cl/cl_screen.c \
     src/external/bsd/nvi/dist/cl/cl_term.c
 cvs rdiff -u -r1.2 -r1.2.6.1 src/external/bsd/nvi/dist/common/key.h
 cvs rdiff -u -r1.7 -r1.7.6.1 src/external/bsd/nvi/dist/common/vi_db1.c
 cvs rdiff -u -r1.2 -r1.2.6.1 src/external/bsd/nvi/dist/docs/vi.man/vi.1
 cvs rdiff -u -r1.3 -r1.3.6.1 src/external/bsd/nvi/dist/ex/ex_map.c
 cvs rdiff -u -r1.4 -r1.4.6.1 src/external/bsd/nvi/dist/ex/ex_script.c
 cvs rdiff -u -r1.5 -r1.5.2.1 src/external/bsd/nvi/usr.bin/nvi/Makefile

 Please note that diffs are not public domain; they are subject to the
 copyright notices on the relevant files.

State-Changed-From-To: open->closed
State-Changed-By: dholland@NetBSD.org
State-Changed-When: Sun, 18 Dec 2016 21:16:32 +0000
State-Changed-Why:
fixed and pulled up


>Unformatted:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2014 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.