mirror of
https://github.com/drakkan/sftpgo.git
synced 2025-12-06 14:20:55 +03:00
rsync: enforce a supported format and limit the allowed options
Many rsync options are unsafe to use in restricted environments and may pose security risks. Signed-off-by: Nicola Murino <nicola.murino@gmail.com>
This commit is contained in:
@@ -844,7 +844,7 @@ func TestRsyncOptions(t *testing.T) {
|
||||
}
|
||||
cmd, err := sshCmd.getSystemCommand()
|
||||
assert.NoError(t, err)
|
||||
assert.True(t, slices.Contains(cmd.cmd.Args, "--safe-links"),
|
||||
assert.Equal(t, []string{"rsync", "--server", "-vlogDtprze.iLsfxC", "--safe-links", ".", user.HomeDir + "/"}, cmd.cmd.Args,
|
||||
"--safe-links must be added if the user has the create symlinks permission")
|
||||
|
||||
permissions["/"] = []string{dataprovider.PermDownload, dataprovider.PermUpload, dataprovider.PermCreateDirs,
|
||||
@@ -854,6 +854,12 @@ func TestRsyncOptions(t *testing.T) {
|
||||
conn = &Connection{
|
||||
BaseConnection: common.NewBaseConnection("", common.ProtocolSFTP, "", "", user),
|
||||
}
|
||||
sshCmd = sshCommand{
|
||||
command: "rsync",
|
||||
connection: conn,
|
||||
}
|
||||
_, err = sshCmd.getSystemCommand()
|
||||
assert.Error(t, err)
|
||||
sshCmd = sshCommand{
|
||||
command: "rsync",
|
||||
connection: conn,
|
||||
@@ -861,8 +867,8 @@ func TestRsyncOptions(t *testing.T) {
|
||||
}
|
||||
cmd, err = sshCmd.getSystemCommand()
|
||||
assert.NoError(t, err)
|
||||
assert.True(t, slices.Contains(cmd.cmd.Args, "--munge-links"),
|
||||
"--munge-links must be added if the user has the create symlinks permission")
|
||||
assert.Equal(t, []string{"rsync", "--server", "-vlogDtprze.iLsfxC", "--munge-links", ".", user.HomeDir + "/"}, cmd.cmd.Args,
|
||||
"--munge-links must be added if the user hasn't the create symlinks permission")
|
||||
|
||||
sshCmd.connection.User.VirtualFolders = append(sshCmd.connection.User.VirtualFolders, vfs.VirtualFolder{
|
||||
BaseVirtualFolder: vfs.BaseVirtualFolder{
|
||||
@@ -2241,3 +2247,43 @@ func TestAuthenticationErrors(t *testing.T) {
|
||||
assert.ErrorIs(t, err, sftpAuthError)
|
||||
assert.NotErrorIs(t, err, util.ErrNotFound)
|
||||
}
|
||||
|
||||
func TestRsyncArguments(t *testing.T) {
|
||||
assert.False(t, canAcceptRsyncArgs(nil))
|
||||
args := []string{"-e", "--server"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.iLsfxCIvu", ".", "."}
|
||||
assert.True(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "--server", "-vlogDtpre.iLsfxCIvu", ".", "."}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "..", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.iLsfxCIvu", ".", "."}
|
||||
assert.True(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.iLsfxCIvu", "--delete", ".", "/"}
|
||||
assert.True(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.iLsfxCIvu", "--delete", ".", "/"}
|
||||
assert.True(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.iLsfxCIvu", "--delete", "/", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.iLsfxCIvu", ".", "path1", "path2"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.iLsfxCIvu", "."}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--sender", "-vlogDtpre.iLsfxCIvu", "--delete", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.", "--delete", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-vlogDtpre.", "--delete", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "--sender", "-e.iLsfxCIvu", "--delete", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.iLsfxCIvu", "--delete", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.iLsfxCIvu", "--delete", "--safe-links"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
args = []string{"--server", "-vlogDtpre.iLsfxCIvu", "--unsupported-option", ".", "/"}
|
||||
assert.False(t, canAcceptRsyncArgs(args))
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user