Links from unknown referers are now blocked by default, to prevent XSS attacks. This may break browsers that don't supply a Referer: HTTP header.
---- Changes since 1.400 ----
Big Czech translation updates, thanks to Petr Vanek and the Czech translation team.
+All popups in Webmin are now XSS-safe, and thus do not need protection from unknown referers which prevented them from working in some browsers.
+All Webmin session IDs are now stored MD5 hashed, to prevent sessions from being captured if the sessiondb DBM is somehow read by an attacker.
+Many Dutch updates, thanks to Gandyman.
-Webmin Version 1.400
+Webmin Version 1.403
--------------------
Webmin is a web-based interface for system administration for Unix.
Using any browser that supports tables and forms, you can setup user
&ReadParse();
%text = &load_language($current_theme);
-# Work out what categories we have
+# Work out what modules and categories we have
@modules = &get_visible_module_infos();
+if (&get_product_name() eq 'webmin') {
+ @unmodules = grep { $_->{'installed'} eq '0' } @modules;
+ @modules = grep { $_->{'installed'} ne '0' } @modules;
+ }
%cats = &list_categories(\@modules);
if (defined($cats{''})) {
$cats{'others'} = $cats{''};
}
print "</div>\n";
}
+
+ # Show un-installed modules
+ if (@unmodules) {
+ &print_category_opener('_unused', $in{'_unused'} ? 1 : 0,
+ "<font color=#888888>$text{'main_unused'}</font>");
+ $cls = $in{'_unused'} ? "itemshown" : "itemhidden";
+ print "<div class='$cls' id='_unused'>";
+ foreach $minfo (@unmodules) {
+ &print_category_link("$minfo->{'dir'}/",
+ $minfo->{'desc'},
+ undef,
+ undef,
+ $minfo->{'noframe'} ? "_top" : "",
+ );
+ }
+ print "</div>\n";
+ }
}
# Show module/help search form
print "<div class='aftericon'><a target=right href='feedback_form.cgi'>$text{'left_feedback'}</a></div></div>\n";
}
+# Show refesh modules link, for master admin
+if (&foreign_available("webmin")) {
+ print "<div class='linkwithicon'><img src=images/refresh-small.gif>\n";
+ print "<div class='aftericon'><a target=right href='webmin/refresh_modules.cgi'>$text{'main_refreshmods'}</a></div></div>\n";
+ }
+
# Show logout link
&get_miniserv_config(\%miniserv);
if ($miniserv{'logout'} && !$ENV{'SSL_USER'} && !$ENV{'LOCAL_USER'} &&
return $rv;
}
+sub theme_post_change_modules
+{
+print "<script>\n";
+print "top.left.location = top.left.location;\n";
+print "</script>\n";
+}
+
+1;
+
&foreign_call($m, "config_post_save", \%config, \%oldconfig);
}
+# Refresh installed modules
+if (&foreign_check("webmin")) {
+ &foreign_require("webmin", "webmin-lib.pl");
+ &webmin::build_installed_modules(0, $m);
+ }
+
&webmin_log("_config_", undef, undef, \%in, $m);
&redirect("/$m/");
else {
&error_exit("Unknown permissions $perms");
}
-
- # Open passive port
- $pasv = &ftp_command("PASV", 2, \$err);
- $pasv || &error_exit("FTP port failed : $err");
- $pasv =~ /\(([0-9,]+)\)/;
- @n = split(/,/ , $1);
- &open_socket("$n[0].$n[1].$n[2].$n[3]", $n[4]*256 + $n[5],
- "CON", \$err) ||
- &error_exit("FTP port failed : $err");
-
- if ($mode == 0) {
- # Read from file
- &ftp_command("RETR $file", 1, \$err) ||
- &error_exit("FTP read failed : $err");
- $opened = 1;
- }
- elsif ($mode == 1) {
- # Create new file if requested by the client, or if
- # the touch command was specified by the caller
- &ftp_command("STOR $file", 1, \$err) ||
- &error_exit("FTP write failed : $err");
- $touched = 0;
- $opened = 1;
- }
- elsif ($mode == 2) {
- # Otherwise append to the file
- &ftp_command("APPE $file", 1, \$err) ||
- &error_exit("FTP write failed : $err");
- $opened = 1;
- }
- else {
- $opened = 0;
- }
print "A0\n";
}
elsif ($line =~ /^W(\d+)/) {
# Write to FTP server
- $opened || &error_exit("FTP connection not opened yet");
+ if ($opened != 1) {
+ &open_ftp_file($mode);
+ }
+ #$opened || &error_exit("FTP connection not opened yet");
$len = $1;
read(STDIN, $buf, $len);
$wrote = (print CON $buf);
}
elsif ($line =~ /^R(\d+)/) {
# Read from to FTP server
- # XXX doesn't work yet?
- $opened || &error_exit("FTP connection not opened yet");
+ if ($opened != 2) {
+ &open_ftp_file(0);
+ }
$len = $1;
$read = read(CON, $buf, $len);
if ($read >= 0) {
return $rv;
}
+sub open_ftp_file
+{
+local ($mode) = @_;
+
+# Open passive port
+local $pasv = &ftp_command("PASV", 2, \$err);
+$pasv || &error_exit("FTP port failed : $err");
+$pasv =~ /\(([0-9,]+)\)/;
+local @n = split(/,/ , $1);
+&open_socket("$n[0].$n[1].$n[2].$n[3]", $n[4]*256 + $n[5],
+ "CON", \$err) ||
+ &error_exit("FTP port failed : $err");
+
+if ($mode == 0) {
+ # Read from file
+ &ftp_command("RETR $file", 1, \$err) ||
+ &error_exit("FTP read failed : $err");
+ $opened = 2;
+ }
+elsif ($mode == 1) {
+ # Create new file if requested by the client, or if
+ # the touch command was specified by the caller
+ &ftp_command("STOR $file", 1, \$err) ||
+ &error_exit("FTP write failed : $err");
+ $touched = 0;
+ $opened = 1;
+ }
+elsif ($mode == 2) {
+ # Otherwise append to the file
+ &ftp_command("APPE $file", 1, \$err) ||
+ &error_exit("FTP write failed : $err");
+ $opened = 1;
+ }
+else {
+ $opened = 0;
+ }
+}
dump_ermt=Missing or invalid path to <tt>rmt</tt> program
dump_reverify=Attempt test restore after backup to verify?
dump_remount=Remount with <tt>noatime</tt> option during backup?
+dump_eftpupdate=Adding files to an existing archive is not possible when using FTP.
edit_err=Failed to create backup
edit_edir=Missing backup directory
$_[0]->{'multi'} = $in{'multi'};
$_[0]->{'links'} = $in{'links'};
$_[0]->{'xdev'} = $in{'xdev'};
+ if ($in{'update'} && $in{'rsh_def'} == 3) {
+ # Cannot append via FTP
+ &error($text{'dump_eftpupdate'});
+ }
$_[0]->{'update'} = $in{'update'};
if ($in{'gzip'} && $in{'update'}) {
&error($text{'dump_egzip3'});
main_skill=Skill level
main_readonly=(Read-only mode)
main_return=Return to $1
+main_unused=Un-used Modules
+main_refreshmods=Refesh Modules
link_essl=The Net::SSLeay Perl module needed to make HTTPS connections is not installed on your system.
if (!$webmail) {
# Add to our repository
chdir("/usr/local/webadmin/deb/repository");
+ system("reprepro -Vb . remove sarge $product");
system("reprepro -Vb . includedeb sarge ../${product}_${ver}_all.deb");
}
"config-lib.pl", "entities_map.txt", "ui-lib.pl",
"password_form.cgi", "password_change.cgi", "pam_login.cgi",
"module_chooser.cgi", "config-windows", "xmlrpc.cgi",
- "uptracker.cgi", "create-module.pl", "webmin_search.cgi" );
+ "uptracker.cgi", "create-module.pl", "webmin_search.cgi",
+ );
if ($min) {
# Only those required by others
@mlist = ("cron", "init", "inittab", "proc", "webmin", "acl", "servers",
system("rm -rf $zipdir/webmin");
system("mkdir $zipdir/webmin");
system("cp -rp $tardir/$dir/* $zipdir/webmin");
- system("rm -rf $zipdir/webmin/{fdisk,exports,bsdexports,hpuxexports,sgiexports,zones,rbac}");
+ system("rm -rf $zipdir/webmin/{fdisk,exports,bsdexports,hpuxexports,sgiexports,zones,rbac,Webmin}");
system("rm -rf $zipdir/webmin/acl/Authen-SolarisRBAC-0.1/*");
system("rm -f $zipdir/webmin/software/msi-lib.pl");
system("echo zip >$zipdir/webmin/install-type");
&webmin_log($config{'update_system'}, "install", undef,
{ 'packages' => \@packs } ) if (@packs);
+ if ($in{'caller'} && &foreign_check("webmin")) {
+ # Software installed - refresh installed flag cache
+ &foreign_require("webmin", "webmin-lib.pl");
+ ($inst, $changed) =
+ &webmin::build_installed_modules(0, $in{'caller'});
+ if (@$changed && defined(&theme_post_change_modules)) {
+ &theme_post_change_modules();
+ }
+ }
+
if ($in{'return'}) {
&ui_print_footer($in{'return'}, $in{'returndesc'});
}
return undef if (!&foreign_check($module_name));
local $pkg = &update_system_resolve($name);
return undef if (!$pkg);
-return &text('missing_link', $desc, "../$module_name/install_pack.cgi?source=3&update=".&urlize($pkg)."&return=".&urlize($return)."&returndesc=".&urlize($returndesc), $text{$update_system."_name"});
+local ($cpkg) = caller();
+local $caller = eval '$'.$cpkg.'::module_name';
+return &text('missing_link', $desc, "../$module_name/install_pack.cgi?source=3&update=".&urlize($pkg)."&return=".&urlize($return)."&returndesc=".&urlize($returndesc)."&caller=".&urlize($caller), $text{$update_system."_name"});
}
# update_system_button(field-name, label)
return &theme_ui_form_start(@_) if (defined(&theme_ui_form_start));
local ($script, $method, $target, $tags) = @_;
local $rv;
-$rv .= "<form class='ui_form' action='$script' ".
+$rv .= "<form class='ui_form' action='".&html_escape($script)."' ".
($method eq "post" ? "method=post" :
$method eq "form-data" ?
"method=post enctype=multipart/form-data" :
$rv .= "</tr>\n";
}
$rv .= "</table>\n";
-if ($title) {
+if (defined($title)) {
$rv = "<table class=ui_table border ".
($width ? " width=$width%" : "").">\n".
- "<tr $tb> <td><b>$title</b></td> </tr>\n".
+ ($title ? "<tr $tb> <td><b>$title</b></td> </tr>\n" : "").
"<tr $cb> <td>$rv</td> </tr>\n".
"</table>";
}
$m->{'desc'} = $gaccess{"desc_".$m->{'dir'}};
}
}
+
+# Apply installed flags
+local %installed;
+&read_file_cached("$config_directory/installed.cache", \%installed);
+foreach $m (@rv) {
+ $m->{'installed'} = $installed{$m->{'dir'}};
+ }
+
return @rv;
}
blocked_cleardesc=Click this button to clear all current host and user blocks, by restarting the Webmin server process.
blocked_restarting=The Webmin server process is now restarting to clear blocked hosts and users - please wait for a few seconds before continuing.
+refreshmods_title=Refresh Modules
+refreshmods_installed=Checking for usable Webmin modules ..
+refeshmods_counts=.. found $2 with installed applications, $1 not installed.
--- /dev/null
+
+require 'webmin-lib.pl';
+
+# Update cache of which module's underlying servers are installed
+sub module_install
+{
+&build_installed_modules();
+}
+
return undef;
}
+# build_installed_modules(force-all, force-mod)
+# Calls each module's install_check function, and updates the cache of
+# modules whose underlying servers are installed.
+sub build_installed_modules
+{
+local ($force, $mod) = @_;
+local %installed;
+local $changed;
+&read_file_cached("$config_directory/installed.cache", \%installed);
+local @changed;
+foreach my $minfo (&get_all_module_infos()) {
+ next if ($mod && $minfo->{'dir'} ne $mod);
+ next if (defined($installed{$minfo->{'dir'}}) && !$force && !$mod);
+ next if (!&check_os_support($minfo));
+ $@ = undef;
+ local $o = $installed{$minfo->{'dir'}};
+ eval {
+ local $main::error_must_die = 1;
+ $installed{$minfo->{'dir'}} =
+ &foreign_installed($minfo->{'dir'}, 0) ? 1 : 0;
+ };
+ if ($@) {
+ # Couldn't check .. assume no
+ $installed{$minfo->{'dir'}} = 0;
+ }
+ push(@changed, $minfo->{'dir'}) if ($installed{$minfo->{'dir'}} ne $o);
+ }
+&write_file("$config_directory/installed.cache", \%installed);
+return wantarray ? (\%installed, \@changed) : \%installed;
+}
+
1;