From ef69007a43dca07a9e6e81e1450629de8410e1a5 Mon Sep 17 00:00:00 2001 From: Michael Stapelberg Date: Sat, 9 Apr 2022 00:11:47 +0200 Subject: [PATCH] =?UTF-8?q?use=20renameio=20to=20avoid=20=E2=80=9Ctext=20f?= =?UTF-8?q?ile=20busy=E2=80=9D=20errors?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Before this commit, extracting a breakglass would fail when /tmp/breakglass*/sh was busy because it was being run in a separate connection. --- go.mod | 1 + go.sum | 2 ++ scp.go | 6 +++--- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 9218e99..be0fc47 100644 --- a/go.mod +++ b/go.mod @@ -5,6 +5,7 @@ go 1.17 require ( github.com/gokrazy/gokrazy v0.0.0-20211024151958-b718dd90ae71 github.com/gokrazy/internal v0.0.0-20210621162516-1b3b5687a06d + github.com/google/renameio/v2 v2.0.0 github.com/google/shlex v0.0.0-20181106134648-c34317bd91bf github.com/kr/pty v1.1.8 github.com/pkg/sftp v1.13.0 diff --git a/go.sum b/go.sum index 1889fcd..5d0548f 100644 --- a/go.sum +++ b/go.sum @@ -11,6 +11,8 @@ github.com/gokrazy/internal v0.0.0-20210621162516-1b3b5687a06d/go.mod h1:Gqv1x1D github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/gopacket v1.1.16/go.mod h1:UCLx9mCmAwsVbn6qQl1WIEt2SO7Nd2fD0th1TBAsqBw= +github.com/google/renameio/v2 v2.0.0 h1:UifI23ZTGY8Tt29JbYFiuyIU3eX+RNFtUwefq9qAhxg= +github.com/google/renameio/v2 v2.0.0/go.mod h1:BtmJXm5YlszgC+TD4HOEEUFgkJP3nLxehU6hfe7jRt4= github.com/google/shlex v0.0.0-20181106134648-c34317bd91bf h1:7+FW5aGwISbqUtkfmIpZJGRgNFg2ioYPvFaUxdqpDsg= github.com/google/shlex v0.0.0-20181106134648-c34317bd91bf/go.mod h1:RpwtwJQFrIEPstU94h88MWPXP2ektJZ8cZ0YntAmXiE= github.com/kr/fs v0.1.0 h1:Jskdu9ieNAYnjxsi0LbQp1ulIKZV1LAFgK1tWhpZgl8= diff --git a/scp.go b/scp.go index 7ed9e56..9229c7c 100644 --- a/scp.go +++ b/scp.go @@ -11,6 +11,7 @@ import ( "strconv" "strings" + "github.com/google/renameio/v2" "golang.org/x/crypto/ssh" ) @@ -83,15 +84,14 @@ func scpSink(channel ssh.Channel, req *ssh.Request, cmdline []string) error { continue // directory, don’t try to OpenFile() it } mode := h.FileInfo().Mode() & os.ModePerm - out, err := os.OpenFile(h.Name, os.O_CREATE|os.O_TRUNC|os.O_WRONLY, mode) + out, err := renameio.NewPendingFile(h.Name, renameio.WithStaticPermissions(mode)) if err != nil { return err } if _, err := io.Copy(out, tr); err != nil { - out.Close() return err } - if err := out.Close(); err != nil { + if err := out.CloseAtomicallyReplace(); err != nil { return err } }