351 lines
8.6 KiB
Perl
351 lines
8.6 KiB
Perl
#-*- Mode: perl; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
|
#
|
|
# Copyright (C) 2000-2001 Ximian, Inc.
|
|
#
|
|
# Authors: Hans Petter Jansson <hpj@ximian.com>
|
|
#
|
|
# This program is free software; you can redistribute it and/or modify
|
|
# it under the terms of the GNU Library General Public License as published
|
|
# by the Free Software Foundation; either version 2 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU Library General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU Library General Public License
|
|
# along with this program; if not, write to the Free Software
|
|
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
|
|
|
|
package Shares::SMB;
|
|
|
|
use Utils::File;
|
|
|
|
# --- share_export_smb_info; information on a particular SMB export --- #
|
|
|
|
sub gst_share_smb_info_set
|
|
{
|
|
my ($info, $key, $value) = @_;
|
|
|
|
if ($value eq "")
|
|
{
|
|
delete $info->{$key};
|
|
}
|
|
else
|
|
{
|
|
$info->{$key} = $value;
|
|
}
|
|
}
|
|
|
|
sub gst_share_smb_info_get_name
|
|
{
|
|
return $_[0]->{'name'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_name
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'name', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_point
|
|
{
|
|
return $_[0]->{'point'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_point
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'point', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_comment
|
|
{
|
|
return $_[0]->{'comment'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_comment
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'comment', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_enabled
|
|
{
|
|
return $_[0]->{'enabled'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_enabled
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'enabled', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_browse
|
|
{
|
|
return $_[0]->{'browse'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_browse
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'browse', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_public
|
|
{
|
|
return $_[0]->{'public'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_public
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'public', $_[1]);
|
|
}
|
|
|
|
sub gst_share_smb_info_get_write
|
|
{
|
|
return $_[0]->{'write'};
|
|
}
|
|
|
|
sub gst_share_smb_info_set_write
|
|
{
|
|
&gst_share_smb_info_set ($_[0], 'write', $_[1]);
|
|
}
|
|
|
|
|
|
# --- share_smb_table; multiple instances of share_smb_info --- #
|
|
|
|
sub smb_table_find
|
|
{
|
|
my ($name, $shares) = @_;
|
|
|
|
foreach $i (@$shares)
|
|
{
|
|
return $i if ($$i[0] eq $name)
|
|
}
|
|
|
|
return undef;
|
|
}
|
|
|
|
sub get_distro_smb_file
|
|
{
|
|
my ($smb_comb);
|
|
|
|
my %dist_map =
|
|
(
|
|
"debian" => "debian",
|
|
"redhat-6.2" => "redhat-6.2",
|
|
"redhat-7.0" => "debian",
|
|
"redhat-7.1" => "debian",
|
|
"redhat-7.2" => "debian",
|
|
"redhat-7.3" => "debian",
|
|
"redhat-8.0" => "debian",
|
|
"mandrake-9.0" => "debian",
|
|
"suse-9.0" => "debian",
|
|
"slackware-9.1.0" => "debian",
|
|
"gentoo" => "debian",
|
|
"archlinux" => "debian",
|
|
"pld-1.0" => "pld-1.0",
|
|
"vine-3.0" => "debian",
|
|
"freebsd-5" => "freebsd-5",
|
|
);
|
|
|
|
my %dist_tables =
|
|
(
|
|
"redhat-6.2" => "/etc/smb.conf",
|
|
"debian" => "/etc/samba/smb.conf",
|
|
"pld-1.0" => "/etc/smb/smb.conf",
|
|
"freebsd-5" => "/usr/local/etc/smb.conf",
|
|
);
|
|
|
|
my $dist = $dist_map {$Utils::Backend::tool{"platform"}};
|
|
return $dist_tables{$dist} if $dist;
|
|
return undef;
|
|
}
|
|
|
|
sub get_share_info
|
|
{
|
|
my ($smb_conf_name, $section) = @_;
|
|
my @share;
|
|
|
|
push @share, $section;
|
|
push @share, &Utils::Parse::get_from_ini ($smb_conf_name, $section, "path");
|
|
push @share, &Utils::Parse::get_from_ini ($smb_conf_name, $section, "comment");
|
|
push @share, &Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "available");
|
|
push @share, &Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "browsable") ||
|
|
&Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "browseable");
|
|
push @share, &Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "public") ||
|
|
&Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "guest");
|
|
push @share, &Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "writable") ||
|
|
&Utils::Parse::get_from_ini_bool ($smb_conf_name, $section, "writeable");
|
|
|
|
return \@share;
|
|
}
|
|
|
|
sub set_share_info
|
|
{
|
|
my ($smb_conf_file, $share) = @_;
|
|
my ($section);
|
|
|
|
$section = shift (@$share);
|
|
|
|
&Utils::Replace::set_ini ($smb_conf_file, $section, "path", shift (@$share));
|
|
&Utils::Replace::set_ini ($smb_conf_file, $section, "comment", shift (@$share));
|
|
&Utils::Replace::set_ini_bool ($smb_conf_file, $section, "available", shift (@$share));
|
|
&Utils::Replace::set_ini_bool ($smb_conf_file, $section, "browsable", shift (@$share));
|
|
&Utils::Replace::set_ini_bool ($smb_conf_file, $section, "public", shift (@$share));
|
|
&Utils::Replace::set_ini_bool ($smb_conf_file, $section, "writable", shift (@$share));
|
|
|
|
&Utils::Replace::remove_ini_var ($smb_conf_file, $section, "browseable");
|
|
&Utils::Replace::remove_ini_var ($smb_conf_file, $section, "guest");
|
|
&Utils::Replace::remove_ini_var ($smb_conf_file, $section, "writeable");
|
|
}
|
|
|
|
sub get_shares
|
|
{
|
|
my ($smb_conf_file) = @_;
|
|
my (@sections, @table, $share);
|
|
|
|
# Get the sections.
|
|
@sections = &Utils::Parse::get_ini_sections ($smb_conf_file);
|
|
|
|
for $section (@sections)
|
|
{
|
|
next if ($section =~ /^(global)|(homes)|(printers)|(print\$)$/);
|
|
next if (&Utils::Parse::get_from_ini_bool ($smb_conf_file, $section, "printable"));
|
|
|
|
$share = &get_share_info ($smb_conf_file, $section);
|
|
push @table, $share;
|
|
}
|
|
|
|
return \@table;
|
|
}
|
|
|
|
sub get_smb_users
|
|
{
|
|
my ($fd, @info, $users);
|
|
|
|
$fd = &Utils::File::run_pipe_read ("pdbedit -L");
|
|
return [] if (!$fd);
|
|
|
|
while (<$fd>)
|
|
{
|
|
chomp;
|
|
@info = split (/:/, $_);
|
|
push @$users, [ $info[0], "" ];
|
|
}
|
|
|
|
return $users;
|
|
}
|
|
|
|
sub get
|
|
{
|
|
my ($smb_conf_file);
|
|
my ($shares, $workgroup, $desc, $wins, $winsserver, $users);
|
|
|
|
$smb_conf_file = &get_distro_smb_file;
|
|
$shares = &get_shares ($smb_conf_file);
|
|
|
|
$workgroup = &Utils::Parse::get_from_ini ($smb_conf_file, "global", "workgroup");
|
|
$smbdesc = &Utils::Parse::get_from_ini ($smb_conf_file, "global", "server string");
|
|
$wins = &Utils::Parse::get_from_ini_bool ($smb_conf_file, "global", "wins support");
|
|
$winsserver = &Utils::Parse::get_from_ini ($smb_conf_file, "global", "wins server");
|
|
$users = &get_smb_users ();
|
|
|
|
return ($shares, $workgroup, $smbdesc, $wins, $winsserver, $users);
|
|
}
|
|
|
|
sub set_shares
|
|
{
|
|
my ($smb_conf_file, $shares) = @_;
|
|
my (@sections, $section, $share);
|
|
|
|
# Get the sections.
|
|
@sections = &Utils::Parse::get_ini_sections ($smb_conf_file);
|
|
|
|
# remove deleted sections
|
|
foreach $section (@sections)
|
|
{
|
|
next if ($section =~ /^(global)|(homes)|(printers)|(print\$)$/);
|
|
next if (&Utils::Parse::get_from_ini_bool ($smb_conf_file, $section, "printable"));
|
|
|
|
if (!&smb_table_find ($section, $shares))
|
|
{
|
|
Utils::Replace::remove_ini_section ($smb_conf_file, $section);
|
|
}
|
|
}
|
|
|
|
for $share (@$shares)
|
|
{
|
|
&set_share_info ($smb_conf_file, $share);
|
|
}
|
|
}
|
|
|
|
sub set_smb_users
|
|
{
|
|
my ($users) = @_;
|
|
my ($old_users, $user, $config, $state);
|
|
my ($hash, $old_hash, $pipe);
|
|
|
|
$old_users = &get_smb_users ();
|
|
|
|
foreach $user (@$users)
|
|
{
|
|
$$config{$$user[0]} |= 1;
|
|
$hash{$$user[0]} = $user;
|
|
}
|
|
|
|
foreach $user (@$old_users)
|
|
{
|
|
$$config{$$user[0]} |= 2;
|
|
$old_hash{$$user[0]} = $user;
|
|
}
|
|
|
|
foreach $i (keys %$config)
|
|
{
|
|
$state = $$config{$i};
|
|
$user = $hash{$i};
|
|
|
|
if ($state == 1 || ($state == 3 && $$user[1]))
|
|
{
|
|
# User added, or password was modified
|
|
$user = $hash{$i};
|
|
$pipe = &Utils::File::run_pipe_write ("smbpasswd -s -a $$user[0]");
|
|
# Have to write the password twice
|
|
print $pipe "$$user[1]\n";
|
|
print $pipe "$$user[1]\n";
|
|
&Utils::File::close_file ($pipe);
|
|
}
|
|
elsif ($state == 2)
|
|
{
|
|
# User deleted
|
|
$user = $old_hash{$i};
|
|
&Utils::File::run ("pdbedit", "--delete", "-u", $$user[0]);
|
|
}
|
|
}
|
|
}
|
|
|
|
sub set
|
|
{
|
|
my ($shares, $workgroup, $desc, $wins, $winsserver, $users) = @_;
|
|
my ($smb_conf_file);
|
|
my (@sections, $export);
|
|
|
|
$smb_conf_file = &get_distro_smb_file;
|
|
|
|
&set_shares ($smb_conf_file, $shares);
|
|
|
|
&Utils::Replace::set_ini ($smb_conf_file, "global", "workgroup", $workgroup);
|
|
&Utils::Replace::set_ini ($smb_conf_file, "global", "server string", $desc);
|
|
&Utils::Replace::set_ini_bool ($smb_conf_file, "global", "wins support", $wins);
|
|
&Utils::Replace::set_ini ($smb_conf_file, "global", "wins server", ($wins) ? "" : $winsserver);
|
|
|
|
&set_smb_users ($users);
|
|
}
|
|
|
|
sub get_files
|
|
{
|
|
my ($files);
|
|
|
|
push @$files, &get_distro_smb_file ();
|
|
return $files;
|
|
}
|
|
|
|
1;
|