On Mon, Jun 19, 2017 at 03:57:35AM -0600, Anthony J. Bentley wrote: > Hi, > > Jason McIntyre writes: > > ok by me. note that posix ex(1) does detail a working [s]ubstitute command, > > so i'm not sure whether we should support this or not. > > Hm, so it does. I think I would prefer to follow POSIX in this case. > Here's a diff to allow "substitute" to work. > > Annoyingly, there's an ambiguity in the POSIX synopsis (and ours). > > [2addr] s[ubstitute][/pattern/repl/[options][count][flags]] > > This implies that "su" could expand to "substitute". But it expands (and > should expand) to "suspend" instead. Since in our vi the first match > always wins, the simplest way to implement this is to use separate ex > commands: > > [2addr] s[/pattern/repl/[options][count][flags]] > [2addr] sub[stitute][/pattern/repl/[options][count][flags]] > > There are already plenty of duplicate commands (e.g., "#"/"nu", > "cd"/"chd", "co"/"t"...) so I think it's an acceptable approach. >
evening. shouldn;t it be that we should show the suspend command as sus[pend] the shortest "s" matches "substitute", right. so we show it as s[ubstitute] i cannot find any text that describes what "su" *should* match though, so i'm not sure. logically i'd expect it to match "substitute", since that is first alphabetically. that's why i think it should be sus[pend], not sub[stitute]. i don;t have any other versions of vi to compare how other systems do this. jmc > Index: docs/USD.doc/vi.man/vi.1 > =================================================================== > RCS file: /cvs/src/usr.bin/vi/docs/USD.doc/vi.man/vi.1,v > retrieving revision 1.67 > diff -u -p -r1.67 vi.1 > --- docs/USD.doc/vi.man/vi.1 15 Jun 2017 06:44:47 -0000 1.67 > +++ docs/USD.doc/vi.man/vi.1 19 Jun 2017 09:19:23 -0000 > @@ -356,7 +356,7 @@ matches the end of the word. > .It > .Sq ~ > matches the replacement part of the last > -.Cm substitute > +.Cm s > command. > .El > .Sh BUFFERS > @@ -1996,52 +1996,65 @@ Grow or shrink the current screen. > Rewind the argument list. > .Pp > .It Xo > -.Cm se Ns Op Cm t > +.Op Ar range > .Sm off > -.Op option Oo = Oo value Oc Oc \ \&... > +.Cm s > +.Oo Cm / Ar pattern Cm / Ar replace Cm / > +.Op Ar options > +.Op Ar count > +.Op Ar flags > +.Oc > .Sm on > -.Pf \ \& Op nooption ... > -.Op option? ... > -.Op Ar all > -.Xc > -Display or set editor options. > -.Pp > -.It Cm sh Ns Op Cm ell > -Run a shell program. > -.Pp > -.It Xo > -.Cm so Ns Op Cm urce > -.Ar file > .Xc > -Read and execute > -.Nm ex > -commands from a file. > -.Pp > .It Xo > .Op Ar range > -.Cm s Ns Op Cm ubstitute > .Sm off > -.Op / Ar pattern No / Ar replace No / > -.Sm on > -.Pf \ \& Op Ar options > +.Cm sub Op Cm stitute > +.Oo Cm / Ar pattern Cm / Ar replace Cm / > +.Op Ar options > .Op Ar count > .Op Ar flags > +.Sm on > .Xc > .It Xo > .Op Ar range > +.Sm off > .Cm & > .Op Ar options > .Op Ar count > .Op Ar flags > +.Sm on > .Xc > .It Xo > .Op Ar range > +.Sm off > .Cm ~ > .Op Ar options > .Op Ar count > .Op Ar flags > +.Sm on > .Xc > -Make substitutions. > +Substitute the regular expression > +.Ar pattern > +with > +.Ar replace . > +When invoked as > +.Cm & , > +or if > +.Cm / Ns Ar pattern Ns Cm / Ns Ar replace Ns Cm / > +is omitted, > +.Ar pattern > +and > +.Ar replace > +from the most recent > +.Cm s > +command are used. > +.Cm ~ > +behaves like > +.Cm & , > +except the pattern used is the most recent regular expression used by any > +command. > +.Pp > The > .Ar replace > field may contain any of the following sequences: > @@ -2051,13 +2064,13 @@ The text matched by > .Ar pattern . > .It Sq \(a~ > The replacement part of the previous > -.Cm substitute > +.Cm s > command. > .It Sq % > If this is the entire > .Ar replace > pattern, the replacement part of the previous > -.Cm substitute > +.Cm s > command. > .It Sq \e# > Where > @@ -2082,6 +2095,40 @@ to be converted to uppercase. > Causes the next character to be converted to uppercase. > .El > .Pp > +The > +.Ar options > +field may contain any of the following characters: > +.Bl -tag -width Ds > +.It Sq c > +Prompt for confirmation before each replacement is done. > +.It Sq g > +Replace all instances of > +.Ar pattern > +in a line, not just the first. > +.El > +.Pp > +.It Xo > +.Cm se Ns Op Cm t > +.Sm off > +.Op option Oo = Oo value Oc Oc \ \&... > +.Sm on > +.Pf \ \& Op nooption ... > +.Op option? ... > +.Op Ar all > +.Xc > +Display or set editor options. > +.Pp > +.It Cm sh Ns Op Cm ell > +Run a shell program. > +.Pp > +.It Xo > +.Cm so Ns Op Cm urce > +.Ar file > +.Xc > +Read and execute > +.Nm ex > +commands from a file. > +.Pp > .It Xo > .Cm su Ns Op Cm spend Ns > .Op Cm !\& > @@ -2291,7 +2338,9 @@ Remember the values of the > and > .Sq g > suffixes to the > -.Cm substitute > +.Cm s , & > +and > +.Cm ~ > commands, instead of initializing them as unset for each new command. > .It Cm escapetime Bq 1 > The tenths of a second > Index: ex/ex_cmd.c > =================================================================== > RCS file: /cvs/src/usr.bin/vi/ex/ex_cmd.c,v > retrieving revision 1.10 > diff -u -p -r1.10 ex_cmd.c > --- ex/ex_cmd.c 19 Nov 2015 07:53:31 -0000 1.10 > +++ ex/ex_cmd.c 19 Jun 2017 09:19:23 -0000 > @@ -288,8 +288,8 @@ EXCMDLIST const cmds[] = { > * Adding new commands starting with 's' may break the substitute command > code > * in ex_cmd() (the ex parser). Read through the comments there, first. > */ > -/* C_SUBSTITUTE */ > - {"s", ex_s, E_ADDR2, > +/* C_S */ > + {"s", ex_s, E_ADDR2, > "s", > "[line [,line]] s [[/;]RE[/;]repl[/;] [cgr] [count] [#lp]]", > "substitute on lines matching an RE"}, > @@ -323,6 +323,11 @@ EXCMDLIST const cmds[] = { > "!", > "su[spend][!]", > "suspend the edit session"}, > +/* C_SUBSTITUTE */ > + {"substitute", ex_s, E_ADDR2, > + "s", > + "[line [,line]] sub[stitute] [[/;]RE[/;]repl[/;] [cgr] [count] > [#lp]]", > + "substitute on lines matching an RE"}, > /* C_T */ > {"t", ex_copy, E_ADDR2|E_AUTOPRINT, > "l1", > Index: include/ex_def.h > =================================================================== > RCS file: /cvs/src/usr.bin/vi/include/ex_def.h,v > retrieving revision 1.5 > diff -u -p -r1.5 ex_def.h > --- include/ex_def.h 19 Nov 2015 07:53:31 -0000 1.5 > +++ include/ex_def.h 19 Jun 2017 09:19:23 -0000 > @@ -46,31 +46,32 @@ > #define C_RECOVER 43 > #define C_RESIZE 44 > #define C_REWIND 45 > -#define C_SUBSTITUTE 46 > +#define C_S 46 > #define C_SCRIPT 47 > #define C_SET 48 > #define C_SHELL 49 > #define C_SOURCE 50 > #define C_STOP 51 > #define C_SUSPEND 52 > -#define C_T 53 > -#define C_TAG 54 > -#define C_TAGNEXT 55 > -#define C_TAGPOP 56 > -#define C_TAGPREV 57 > -#define C_TAGTOP 58 > -#define C_UNDO 59 > -#define C_UNABBREVIATE 60 > -#define C_UNMAP 61 > -#define C_V 62 > -#define C_VERSION 63 > -#define C_VISUAL_EX 64 > -#define C_VISUAL_VI 65 > -#define C_VIUSAGE 66 > -#define C_WRITE 67 > -#define C_WN 68 > -#define C_WQ 69 > -#define C_XIT 70 > -#define C_YANK 71 > -#define C_Z 72 > -#define C_SUBTILDE 73 > +#define C_SUBSTITUTE 53 > +#define C_T 54 > +#define C_TAG 55 > +#define C_TAGNEXT 56 > +#define C_TAGPOP 57 > +#define C_TAGPREV 58 > +#define C_TAGTOP 59 > +#define C_UNDO 60 > +#define C_UNABBREVIATE 61 > +#define C_UNMAP 62 > +#define C_V 63 > +#define C_VERSION 64 > +#define C_VISUAL_EX 65 > +#define C_VISUAL_VI 66 > +#define C_VIUSAGE 67 > +#define C_WRITE 68 > +#define C_WN 69 > +#define C_WQ 70 > +#define C_XIT 71 > +#define C_YANK 72 > +#define C_Z 73 > +#define C_SUBTILDE 74 >