diff options
Diffstat (limited to 'xmake')
| -rw-r--r-- | xmake/core/base/os.lua | 45 | ||||
| -rw-r--r-- | xmake/core/sandbox/modules/os.lua | 6 |
2 files changed, 51 insertions, 0 deletions
diff --git a/xmake/core/base/os.lua b/xmake/core/base/os.lua index 9332f2c61..86f04e35d 100644 --- a/xmake/core/base/os.lua +++ b/xmake/core/base/os.lua @@ -1106,6 +1106,51 @@ function os.iorunv(program, argv, opt) return ok == 0, outdata, errdata, errors end +-- run command in the given shell and return output and error data +-- +-- @param shell the shell name (e.g. sh, bash, zsh, cmd, pwsh, powershell) +-- @param cmd the command string +-- @param opt the options +-- +-- @return ok, stdout, stderr, errors +-- +function os.iorun_in_shell(shell, cmd, opt) + + -- check + if not shell or not cmd then + return false, nil, nil, "invalid arguments" + end + + -- run in pwsh/powershell + if shell == "pwsh" or shell == "powershell" then + local shell_cmd = string.format("& { %s; exit $LASTEXITCODE }", cmd) + return os.iorunv(shell, {"-c", shell_cmd}, opt) + + -- run in cmd + elseif shell == "cmd" then + + -- use batfile to robust pipe handling + local batfile = os.tmpfile() .. ".bat" + local batch_content = "@echo off\n" + + -- append command + batch_content = batch_content .. cmd .. "\n" + + -- append exit code check + batch_content = batch_content .. "if %errorlevel% neq 0 exit /b %errorlevel%\n" + + io.writefile(batfile, batch_content) + + local ok, out, err, errors = os.iorunv(batfile, {}, opt) + os.rm(batfile) + return ok, out, err, errors + + -- run in sh/bash/zsh... + else + return os.iorunv(shell, {"-c", cmd}, opt) + end +end + -- raise an exception and abort the current script -- -- the parent function will capture it if we uses pcall or xpcall diff --git a/xmake/core/sandbox/modules/os.lua b/xmake/core/sandbox/modules/os.lua index aebb3cfb0..ec5cb0e1e 100644 --- a/xmake/core/sandbox/modules/os.lua +++ b/xmake/core/sandbox/modules/os.lua @@ -324,6 +324,12 @@ function sandbox_os.iorunv(program, argv, opt) return outdata, errdata end +-- run command in shell with io redirection and return (ok, out, err) +function sandbox_os.iorun_in_shell(shell, cmd, ...) + cmd = vformat(cmd, ...) + return os.iorun_in_shell(shell, cmd) +end + -- execute command function sandbox_os.exec(cmd, ...) cmd = vformat(cmd, ...) |
