Skip to content

Commit db16dce

Browse files
committed
Quote rc commands if necessary
Surround an argument with quotes before assembling it into a command base on whether a command requires quoting to be parsed by rc as it was received through args. If the arg contains any of rc's special characters or whitespace as documented in rc(1), it is quoted and any ' characters are escaped to ''. The quoted command string is also appended to the dump command. Fixes #135
1 parent 96bdba9 commit db16dce

File tree

1 file changed

+21
-1
lines changed

1 file changed

+21
-1
lines changed

acme/Watch/main.go

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@ import (
4747
"9fans.net/go/acme"
4848
)
4949

50+
const rcspecial = "#;&|^$=`'{}()<> \t\n"
51+
5052
var args []string
5153
var win *acme.Win
5254
var needrun = make(chan bool, 1)
@@ -64,6 +66,8 @@ func main() {
6466
flag.Parse()
6567
args = flag.Args()
6668

69+
escaped := rcquote(args)
70+
6771
var err error
6872
win, err = acme.New()
6973
if err != nil {
@@ -78,9 +82,10 @@ func main() {
7882
if *recursive {
7983
cmd += " -r"
8084
}
85+
cmd += " " + escaped
8186
win.Ctl(cmd)
8287
win.Fprintf("tag", "Get Kill Quit ")
83-
win.Fprintf("body", "%% %s\n", strings.Join(args, " "))
88+
win.Fprintf("body", "%% %s\n", escaped)
8489

8590
needrun <- true
8691
go events()
@@ -329,3 +334,18 @@ func runBackground(id int, dir string) {
329334
// Continue loop with lock held
330335
}
331336
}
337+
338+
func rcquote(args []string) string {
339+
var b strings.Builder
340+
for i, arg := range args {
341+
if i != 0 {
342+
b.WriteRune(' ')
343+
}
344+
if strings.ContainsAny(arg, rcspecial) {
345+
fmt.Fprintf(&b, "'%s'", strings.ReplaceAll(arg, "'", "''"))
346+
} else {
347+
b.WriteString(arg)
348+
}
349+
}
350+
return b.String()
351+
}

0 commit comments

Comments
 (0)