mirror of
https://github.com/webmin/webmin.git
synced 2026-02-09 08:42:20 +00:00
Re-factored SSL cert creation code
This commit is contained in:
@@ -120,36 +120,8 @@ print &ui_table_start($text{'ssl_header1'}, undef, 2);
|
||||
|
||||
$host = $ENV{'HTTP_HOST'};
|
||||
$host =~ s/:.*//;
|
||||
print &ui_table_row($text{'ssl_cn'},
|
||||
&ui_opt_textbox("commonName", $host, 30,
|
||||
$text{'ssl_all'}));
|
||||
|
||||
print &ui_table_row($text{'ca_email'},
|
||||
&ui_textbox("emailAddress", $d->{'emailto'}, 30));
|
||||
|
||||
print &ui_table_row($text{'ca_ou'},
|
||||
&ui_textbox("organizationalUnitName", undef, 30));
|
||||
|
||||
$o = "Webmin Webserver on ".&get_system_hostname();
|
||||
print &ui_table_row($text{'ca_o'},
|
||||
&ui_textbox("organizationName", $o, 30));
|
||||
|
||||
print &ui_table_row($text{'ca_city'},
|
||||
&ui_textbox("cityName", undef, 30));
|
||||
|
||||
print &ui_table_row($text{'ca_sp'},
|
||||
&ui_textbox("stateOrProvinceName", undef, 15));
|
||||
|
||||
print &ui_table_row($text{'ca_c'},
|
||||
&ui_textbox("countryName", undef, 2));
|
||||
|
||||
print &ui_table_row($text{'ssl_size'},
|
||||
&ui_opt_textbox("size", undef, 6,
|
||||
"$text{'default'} ($default_key_size)").
|
||||
" ".$text{'ssl_bits'});
|
||||
|
||||
print &ui_table_row($text{'ssl_days'},
|
||||
&ui_textbox("days", 1825, 8));
|
||||
print &show_ssl_key_form($host, undef,
|
||||
"Webmin Webserver on ".&get_system_hostname());
|
||||
|
||||
print &ui_table_row($text{'ssl_newfile'},
|
||||
&ui_textbox("newfile", "$config_directory/miniserv.pem", 40));
|
||||
|
||||
@@ -364,6 +364,7 @@ newkey_ecat=An error occurred writing to the new key file :
|
||||
newkey_ok=Successfully generated the following SSL key.
|
||||
newkey_esize=Missing or invalid key size
|
||||
newkey_edays=Missing or invalid number of days before expiry
|
||||
newkey_ecountry=Country code must be two letters
|
||||
|
||||
startpage_title=Index Page Options
|
||||
startpage_intro2=This page allows you to control the appearance of the main Webmin menu. Some options may only be effective when using the default theme.
|
||||
|
||||
@@ -4,65 +4,17 @@
|
||||
|
||||
require './webmin-lib.pl';
|
||||
&ReadParse();
|
||||
|
||||
# Validate inputs
|
||||
&error_setup($text{'newkey_err'});
|
||||
$in{'commonName_def'} || $in{'commonName'} =~ /^[A-Za-z0-9\.\-\*]+$/ ||
|
||||
&error($text{'newkey_ecn'});
|
||||
$in{'newfile'} || &error($text{'newkey_efile'});
|
||||
$in{'size_def'} || $in{'size'} =~ /^\d+$/ || &error($text{'newkey_esize'});
|
||||
$in{'days'} =~ /^\d+$/ || &error($text{'newkey_edays'});
|
||||
|
||||
# Validate inputs and create the key
|
||||
$err = &parse_ssl_key_form(\%in, $in{'newfile'});
|
||||
&error($err) if ($err);
|
||||
|
||||
# Tell the user
|
||||
&ui_print_header(undef, $text{'newkey_title'}, "");
|
||||
|
||||
%aclconfig = &foreign_config('acl');
|
||||
&foreign_require("acl", "acl-lib.pl");
|
||||
if (!($cmd = &acl::get_ssleay())) {
|
||||
print "<p>",&text('newkey_ecmd', "<tt>$aclconfig{'ssleay'}</tt>",
|
||||
"$gconfig{'webprefix'}/config.cgi?acl"),"<p>\n";
|
||||
&ui_print_footer("", $text{'index_return'});
|
||||
exit;
|
||||
}
|
||||
|
||||
# Create key file
|
||||
$ctemp = &transname();
|
||||
$ktemp = &transname();
|
||||
$outtemp = &transname();
|
||||
$size = $in{'size_def'} ? $default_key_size : $in{'size'};
|
||||
open(CA, "| $cmd req -newkey rsa:$size -x509 -nodes -out $ctemp -keyout $ktemp -days $in{'days'} >$outtemp 2>&1");
|
||||
print CA ($in{'countryName'} || "."),"\n";
|
||||
print CA ($in{'stateOrProvinceName'} || "."),"\n";
|
||||
print CA ($in{'cityName'} || "."),"\n";
|
||||
print CA ($in{'organizationName'} || "."),"\n";
|
||||
print CA ($in{'organizationalUnitName'} || "."),"\n";
|
||||
print CA ($in{'commonName_def'} ? "*" : $in{'commonName'}),"\n";
|
||||
print CA ($in{'emailAddress'} || "."),"\n";
|
||||
close(CA);
|
||||
$rv = $?;
|
||||
$out = `cat $outtemp`;
|
||||
unlink($outtemp);
|
||||
if (!-r $ctemp || !-r $ktemp || $?) {
|
||||
print "<p>$text{'newkey_essl'}<br>\n";
|
||||
print "<pre>$out</pre>\n";
|
||||
&ui_print_footer("", $text{'index_return'});
|
||||
exit;
|
||||
}
|
||||
&lock_file($in{'newfile'});
|
||||
$catout = `cat $ctemp $ktemp 2>&1 >'$in{'newfile'}'`;
|
||||
unlink($ctemp);
|
||||
unlink($ktemp);
|
||||
if ($catout || $?) {
|
||||
print "<p>$text{'newkey_ecat'}<br>\n";
|
||||
print "<pre>$catout</pre>\n";
|
||||
&ui_print_footer("", $text{'index_return'});
|
||||
exit;
|
||||
}
|
||||
chmod(0600, $in{'newfile'});
|
||||
&unlock_file($in{'newfile'});
|
||||
|
||||
print "<p>$text{'newkey_ok'}<br>\n";
|
||||
$key = `cat '$in{'newfile'}'`;
|
||||
print "<pre>$key</pre>";
|
||||
$key = &read_file_contents($in{'newfile'});
|
||||
print "<pre>".&html_escape($key)."</pre>";
|
||||
&ui_print_footer("", $text{'index_return'});
|
||||
|
||||
# Configure webmin to use the new file
|
||||
|
||||
@@ -1239,4 +1239,114 @@ close(BLOCKED);
|
||||
return @rv;
|
||||
}
|
||||
|
||||
# show_ssl_key_form([defhost], [defemail], [deforg])
|
||||
# Returns HTML for inputs to generate a new self-signed cert
|
||||
sub show_ssl_key_form
|
||||
{
|
||||
local ($defhost, $defemail, $deforg) = @_;
|
||||
local $rv;
|
||||
|
||||
$rv .= &ui_table_row($text{'ssl_cn'},
|
||||
&ui_opt_textbox("commonName", $defhost, 30,
|
||||
$text{'ssl_all'}));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_email'},
|
||||
&ui_textbox("emailAddress", $defemail, 30));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_ou'},
|
||||
&ui_textbox("organizationalUnitName", undef, 30));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_o'},
|
||||
&ui_textbox("organizationName", $deforg, 30));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_city'},
|
||||
&ui_textbox("cityName", undef, 30));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_sp'},
|
||||
&ui_textbox("stateOrProvinceName", undef, 15));
|
||||
|
||||
$rv .= &ui_table_row($text{'ca_c'},
|
||||
&ui_textbox("countryName", undef, 2));
|
||||
|
||||
$rv .= &ui_table_row($text{'ssl_size'},
|
||||
&ui_opt_textbox("size", undef, 6,
|
||||
"$text{'default'} ($default_key_size)").
|
||||
" ".$text{'ssl_bits'});
|
||||
|
||||
$rv .= &ui_table_row($text{'ssl_days'},
|
||||
&ui_textbox("days", 1825, 8));
|
||||
|
||||
return $rv;
|
||||
}
|
||||
|
||||
# parse_ssl_key_form(&in, keyfile, [certfile])
|
||||
# Parses the key generation form, and creates new key and cert files.
|
||||
# Returns undef on success or an error message on failure.
|
||||
sub parse_ssl_key_form
|
||||
{
|
||||
local ($in, $keyfile, $certfile) = @_;
|
||||
local %in = %$in;
|
||||
|
||||
# Validate inputs
|
||||
$in{'commonName_def'} || $in{'commonName'} =~ /^[A-Za-z0-9\.\-\*]+$/ ||
|
||||
return $text{'newkey_ecn'};
|
||||
$in{'newfile'} || return $text{'newkey_efile'};
|
||||
$in{'size_def'} || $in{'size'} =~ /^\d+$/ || return $text{'newkey_esize'};
|
||||
$in{'days'} =~ /^\d+$/ || return $text{'newkey_edays'};
|
||||
$in{'countryName'} =~ /^\S\S$/ || return $text{'newkey_ecountry'};
|
||||
|
||||
# Work out SSL command
|
||||
local %aclconfig = &foreign_config('acl');
|
||||
&foreign_require("acl", "acl-lib.pl");
|
||||
local $cmd = &acl::get_ssleay();
|
||||
if (!$cmd) {
|
||||
return &text('newkey_ecmd', "<tt>$aclconfig{'ssleay'}</tt>",
|
||||
"$gconfig{'webprefix'}/config.cgi?acl");
|
||||
}
|
||||
|
||||
# Run openssl and feed it key data
|
||||
local $ctemp = &transname();
|
||||
local $ktemp = &transname();
|
||||
local $outtemp = &transname();
|
||||
local $size = $in{'size_def'} ? $default_key_size : quotemeta($in{'size'});
|
||||
open(CA, "| $cmd req -newkey rsa:$size -x509 -nodes -out $ctemp -keyout $ktemp -days ".quotemeta($in{'days'})." >$outtemp 2>&1");
|
||||
print CA ($in{'countryName'} || "."),"\n";
|
||||
print CA ($in{'stateOrProvinceName'} || "."),"\n";
|
||||
print CA ($in{'cityName'} || "."),"\n";
|
||||
print CA ($in{'organizationName'} || "."),"\n";
|
||||
print CA ($in{'organizationalUnitName'} || "."),"\n";
|
||||
print CA ($in{'commonName_def'} ? "*" : $in{'commonName'}),"\n";
|
||||
print CA ($in{'emailAddress'} || "."),"\n";
|
||||
close(CA);
|
||||
local $rv = $?;
|
||||
local $out = &read_file_contents($outtemp);
|
||||
unlink($outtemp);
|
||||
if (!-r $ctemp || !-r $ktemp || $?) {
|
||||
return $text{'newkey_essl'}."<br>"."<pre>".&html_escape($out)."</pre>";
|
||||
}
|
||||
|
||||
# Write to the final files
|
||||
local $certout = &read_file_contents($ctemp);
|
||||
local $keyout = &read_file_contents($ktemp);
|
||||
unlink($ctemp, $ktemp);
|
||||
|
||||
&open_lock_tempfile(KEYFILE, ">$keyfile");
|
||||
&print_tempfile(KEYFILE, $keyout);
|
||||
if ($certfile) {
|
||||
# Separate files
|
||||
&open_lock_tempfile(CERTFILE, ">$certfile");
|
||||
&print_tempfile(CERTFILE, $certout);
|
||||
&close_tempfile(CERTFILE);
|
||||
&set_ownership_permissions(undef, undef, 0600, $certfile);
|
||||
}
|
||||
else {
|
||||
# Both go in the same file
|
||||
&print_tempfile(KEYFILE, $certout);
|
||||
}
|
||||
&close_tempfile(KEYFILE);
|
||||
&set_ownership_permissions(undef, undef, 0600, $keyfile);
|
||||
|
||||
return undef;
|
||||
}
|
||||
|
||||
1;
|
||||
|
||||
Reference in New Issue
Block a user