cmd/drover: ReElevate — surface UTF16 + Getwd errors, escape quotes
Code review found 5 silently-ignored errors in ReElevate (UTF16 conversions and os.Getwd) plus unescaped argument quoting that breaks args containing literal `"`. Each error is now wrapped with a clear message; quotes are backslash-escaped per the MSVC argv convention. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -3,7 +3,9 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
|
"strings"
|
||||||
"syscall"
|
"syscall"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
||||||
@@ -59,15 +61,23 @@ func ReElevate(args []string) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
verb, _ := syscall.UTF16PtrFromString("runas")
|
verb, err := syscall.UTF16PtrFromString("runas")
|
||||||
exePtr, _ := syscall.UTF16PtrFromString(exe)
|
if err != nil {
|
||||||
|
return fmt.Errorf("encode verb: %w", err)
|
||||||
|
}
|
||||||
|
exePtr, err := syscall.UTF16PtrFromString(exe)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("encode exe: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
var paramsPtr *uint16
|
var paramsPtr *uint16
|
||||||
if len(args) > 0 {
|
if len(args) > 0 {
|
||||||
// Quote each arg in case of spaces.
|
// Quote each arg in case of spaces, and escape internal quotes.
|
||||||
quoted := make([]string, len(args))
|
quoted := make([]string, len(args))
|
||||||
for i, a := range args {
|
for i, a := range args {
|
||||||
quoted[i] = `"` + a + `"`
|
// Escape any internal quotes with backslash (MSVC argv convention).
|
||||||
|
escaped := strings.ReplaceAll(a, "\"", "\\\"")
|
||||||
|
quoted[i] = `"` + escaped + `"`
|
||||||
}
|
}
|
||||||
joined := ""
|
joined := ""
|
||||||
for i, q := range quoted {
|
for i, q := range quoted {
|
||||||
@@ -76,11 +86,20 @@ func ReElevate(args []string) error {
|
|||||||
}
|
}
|
||||||
joined += q
|
joined += q
|
||||||
}
|
}
|
||||||
paramsPtr, _ = syscall.UTF16PtrFromString(joined)
|
paramsPtr, err = syscall.UTF16PtrFromString(joined)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("encode params: %w", err)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
cwd, _ := os.Getwd()
|
cwd, err := os.Getwd()
|
||||||
cwdPtr, _ := syscall.UTF16PtrFromString(cwd)
|
if err != nil {
|
||||||
|
return fmt.Errorf("get cwd: %w", err)
|
||||||
|
}
|
||||||
|
cwdPtr, err := syscall.UTF16PtrFromString(cwd)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("encode cwd: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
// SW_NORMAL = 1
|
// SW_NORMAL = 1
|
||||||
return windows.ShellExecute(0, verb, exePtr, paramsPtr, cwdPtr, 1)
|
return windows.ShellExecute(0, verb, exePtr, paramsPtr, cwdPtr, 1)
|
||||||
|
|||||||
Reference in New Issue
Block a user