index 0e177473eec45cdc43a6cc9c11fab54bd60bffda..7bd0ba2709faed68e4ee3ec4ab50af4cf80f59f6 100755 (executable)
use Net::LDAP;
use Net::LDAP::Util qw(:escape);
use Time::HiRes qw( usleep);
use Net::LDAP;
use Net::LDAP::Util qw(:escape);
use Time::HiRes qw( usleep);
+use DateTime;
my $modules_path = "/usr/lib/gosa-si/modules";
use lib "/usr/lib/gosa-si/modules";
my $modules_path = "/usr/lib/gosa-si/modules";
use lib "/usr/lib/gosa-si/modules";
our $prg= basename($0);
our $global_kernel;
our $prg= basename($0);
our $global_kernel;
-my (%cfg_defaults, $foreground, $verbose, $ping_timeout);
+my ($foreground, $ping_timeout);
my ($bus_activ, $bus, $msg_to_bus, $bus_cipher);
my ($server);
my ($gosa_server, $job_queue_timeout, $job_queue_loop_delay);
my ($messaging_db_loop_delay);
my ($known_modules);
my ($bus_activ, $bus, $msg_to_bus, $bus_cipher);
my ($server);
my ($gosa_server, $job_queue_timeout, $job_queue_loop_delay);
my ($messaging_db_loop_delay);
my ($known_modules);
-my ($pid_file, $procid, $pid, $log_file);
-my ($arp_activ, $arp_fifo);
+my ($procid, $pid);
+my ($arp_fifo);
my ($xml);
my $sources_list;
my $max_clients;
my ($xml);
my $sources_list;
my $max_clients;
"targettag DEFAULT 'none'",
"xmlmessage DEFAULT 'none'",
"module DEFAULT 'none'",
"targettag DEFAULT 'none'",
"xmlmessage DEFAULT 'none'",
"module DEFAULT 'none'",
+ "sessionid DEFAULT '0'",
);
# holds all gosa jobs
);
# holds all gosa jobs
our $known_clients_db;
our $known_clients_tn = "known_clients";
my $known_clients_file_name;
our $known_clients_db;
our $known_clients_tn = "known_clients";
my $known_clients_file_name;
-my @known_clients_col_names = ("hostname", "status", "hostkey", "timestamp", "macaddress", "events");
+my @known_clients_col_names = ("hostname", "status", "hostkey", "timestamp", "macaddress", "events", "keylifetime");
# holds all registered clients at a foreign server
our $foreign_clients_db;
# holds all registered clients at a foreign server
our $foreign_clients_db;
"address" => [\$foreign_server_string, ""],
"domain" => [\$server_domain, ""],
"key" => [\$ServerPackages_key, "none"],
"address" => [\$foreign_server_string, ""],
"domain" => [\$server_domain, ""],
"key" => [\$ServerPackages_key, "none"],
- "key-lifetime" => [\$foreign_servers_register_delay, 600],
+ "key-lifetime" => [\$foreign_servers_register_delay, 120],
}
);
}
);
if(not defined $level) { $level = 1 }
if(defined $log_file){
open(LOG_HANDLE, ">>$log_file");
if(not defined $level) { $level = 1 }
if(defined $log_file){
open(LOG_HANDLE, ">>$log_file");
+ chmod 0600, $log_file;
if(not defined open( LOG_HANDLE, ">>$log_file" )) {
print STDERR "cannot open $log_file: $!";
return }
if(not defined open( LOG_HANDLE, ">>$log_file" )) {
print STDERR "cannot open $log_file: $!";
return }
my ($msg, $address, $encrypt_key, $msg_header, $session_id) = @_ ;
my $error = 0;
my $header;
my ($msg, $address, $encrypt_key, $msg_header, $session_id) = @_ ;
my $error = 0;
my $header;
+ my $timestamp = &get_time();
my $new_status;
my $act_status;
my ($sql_statement, $res);
my $new_status;
my $act_status;
my ($sql_statement, $res);
# known_clients
$sql_statement = "SELECT * FROM known_clients WHERE hostname='$address'";
$res = $known_clients_db->select_dbentry($sql_statement);
# known_clients
$sql_statement = "SELECT * FROM known_clients WHERE hostname='$address'";
$res = $known_clients_db->select_dbentry($sql_statement);
- if( keys(%$res) > 0) {
+ if( keys(%$res) == 1) {
$act_status = $res->{1}->{'status'};
if ($act_status eq "down" && $new_status eq "down") {
$sql_statement = "DELETE FROM known_clients WHERE hostname='$address'";
$res = $known_clients_db->del_dbentry($sql_statement);
daemon_log("$session_id WARNING: failed 2x to send msg to host '$address', delete host from known_clients", 3);
} else {
$act_status = $res->{1}->{'status'};
if ($act_status eq "down" && $new_status eq "down") {
$sql_statement = "DELETE FROM known_clients WHERE hostname='$address'";
$res = $known_clients_db->del_dbentry($sql_statement);
daemon_log("$session_id WARNING: failed 2x to send msg to host '$address', delete host from known_clients", 3);
} else {
- $sql_statement = "UPDATE known_clients SET status='$new_status' WHERE hostname='$address'";
+ $sql_statement = "UPDATE known_clients SET status='$new_status', timestamp='$timestamp' WHERE hostname='$address'";
$res = $known_clients_db->update_dbentry($sql_statement);
if($new_status eq "down"){
daemon_log("$session_id WARNING: set '$address' from status '$act_status' to '$new_status'", 3);
$res = $known_clients_db->update_dbentry($sql_statement);
if($new_status eq "down"){
daemon_log("$session_id WARNING: set '$address' from status '$act_status' to '$new_status'", 3);
# known_server
$sql_statement = "SELECT * FROM $known_server_tn WHERE hostname='$address'";
$res = $known_server_db->select_dbentry($sql_statement);
# known_server
$sql_statement = "SELECT * FROM $known_server_tn WHERE hostname='$address'";
$res = $known_server_db->select_dbentry($sql_statement);
- if( keys(%$res) > 0 ) {
+ if( keys(%$res) == 1) {
$act_status = $res->{1}->{'status'};
if ($act_status eq "down" && $new_status eq "down") {
$sql_statement = "DELETE FROM known_server WHERE hostname='$address'";
$act_status = $res->{1}->{'status'};
if ($act_status eq "down" && $new_status eq "down") {
$sql_statement = "DELETE FROM known_server WHERE hostname='$address'";
daemon_log("$session_id WARNING: failed 2x to send a message to host '$address', delete host from known_server", 3);
}
else {
daemon_log("$session_id WARNING: failed 2x to send a message to host '$address', delete host from known_server", 3);
}
else {
- $sql_statement = "UPDATE known_server SET status='$new_status' WHERE hostname='$address'";
+ $sql_statement = "UPDATE known_server SET status='$new_status', timestamp='$timestamp' WHERE hostname='$address'";
$res = $known_server_db->update_dbentry($sql_statement);
if($new_status eq "down"){
daemon_log("$session_id WARNING: set '$address' from status '$act_status' to '$new_status'", 3);
$res = $known_server_db->update_dbentry($sql_statement);
if($new_status eq "down"){
daemon_log("$session_id WARNING: set '$address' from status '$act_status' to '$new_status'", 3);
}
}
}
}
-sub _start {
- my ($kernel) = $_[KERNEL];
- &trigger_db_loop($kernel);
- $global_kernel = $kernel;
- $kernel->yield('register_at_foreign_servers');
- $kernel->yield('create_fai_server_db', $fai_server_tn );
- $kernel->yield('create_fai_release_db', $fai_release_tn );
- $kernel->sig(USR1 => "sig_handler");
- $kernel->sig(USR2 => "create_packages_list_db");
-}
sub sig_handler {
my ($kernel, $signal) = @_[KERNEL, ARG0] ;
sub sig_handler {
my ($kernel, $signal) = @_[KERNEL, ARG0] ;
sub msg_to_decrypt {
sub msg_to_decrypt {
- my ($session, $heap) = @_[SESSION, HEAP];
+ my ($kernel, $session, $heap) = @_[KERNEL, SESSION, HEAP];
my $session_id = $session->ID;
my ($msg, $msg_hash, $module);
my $error = 0;
my $session_id = $session->ID;
my ($msg, $msg_hash, $module);
my $error = 0;
xmlmessage=>$msg,
timestamp=>&get_time,
module=>$module,
xmlmessage=>$msg,
timestamp=>&get_time,
module=>$module,
+ sessionid=>$session_id,
} );
if ($res != 0) {
# TODO ist das mit $! so ok???
} );
if ($res != 0) {
# TODO ist das mit $! so ok???
sub next_task {
sub next_task {
- my ($session, $heap) = @_[SESSION, HEAP];
- my $task = POE::Wheel::Run->new(
- Program => sub { process_task($session, $heap) },
+ my ($session, $heap, $task) = @_[SESSION, HEAP, ARG0];
+ my $running_task = POE::Wheel::Run->new(
+ Program => sub { process_task($session, $heap, $task) },
StdioFilter => POE::Filter::Reference->new(),
StdoutEvent => "task_result",
StderrEvent => "task_debug",
CloseEvent => "task_done",
);
StdioFilter => POE::Filter::Reference->new(),
StdoutEvent => "task_result",
StderrEvent => "task_debug",
CloseEvent => "task_done",
);
-
- $heap->{task}->{ $task->ID } = $task;
+ $heap->{task}->{ $running_task->ID } = $running_task;
}
sub handle_task_result {
}
sub handle_task_result {
sub process_task {
no strict "refs";
sub process_task {
no strict "refs";
- my ($session, $heap, $input) = @_;
- my $session_id = $session->ID;
+ my ($session, $heap, $task) = @_;
my $error = 0;
my $answer_l;
my ($answer_header, @answer_target_l, $answer_source);
my $client_answer = "";
my $error = 0;
my $answer_l;
my ($answer_header, @answer_target_l, $answer_source);
my $client_answer = "";
- ##################################################
- # fetch first unprocessed message from incoming_db
- # sometimes the program is faster than sqlite, so wait until informations are present at db
- my $id_sql;
- my $id_res;
- my $message_id;
-# TODO : das hier ist sehr sehr unschön
-# to be tested: speed enhancement with usleep 100000???
- while (1) {
- $id_sql = "SELECT min(id) FROM $incoming_tn WHERE (NOT headertag LIKE 'answer%')";
- $id_res = $incoming_db->exec_statement($id_sql);
- $message_id = @{@$id_res[0]}[0];
- if (defined $message_id) { last }
- usleep(100000);
- }
-
- # fetch new message from incoming_db
- my $sql = "SELECT * FROM $incoming_tn WHERE id=$message_id";
- my $res = $incoming_db->exec_statement($sql);
-
# prepare all variables needed to process message
# prepare all variables needed to process message
- my $msg = @{@$res[0]}[4];
- my $incoming_id = @{@$res[0]}[0];
- my $module = @{@$res[0]}[5];
- my $header = @{@$res[0]}[2];
+ my $msg = $task->{'xmlmessage'};
+ my $incoming_id = $task->{'id'};
+ my $module = $task->{'module'};
+ my $header = $task->{'headertag'};
+ my $session_id = $task->{'sessionid'};
my $msg_hash = $xml->XMLin($msg, ForceArray=>1);
my $msg_hash = $xml->XMLin($msg, ForceArray=>1);
-
- # messages which are an answer to a still running process should not be processed here
- if ($header =~ /^answer_(\d+)/) {
- return;
- }
-
- # delete message from db
- my $delete_sql = "DELETE FROM $incoming_tn WHERE id=$incoming_id";
- my $delete_res = $incoming_db->exec_statement($delete_sql);
+ my $source = @{$msg_hash->{'source'}}[0];
+
+ # set timestamp of incoming client uptodate, so client will not
+ # be deleted from known_clients because of expiration
+ my $act_time = &get_time();
+ my $sql = "UPDATE $known_clients_tn SET timestamp='$act_time' WHERE hostname='$source'";
+ my $res = $known_clients_db->exec_statement($sql);
######################
# process incoming msg
if( $error == 0) {
######################
# process incoming msg
if( $error == 0) {
- daemon_log("$session_id INFO: Incoming msg (session_id=$session_id) with header '".@{$msg_hash->{'header'}}[0].
- "' from '".$heap->{'remote_ip'}."'", 5);
+ daemon_log("$session_id INFO: Incoming msg (session_id=$session_id) with header '".@{$msg_hash->{'header'}}[0]."'", 5);
daemon_log("$session_id DEBUG: Processing module ".$module, 7);
$answer_l = &{ $module."::process_incoming_msg" }($msg, $msg_hash, $session_id);
daemon_log("$session_id DEBUG: Processing module ".$module, 7);
$answer_l = &{ $module."::process_incoming_msg" }($msg, $msg_hash, $session_id);
}
}
+sub session_start {
+ my ($kernel) = $_[KERNEL];
+ &trigger_db_loop($kernel);
+ $global_kernel = $kernel;
+ $kernel->yield('register_at_foreign_servers');
+ $kernel->yield('create_fai_server_db', $fai_server_tn );
+ $kernel->yield('create_fai_release_db', $fai_release_tn );
+ $kernel->yield('watch_for_next_tasks');
+ $kernel->sig(USR1 => "sig_handler");
+ $kernel->sig(USR2 => "create_packages_list_db");
+}
sub trigger_db_loop {
my ($kernel) = @_ ;
sub trigger_db_loop {
my ($kernel) = @_ ;
$kernel->delay_set('watch_for_new_messages', $messaging_db_loop_delay);
$kernel->delay_set('watch_for_delivery_messages', $messaging_db_loop_delay);
$kernel->delay_set('watch_for_done_messages', $messaging_db_loop_delay);
$kernel->delay_set('watch_for_new_messages', $messaging_db_loop_delay);
$kernel->delay_set('watch_for_delivery_messages', $messaging_db_loop_delay);
$kernel->delay_set('watch_for_done_messages', $messaging_db_loop_delay);
+ $kernel->delay_set('watch_for_old_known_clients', $job_queue_loop_delay);
}
}
# fetch key to encrypt msg propperly for usr/host
my $sql = "SELECT * FROM $known_clients_tn WHERE (hostname='$receiver_host')";
&daemon_log("0 DEBUG: $sql", 7);
# fetch key to encrypt msg propperly for usr/host
my $sql = "SELECT * FROM $known_clients_tn WHERE (hostname='$receiver_host')";
&daemon_log("0 DEBUG: $sql", 7);
- my $res = $known_clients_db->exec_statement($sql);
+ my $res = $known_clients_db->select_dbentry($sql);
# host is already down
if (not ref(@$res[0]) eq "ARRAY") { next; }
# host is already down
if (not ref(@$res[0]) eq "ARRAY") { next; }
}
}
+sub watch_for_old_known_clients {
+ my ($kernel,$heap) = @_[KERNEL, HEAP];
+
+ my $sql_statement = "SELECT * FROM $known_clients_tn";
+ my $res = $known_clients_db->select_dbentry( $sql_statement );
+
+ my $act_time = int(&get_time());
+
+ while ( my ($hit_num, $hit) = each %$res) {
+ my $expired_timestamp = int($hit->{'timestamp'});
+ $expired_timestamp =~ /(\d{4})(\d\d)(\d\d)(\d\d)(\d\d)(\d\d)/;
+ my $dt = DateTime->new( year => $1,
+ month => $2,
+ day => $3,
+ hour => $4,
+ minute => $5,
+ second => $6,
+ );
+
+ $dt->add( seconds => 2 * int($hit->{'keylifetime'}) );
+ $expired_timestamp = $dt->ymd('').$dt->hms('')."\n";
+ if ($act_time > $expired_timestamp) {
+ my $hostname = $hit->{'hostname'};
+ my $del_sql = "DELETE FROM $known_clients_tn WHERE hostname='$hostname'";
+ my $del_res = $known_clients_db->exec_statement($del_sql);
+
+ &main::daemon_log("0 INFO: timestamp '".$hit->{'timestamp'}."' of client '$hostname' is expired('$expired_timestamp'), client will be deleted from known_clients_db", 5);
+ }
+
+ }
+
+ $kernel->delay_set('watch_for_old_known_clients', $job_queue_loop_delay);
+}
+
+
+sub watch_for_next_tasks {
+ my ($kernel,$heap) = @_[KERNEL, HEAP];
+
+ my $sql = "SELECT * FROM $incoming_tn";
+ my $res = $incoming_db->select_dbentry($sql);
+
+ while ( my ($hit_num, $hit) = each %$res) {
+ my $headertag = $hit->{'headertag'};
+ if ($headertag =~ /^answer_(\d+)/) {
+ # do not start processing, this message is for a still running POE::Wheel
+ next;
+ }
+ my $message_id = $hit->{'id'};
+ $kernel->yield('next_task', $hit);
+
+ my $sql = "DELETE FROM $incoming_tn WHERE id=$message_id";
+ my $res = $incoming_db->exec_statement($sql);
+ }
+
+ $kernel->delay_set('watch_for_next_tasks', 1);
+}
+
+
sub get_ldap_handle {
my ($session_id) = @_;
my $heap;
sub get_ldap_handle {
my ($session_id) = @_;
my $heap;
if ($session_id == 0) {
daemon_log("$session_id DEBUG: get_ldap_handle invoked without a session_id, create a new ldap_handle", 7);
$ldap_handle = Net::LDAP->new( $ldap_uri );
if ($session_id == 0) {
daemon_log("$session_id DEBUG: get_ldap_handle invoked without a session_id, create a new ldap_handle", 7);
$ldap_handle = Net::LDAP->new( $ldap_uri );
- $ldap_handle->bind($ldap_admin_dn, password => $ldap_admin_password);
+ $ldap_handle->bind($ldap_admin_dn, apassword => $ldap_admin_password);
} else {
my $session_reference = $global_kernel->ID_id_to_session($session_id);
} else {
my $session_reference = $global_kernel->ID_id_to_session($session_id);
POE::Component::Server::TCP->new(
POE::Component::Server::TCP->new(
+ Alias => "TCP_SERVER",
Port => $server_port,
ClientInput => sub {
my ($kernel, $input) = @_[KERNEL, ARG0];
push(@tasks, $input);
push(@msgs_to_decrypt, $input);
$kernel->yield("msg_to_decrypt");
Port => $server_port,
ClientInput => sub {
my ($kernel, $input) = @_[KERNEL, ARG0];
push(@tasks, $input);
push(@msgs_to_decrypt, $input);
$kernel->yield("msg_to_decrypt");
- $kernel->yield("next_task");
},
InlineStates => {
},
InlineStates => {
- next_task => \&next_task,
msg_to_decrypt => \&msg_to_decrypt,
msg_to_decrypt => \&msg_to_decrypt,
+ next_task => \&next_task,
task_result => \&handle_task_result,
task_done => \&handle_task_done,
task_debug => \&handle_task_debug,
task_result => \&handle_task_result,
task_done => \&handle_task_done,
task_debug => \&handle_task_debug,
@@ -2815,14 +2856,20 @@ daemon_log("start socket for incoming xml messages at port '$server_port' ", 1);
# create session for repeatedly checking the job queue for jobs
POE::Session->create(
inline_states => {
# create session for repeatedly checking the job queue for jobs
POE::Session->create(
inline_states => {
- _start => \&_start,
+ _start => \&session_start,
register_at_foreign_servers => \®ister_at_foreign_servers,
register_at_foreign_servers => \®ister_at_foreign_servers,
- sig_handler => \&sig_handler,
+ sig_handler => \&sig_handler,
+ next_task => \&next_task,
+ task_result => \&handle_task_result,
+ task_done => \&handle_task_done,
+ task_debug => \&handle_task_debug,
+ watch_for_next_tasks => \&watch_for_next_tasks,
watch_for_new_messages => \&watch_for_new_messages,
watch_for_delivery_messages => \&watch_for_delivery_messages,
watch_for_done_messages => \&watch_for_done_messages,
watch_for_new_jobs => \&watch_for_new_jobs,
watch_for_done_jobs => \&watch_for_done_jobs,
watch_for_new_messages => \&watch_for_new_messages,
watch_for_delivery_messages => \&watch_for_delivery_messages,
watch_for_done_messages => \&watch_for_done_messages,
watch_for_new_jobs => \&watch_for_new_jobs,
watch_for_done_jobs => \&watch_for_done_jobs,
+ watch_for_old_known_clients => \&watch_for_old_known_clients,
create_packages_list_db => \&run_create_packages_list_db,
create_fai_server_db => \&run_create_fai_server_db,
create_fai_release_db => \&run_create_fai_release_db,
create_packages_list_db => \&run_create_packages_list_db,
create_fai_server_db => \&run_create_fai_server_db,
create_fai_release_db => \&run_create_fai_release_db,