summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 29f7b1b)
raw | patch | inline | side by side (parent: 29f7b1b)
author | rettenbe <rettenbe@594d385d-05f5-0310-b6e9-bd551577e9d8> | |
Fri, 8 May 2009 13:05:22 +0000 (13:05 +0000) | ||
committer | rettenbe <rettenbe@594d385d-05f5-0310-b6e9-bd551577e9d8> | |
Fri, 8 May 2009 13:05:22 +0000 (13:05 +0000) |
git-svn-id: https://oss.gonicus.de/repositories/gosa/trunk@13635 594d385d-05f5-0310-b6e9-bd551577e9d8
gosa-si/gosa-si-server | patch | blob | history | |
gosa-si/server/events/server_server_com.pm | patch | blob | history |
diff --git a/gosa-si/gosa-si-server b/gosa-si/gosa-si-server
index 079e867615b5748b0af58371bc30a67e1b6b9160..67d21a7709f944a511cc29d45e2b9ff801c1da23 100755 (executable)
--- a/gosa-si/gosa-si-server
+++ b/gosa-si/gosa-si-server
our $known_server_db;
our $known_server_tn = "known_server";
my $known_server_file_name;
-my @known_server_col_names = ("hostname VARCHAR(255)", "macaddress VARCHAR(17)", "status VARCHAR(255)", "hostkey VARCHAR(255)", "loaded_modules TEXT", "timestamp VARCHAR(14)");
+my @known_server_col_names = ("hostname VARCHAR(255)", "macaddress VARCHAR(17)", "status VARCHAR(255)", "hostkey VARCHAR(255)", "loaded_modules TEXT", "timestamp VARCHAR(14)", "update_time VARCHAR(14)");
# holds all registrated clients
our $known_clients_db;
}
# an error occurred
if(( !$msg ) || ( !$msg_hash ) || ( !$module )){
- # if an incoming msg could not be decrypted (maybe a wrong key), send client a ping. If the client
- # could not understand a msg from its server the client cause a re-registering process
- daemon_log("$session_id WARNING cannot understand incoming msg, send 'ping'-msg to all host with ip '".$heap->{remote_ip}.
- "' to cause a re-registering of the client if necessary", 3);
- my $remote_ip = $heap->{'remote_ip'};
- my $remote_port = $heap->{'remote_port'};
- my $ping_msg = "<xml> <header>gosa_ping</header> <source>$server_address</source><target>$msg_source</target></xml>";
- my ($test_error, $test_error_string) = &send_msg_to_target($ping_msg, "$msg_source", "dummy-key", "gosa_ping", $session_id);
-
+ # If an incoming msg could not be decrypted (maybe a wrong key), decide if msg comes from a client
+ # or a server. In case of a client, send a ping. If the client could not understand a msg from its
+ # server the client cause a re-registering process. In case of a server, decrease update_time in kown_server_db
+ # and trigger a re-registering process for servers
+ if (defined $msg_source && $msg_source =~ /^\d+:$server_port$/)
+ {
+ daemon_log("$session_id WARNING: Cannot understand incoming msg from server '$msg_source'. Cause re-registration process for servers.", 3);
+ my $update_statement = "UPDATE $known_server_tn SET update_time='19700101000000' WHERE hostname='$msg_source'";
+ daemon_log("$session_id DEBUG: $update_statement", 7);
+ my $upadte_res = $known_server_db->exec_statement($update_statement);
+ $kernel->yield("register_at_foreign_servers");
+ }
+ else
+ {
+ daemon_log("$session_id WARNING: Cannot understand incoming msg from client '".$heap->{remote_ip}."'. Send ping-msg to cause a re-registering of the client if necessary", 3);
+ my $remote_ip = $heap->{'remote_ip'};
+ my $remote_port = $heap->{'remote_port'};
+ my $ping_msg = "<xml> <header>gosa_ping</header> <source>$server_address</source><target>$msg_source</target></xml>";
+ my ($test_error, $test_error_string) = &send_msg_to_target($ping_msg, "$msg_source", "dummy-key", "gosa_ping", $session_id);
+ }
$error++;
}
sub register_at_foreign_servers {
my ($kernel) = $_[KERNEL];
- # hole alle bekannten server aus known_server_db
- my $server_sql = "SELECT * FROM $known_server_tn";
- my $server_res = $known_server_db->exec_statement($server_sql);
+ # Set current delay of register_at_foreign_servers to 0
- # no entries in known_server_db
- if (not ref(@$server_res[0]) eq "ARRAY") {
- # TODO
- }
+ # Update status and update-time of all si-server with expired update_time and
+ # block them for race conditional registration processes of other si-servers.
+ my $act_time = &get_time();
+ my $block_statement = "UPDATE $known_server_tn SET status='new_server',update_time='19700101000000' WHERE (CAST(update_time AS UNSIGNED))<$act_time ";
+ &daemon_log("0 DEBUG: $block_statement", 5);
+ my $block_res = $known_server_db->exec_statement($block_statement);
+
+ # Fetch all si-server from db where update_time is younger than act_time
+ my $fetch_statement = "SELECT * FROM $known_server_tn WHERE update_time='19700101000000'";
+ &daemon_log("0 DEBUG: $fetch_statement", 5);
+ my $fetch_res = $known_server_db->exec_statement($fetch_statement);
- # detect already connected clients
+ # Detect already connected clients. Will be added to registration msg later.
my $client_sql = "SELECT * FROM $known_clients_tn";
my $client_res = $known_clients_db->exec_statement($client_sql);
- # send my server details to all other gosa-si-server within the network
- foreach my $hit (@$server_res) {
+ # Send registration messag to all fetched si-server
+ foreach my $hit (@$fetch_res) {
my $hostname = @$hit[0];
my $hostkey = &create_passwd;
- # add already connected clients to registration message
+ # Add already connected clients to registration message
my $myhash = &create_xml_hash('new_server', $server_address, $hostname);
&add_content2xml_hash($myhash, 'key', $hostkey);
map(&add_content2xml_hash($myhash, 'client', @{$_}[0].",".@{$_}[4]), @$client_res);
- # add locally loaded gosa-si modules to registration message
+ # Add locally loaded gosa-si modules to registration message
my $loaded_modules = {};
while (my ($package, $pck_info) = each %$known_modules) {
- next if ((!defined(@$pck_info[2])) || (!(ref (@$pck_info[2]) eq 'HASH')));
- foreach my $act_module (keys(%{@$pck_info[2]})) {
- $loaded_modules->{$act_module} = "";
- }
- }
-
+ next if ((!defined(@$pck_info[2])) || (!(ref (@$pck_info[2]) eq 'HASH')));
+ foreach my $act_module (keys(%{@$pck_info[2]})) {
+ $loaded_modules->{$act_module} = "";
+ }
+ }
map(&add_content2xml_hash($myhash, "loaded_modules", $_), keys(%$loaded_modules));
- # add macaddress to registration message
+ # Add macaddress to registration message
my ($host_ip, $host_port) = split(/:/, $hostname);
my $local_ip = &get_local_ip_for_remote_ip($host_ip);
my $network_interface= &get_interface_for_ip($local_ip);
my $host_mac = &get_mac_for_interface($network_interface);
&add_content2xml_hash($myhash, 'macaddress', $host_mac);
- # build registration message and send it
+ # Build registration message and send it
my $foreign_server_msg = &create_xml_string($myhash);
my $error = &send_msg_to_target($foreign_server_msg, $hostname, $ServerPackages_key, "new_server", 0);
}
-
- $kernel->delay_set("register_at_foreign_servers", $foreign_servers_register_delay);
- return;
+
+
+ # After n sec perform a check of all server registration processes
+ $kernel->delay_set("control_server_registration", 2);
+
+ return;
+}
+
+
+sub control_server_registration {
+ my ($kernel) = $_[KERNEL];
+
+ # Check if all registration processes succeed or not
+ my $select_statement = "SELECT * FROM $known_server_tn WHERE status='new_server'";
+ &daemon_log("0 DEBUG $select_statement", 5);
+ my $select_res = $known_server_db->exec_statement($select_statement);
+
+ # If at least one registration process failed, maybe in case of a race condition
+ # with a foreign registration process
+ if (@$select_res > 0)
+ {
+ # Release block statement 'new_server' to make the server accessible
+ # for foreign registration processes
+ my $update_statement = "UPDATE $known_server_tn SET status='waiting' WHERE status='new_server'";
+ &daemon_log("0 DEBUG: $update_statement", 5);
+ my $update_res = $known_server_db->exec_statement($update_statement);
+
+ # Set a random delay to avoid the registration race condition
+ my $new_foreign_servers_register_delay = int(rand(4))+1;
+ $kernel->delay_set("register_at_foreign_servers", $new_foreign_servers_register_delay);
+ }
+ # If all registration processes succeed
+ else
+ {
+ $kernel->delay_set("register_at_foreign_servers", $foreign_servers_register_delay);
+ }
+
+ return;
}
hostkey=>"none",
loaded_modules => "none",
timestamp=>$cur_timestamp,
+ update_time=>'19700101000000',
} );
}
inline_states => {
_start => \&session_start,
register_at_foreign_servers => \®ister_at_foreign_servers,
+ control_server_registration => \&control_server_registration,
sig_handler => \&sig_handler,
next_task => \&next_task,
task_result => \&handle_task_result,
diff --git a/gosa-si/server/events/server_server_com.pm b/gosa-si/server/events/server_server_com.pm
index 06e87cf2ec4b5391f1bbdd64e7ba267476e83a0b..66eaf77fa869f38099a3b1409c9ca79db7573ea0 100644 (file)
my @clients = exists $msg_hash->{'client'} ? @{$msg_hash->{'client'}} : qw();
my @loaded_modules = exists $msg_hash->{'loaded_modules'} ? @{$msg_hash->{'loaded_modules'}} : qw();
- # sanity check
+ # Ignor message if I'm already within a registration process for server $source
+ my $check_statement = "SELECT * FROM $main::known_server_tn WHERE status='new_server' AND hostname='$source'";
+ &main::daemon_log("$session_id DEBUG $check_statement", 7);
+ my $check_res = $main::known_server_db->select_dbentry($check_statement);
+ my $blocking_process = keys(%$check_res);
+ if ($blocking_process)
+ {
+ return;
+ }
+
+ # Sanity check
if (ref $key eq 'HASH') {
&main::daemon_log("$session_id ERROR: 'new_server'-message from host '$source' contains no key!", 1);
return;
}
- # add foreign server to known_server_db
+ # Add foreign server to known_server_db
+ my $new_update_time = &calc_timestamp(&get_time(), 'plus', $main::foreign_servers_register_delay);
my $func_dic = {table=>$main::known_server_tn,
primkey=>['hostname'],
hostname => $source,
hostkey => $key,
loaded_modules => join(',', @loaded_modules),
timestamp=>&get_time(),
+ update_time=>$new_update_time,
};
my $res = $main::known_server_db->add_dbentry($func_dic);
if (not $res == 0) {
my @clients = exists $msg_hash->{'client'} ? @{$msg_hash->{'client'}} : qw();
my @loaded_modules = exists $msg_hash->{'loaded_modules'} ? @{$msg_hash->{'loaded_modules'}} : qw();
+ my $new_update_time = &calc_timestamp(&get_time(), 'plus', $main::foreign_servers_register_delay);
my $sql = "UPDATE $main::known_server_tn".
- " SET status='$header', hostkey='$key', loaded_modules='".join(",",@loaded_modules)."', macaddress='$mac'".
+ " SET status='$header', hostkey='$key', loaded_modules='".join(",",@loaded_modules)."', macaddress='$mac', update_time='$new_update_time'".
" WHERE hostname='$source'";
my $res = $main::known_server_db->update_dbentry($sql);
push(@sql_list, $del_sql);
my $sql = "INSERT INTO $main::foreign_clients_tn VALUES ("
- ."'".$client_details[0]."'," # hostname
- ."'".$client_details[1]."'," # macaddress
- ."'".$source."'," # regserver
- ."'".&get_time()."')"; # timestamp
+ ."'".$client_details[0]."'," # hostname
+ ."'".$client_details[1]."'," # macaddress
+ ."'".$source."'," # regserver
+ ."'".&get_time()."')"; # timestamp
push(@sql_list, $sql);
}
if (@sql_list) {