rclone/vfs/vfstest/write_unix.go

70 lines
1.5 KiB
Go
Raw Normal View History

2021-09-09 14:25:25 +02:00
//go:build linux || darwin || freebsd
2017-05-10 12:19:32 +02:00
package vfstest
2017-05-10 12:19:32 +02:00
import (
"runtime"
2017-05-10 12:19:32 +02:00
"testing"
"github.com/rclone/rclone/vfs/vfscommon"
2017-05-10 12:19:32 +02:00
"github.com/stretchr/testify/assert"
2024-06-24 16:37:41 +02:00
"github.com/stretchr/testify/require"
"golang.org/x/sys/unix"
2017-05-10 12:19:32 +02:00
)
// TestWriteFileDoubleClose tests double close on write
func TestWriteFileDoubleClose(t *testing.T) {
run.skipIfVFS(t)
2017-05-10 12:19:32 +02:00
run.skipIfNoFUSE(t)
if runtime.GOOS == "darwin" {
t.Skip("Skipping test on OSX")
}
2017-05-10 12:19:32 +02:00
out, err := osCreate(run.path("testdoubleclose"))
2024-06-24 16:37:41 +02:00
require.NoError(t, err)
2017-05-10 12:19:32 +02:00
fd := out.Fd()
fd1, err := unix.Dup(int(fd))
2017-05-10 12:19:32 +02:00
assert.NoError(t, err)
fd2, err := unix.Dup(int(fd))
2017-05-10 12:19:32 +02:00
assert.NoError(t, err)
// close one of the dups - should produce no error
err = unix.Close(fd1)
2017-05-10 12:19:32 +02:00
assert.NoError(t, err)
// write to the file
buf := []byte("hello")
n, err := out.Write(buf)
assert.NoError(t, err)
assert.Equal(t, 5, n)
// close it
err = out.Close()
assert.NoError(t, err)
// write to the other dup
_, err = unix.Write(fd2, buf)
if run.vfsOpt.CacheMode < vfscommon.CacheModeWrites {
// produces an error if cache mode < writes
assert.Error(t, err, "input/output error")
} else {
// otherwise does not produce an error
assert.NoError(t, err)
}
2017-05-10 12:19:32 +02:00
// close the dup - should not produce an error
err = unix.Close(fd2)
assert.NoError(t, err)
2017-05-10 12:19:32 +02:00
run.waitForWriters()
2017-05-10 12:19:32 +02:00
run.rm(t, "testdoubleclose")
}
// writeTestDup performs the platform-specific implementation of the dup() unix
func writeTestDup(oldfd uintptr) (uintptr, error) {
newfd, err := unix.Dup(int(oldfd))
return uintptr(newfd), err
}