]> git.proxmox.com Git - pve-storage.git/blobdiff - PVE/Storage/CIFSPlugin.pm
content path overrides: allow single dots and enforce max-lengths
[pve-storage.git] / PVE / Storage / CIFSPlugin.pm
index a3f9ebedfc2383b2101c9aa4b032c073ee72c65d..6e20f4baf215f2f3654def4750fe427036b4682c 100644 (file)
@@ -13,11 +13,14 @@ use base qw(PVE::Storage::Plugin);
 
 # CIFS helper functions
 
-sub cifs_is_mounted {
-    my ($server, $share, $mountpoint, $mountdata) = @_;
+sub cifs_is_mounted : prototype($$) {
+    my ($scfg, $mountdata) = @_;
+
+    my ($mountpoint, $server, $share) = $scfg->@{'path', 'server', 'share'};
+    my $subdir = $scfg->{subdir} // "/";
 
     $server = "[$server]" if Net::IP::ip_is_ipv6($server);
-    my $source = "//${server}/$share";
+    my $source = "//${server}/$share$subdir";
     $mountdata = PVE::ProcFSTools::parse_proc_mounts() if !$mountdata;
 
     return $mountpoint if grep {
@@ -63,11 +66,14 @@ sub get_cred_file {
     return undef;
 }
 
-sub cifs_mount {
-    my ($server, $share, $mountpoint, $storeid, $smbver, $user, $domain) = @_;
+sub cifs_mount : prototype($$$$$) {
+    my ($scfg, $storeid, $smbver, $user, $domain) = @_;
+
+    my ($mountpoint, $server, $share) = $scfg->@{'path', 'server', 'share'};
+    my $subdir = $scfg->{subdir} // "/";
 
     $server = "[$server]" if Net::IP::ip_is_ipv6($server);
-    my $source = "//${server}/$share";
+    my $source = "//${server}/$share$subdir";
 
     my $cmd = ['/bin/mount', '-t', 'cifs', $source, $mountpoint, '-o', 'soft', '-o'];
 
@@ -128,12 +134,15 @@ sub properties {
 sub options {
     return {
        path => { fixed => 1 },
+       'content-dirs' => { optional => 1 },
        server => { fixed => 1 },
        share => { fixed => 1 },
+       subdir => { optional => 1 },
        nodes => { optional => 1 },
        disable => { optional => 1 },
        maxfiles => { optional => 1 },
        'prune-backups' => { optional => 1 },
+       'max-protected-backups' => { optional => 1 },
        content => { optional => 1 },
        format => { optional => 1 },
        username => { optional => 1 },
@@ -203,12 +212,8 @@ sub status {
     $cache->{mountdata} = PVE::ProcFSTools::parse_proc_mounts()
        if !$cache->{mountdata};
 
-    my $path = $scfg->{path};
-    my $server = $scfg->{server};
-    my $share = $scfg->{share};
-
     return undef
-       if !cifs_is_mounted($server, $share, $path, $cache->{mountdata});
+       if !cifs_is_mounted($scfg, $cache->{mountdata});
 
     return $class->SUPER::status($storeid, $scfg, $cache);
 }
@@ -220,17 +225,15 @@ sub activate_storage {
        if !$cache->{mountdata};
 
     my $path = $scfg->{path};
-    my $server = $scfg->{server};
-    my $share = $scfg->{share};
 
-    if (!cifs_is_mounted($server, $share, $path, $cache->{mountdata})) {
+    if (!cifs_is_mounted($scfg, $cache->{mountdata})) {
 
        mkpath $path if !(defined($scfg->{mkdir}) && !$scfg->{mkdir});
 
        die "unable to activate storage '$storeid' - " .
            "directory '$path' does not exist\n" if ! -d $path;
 
-       cifs_mount($server, $share, $path, $storeid, $scfg->{smbversion},
+       cifs_mount($scfg, $storeid, $scfg->{smbversion},
            $scfg->{username}, $scfg->{domain});
     }
 
@@ -244,10 +247,8 @@ sub deactivate_storage {
        if !$cache->{mountdata};
 
     my $path = $scfg->{path};
-    my $server = $scfg->{server};
-    my $share = $scfg->{share};
 
-    if (cifs_is_mounted($server, $share, $path, $cache->{mountdata})) {
+    if (cifs_is_mounted($scfg, $cache->{mountdata})) {
        my $cmd = ['/bin/umount', $path];
        run_command($cmd, errmsg => 'umount error');
     }
@@ -280,7 +281,7 @@ sub check_connection {
 
     if (my $err = $@) {
        die "$out_str\n" if defined($out_str) &&
-           ($out_str =~ m/NT_STATUS_ACCESS_DENIED/);
+           ($out_str =~ m/NT_STATUS_(ACCESS_DENIED|LOGON_FAILURE)/);
        return 0;
     }