Merge branch 'storageareas' of github.com:ConnorTechnology/ZoneMinder into storageareas
commit
2845f891bc
|
@ -529,6 +529,8 @@ sub MoveTo {
|
||||||
my ( $NewPath ) = ( $NewStorage->Path() =~ /^(.*)$/ ); # De-taint
|
my ( $NewPath ) = ( $NewStorage->Path() =~ /^(.*)$/ ); # De-taint
|
||||||
if ( ! $$NewStorage{Id} ) {
|
if ( ! $$NewStorage{Id} ) {
|
||||||
return "New storage does not have an id. Moving will not happen.";
|
return "New storage does not have an id. Moving will not happen.";
|
||||||
|
} elsif ( $$NewStorage{Id} == $$self{StorageId} ) {
|
||||||
|
return "Event is already located at " . $NewPath;
|
||||||
} elsif ( !$NewPath ) {
|
} elsif ( !$NewPath ) {
|
||||||
return "New path ($NewPath) is empty.";
|
return "New path ($NewPath) is empty.";
|
||||||
} elsif ( ! -e $NewPath ) {
|
} elsif ( ! -e $NewPath ) {
|
||||||
|
|
|
@ -161,9 +161,9 @@ sub Sql {
|
||||||
my ( $temp_attr_name ) = $term->{attr} =~ /^Monitor(.+)$/;
|
my ( $temp_attr_name ) = $term->{attr} =~ /^Monitor(.+)$/;
|
||||||
$self->{Sql} .= 'M.'.$temp_attr_name;
|
$self->{Sql} .= 'M.'.$temp_attr_name;
|
||||||
} elsif ( $term->{attr} eq 'ServerId' or $term->{attr} eq 'MonitorServerId' ) {
|
} elsif ( $term->{attr} eq 'ServerId' or $term->{attr} eq 'MonitorServerId' ) {
|
||||||
$self->{Sql} .= 'M.'.$term->{attr};
|
$self->{Sql} .= 'M.ServerId';
|
||||||
} elsif ( $term->{attr} eq 'StorageServerId' ) {
|
} elsif ( $term->{attr} eq 'StorageServerId' ) {
|
||||||
$self->{Sql} .= 'S.'.$term->{attr};
|
$self->{Sql} .= 'S.ServerId';
|
||||||
} elsif ( $term->{attr} eq 'FilterServerId' ) {
|
} elsif ( $term->{attr} eq 'FilterServerId' ) {
|
||||||
$self->{Sql} .= $Config{ZM_SERVER_ID};
|
$self->{Sql} .= $Config{ZM_SERVER_ID};
|
||||||
# StartTime options
|
# StartTime options
|
||||||
|
|
|
@ -158,6 +158,7 @@ sub new {
|
||||||
( $this->{fileName} = $0 ) =~ s|^.*/||;
|
( $this->{fileName} = $0 ) =~ s|^.*/||;
|
||||||
$this->{logPath} = $Config{ZM_PATH_LOGS};
|
$this->{logPath} = $Config{ZM_PATH_LOGS};
|
||||||
$this->{logFile} = $this->{logPath}.'/'.$this->{id}.'.log';
|
$this->{logFile} = $this->{logPath}.'/'.$this->{id}.'.log';
|
||||||
|
($this->{logFile}) = $this->{logFile} =~ /^([\w\.\/]+)$/;
|
||||||
|
|
||||||
$this->{trace} = 0;
|
$this->{trace} = 0;
|
||||||
|
|
||||||
|
@ -207,6 +208,7 @@ sub initialise( @ ) {
|
||||||
if ( my $logFile = $this->getTargettedEnv('LOG_FILE') ) {
|
if ( my $logFile = $this->getTargettedEnv('LOG_FILE') ) {
|
||||||
$tempLogFile = $logFile;
|
$tempLogFile = $logFile;
|
||||||
}
|
}
|
||||||
|
($tempLogFile) = $tempLogFile =~ /^([\w\.\/]+)$/;
|
||||||
|
|
||||||
my $tempLevel = INFO;
|
my $tempLevel = INFO;
|
||||||
my $tempTermLevel = $this->{termLevel};
|
my $tempTermLevel = $this->{termLevel};
|
||||||
|
@ -582,24 +584,29 @@ sub logPrint {
|
||||||
}
|
}
|
||||||
print($LOGFILE $message) if $level <= $this->{fileLevel};
|
print($LOGFILE $message) if $level <= $this->{fileLevel};
|
||||||
if ( $level <= $this->{databaseLevel} ) {
|
if ( $level <= $this->{databaseLevel} ) {
|
||||||
my $sql = 'INSERT INTO Logs ( TimeKey, Component, Pid, Level, Code, Message, File, Line ) VALUES ( ?, ?, ?, ?, ?, ?, ?, NULL )';
|
if ( ( $this->{dbh} and $this->{dbh}->ping() ) or ( $this->{dbh} = zmDbConnect() ) ) {
|
||||||
$this->{sth} = $this->{dbh}->prepare_cached($sql);
|
|
||||||
if ( !$this->{sth} ) {
|
my $sql = 'INSERT INTO Logs ( TimeKey, Component, Pid, Level, Code, Message, File, Line ) VALUES ( ?, ?, ?, ?, ?, ?, ?, NULL )';
|
||||||
$this->{databaseLevel} = NOLOG;
|
$this->{sth} = $this->{dbh}->prepare_cached($sql);
|
||||||
Error("Can't prepare log entry '$sql': ".$this->{dbh}->errstr());
|
if ( !$this->{sth} ) {
|
||||||
} else {
|
|
||||||
my $res = $this->{sth}->execute($seconds+($microseconds/1000000.0)
|
|
||||||
, $this->{id}
|
|
||||||
, $$
|
|
||||||
, $level
|
|
||||||
, $code
|
|
||||||
, $string
|
|
||||||
, $this->{fileName}
|
|
||||||
);
|
|
||||||
if ( !$res ) {
|
|
||||||
$this->{databaseLevel} = NOLOG;
|
$this->{databaseLevel} = NOLOG;
|
||||||
Error("Can't execute log entry '$sql': ".$this->{sth}->errstr());
|
Error("Can't prepare log entry '$sql': ".$this->{dbh}->errstr());
|
||||||
|
} else {
|
||||||
|
my $res = $this->{sth}->execute($seconds+($microseconds/1000000.0)
|
||||||
|
, $this->{id}
|
||||||
|
, $$
|
||||||
|
, $level
|
||||||
|
, $code
|
||||||
|
, $string
|
||||||
|
, $this->{fileName}
|
||||||
|
);
|
||||||
|
if ( !$res ) {
|
||||||
|
$this->{databaseLevel} = NOLOG;
|
||||||
|
Error("Can't execute log entry '$sql': ".$this->{dbh}->errstr());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
print(STDERR "Can't log to database: ");
|
||||||
}
|
}
|
||||||
} # end if doing db logging
|
} # end if doing db logging
|
||||||
print(STDERR $message) if $level <= $this->{termLevel};
|
print(STDERR $message) if $level <= $this->{termLevel};
|
||||||
|
|
|
@ -242,6 +242,7 @@ use constant KILL_DELAY => 60; # seconds to wait between sending TERM and sendin
|
||||||
our %cmd_hash;
|
our %cmd_hash;
|
||||||
our %pid_hash;
|
our %pid_hash;
|
||||||
our %terminating_processes;
|
our %terminating_processes;
|
||||||
|
our $zm_terminate = 0;
|
||||||
|
|
||||||
sub run {
|
sub run {
|
||||||
my $fd = 0;
|
my $fd = 0;
|
||||||
|
@ -276,9 +277,9 @@ sub run {
|
||||||
listen(SERVER, SOMAXCONN) or Fatal("Can't listen: $!");
|
listen(SERVER, SOMAXCONN) or Fatal("Can't listen: $!");
|
||||||
|
|
||||||
$SIG{CHLD} = \&reaper;
|
$SIG{CHLD} = \&reaper;
|
||||||
$SIG{INT} = \&shutdownAll;
|
$SIG{INT} = \&shutdown_sig_handler;
|
||||||
$SIG{TERM} = \&shutdownAll;
|
$SIG{TERM} = \&shutdown_sig_handler;
|
||||||
$SIG{ABRT} = \&shutdownAll;
|
$SIG{ABRT} = \&shutdown_sig_handler;
|
||||||
$SIG{HUP} = \&logrot;
|
$SIG{HUP} = \&logrot;
|
||||||
|
|
||||||
my $rin = '';
|
my $rin = '';
|
||||||
|
@ -295,12 +296,18 @@ sub run {
|
||||||
dPrint(ZoneMinder::Logger::INFO, 'Loading Server record have ' . $$Server{Name});
|
dPrint(ZoneMinder::Logger::INFO, 'Loading Server record have ' . $$Server{Name});
|
||||||
}
|
}
|
||||||
|
|
||||||
while( 1 ) {
|
while( !$zm_terminate ) {
|
||||||
|
|
||||||
if ( $Config{ZM_SERVER_ID} ) {
|
if ( $Config{ZM_SERVER_ID} ) {
|
||||||
if ( ! ( $secs_count % 60 ) ) {
|
if ( ! ( $secs_count % 60 ) ) {
|
||||||
$dbh = zmDbConnect() if ! $dbh->ping();
|
Debug("Connecting");
|
||||||
|
while ( !$zm_terminate and ! ($dbh and $dbh->ping()) ) {
|
||||||
|
Warning("Not connected to db. Reconnecting");
|
||||||
|
$dbh = zmDbConnect();
|
||||||
|
Debug("Conneted? : $dbh");
|
||||||
|
}
|
||||||
my @cpuload = CpuLoad();
|
my @cpuload = CpuLoad();
|
||||||
|
Debug("UPdating Server record @cpuload");
|
||||||
if ( ! defined $dbh->do(q{UPDATE Servers SET Status=?,CpuLoad=?,TotalMem=?,FreeMem=?,TotalSwap=?,FreeSwap=? WHERE Id=?}, undef,
|
if ( ! defined $dbh->do(q{UPDATE Servers SET Status=?,CpuLoad=?,TotalMem=?,FreeMem=?,TotalSwap=?,FreeSwap=? WHERE Id=?}, undef,
|
||||||
'Running', $cpuload[0], &totalmem, &freemem, &totalswap, &freeswap, $Config{ZM_SERVER_ID} ) ) {
|
'Running', $cpuload[0], &totalmem, &freemem, &totalswap, &freeswap, $Config{ZM_SERVER_ID} ) ) {
|
||||||
Error("Failed Updating status of Server record for Id=$Config{ZM_SERVER_ID}".$dbh->errstr());
|
Error("Failed Updating status of Server record for Id=$Config{ZM_SERVER_ID}".$dbh->errstr());
|
||||||
|
@ -308,7 +315,9 @@ sub run {
|
||||||
}
|
}
|
||||||
$secs_count += 1;
|
$secs_count += 1;
|
||||||
}
|
}
|
||||||
|
Debug("Before select");
|
||||||
my $nfound = select(my $rout = $rin, undef, undef, $timeout);
|
my $nfound = select(my $rout = $rin, undef, undef, $timeout);
|
||||||
|
Debug("Aftere select $nfound");
|
||||||
if ( $nfound > 0 ) {
|
if ( $nfound > 0 ) {
|
||||||
if ( vec($rout, fileno(SERVER), 1) ) {
|
if ( vec($rout, fileno(SERVER), 1) ) {
|
||||||
my $paddr = accept(CLIENT, SERVER);
|
my $paddr = accept(CLIENT, SERVER);
|
||||||
|
@ -330,7 +339,8 @@ sub run {
|
||||||
# Do nothing, this is all we're here for
|
# Do nothing, this is all we're here for
|
||||||
dPrint(ZoneMinder::Logger::WARNING, "Already running, ignoring command '$command'\n");
|
dPrint(ZoneMinder::Logger::WARNING, "Already running, ignoring command '$command'\n");
|
||||||
} elsif ( $command eq 'shutdown' ) {
|
} elsif ( $command eq 'shutdown' ) {
|
||||||
shutdownAll();
|
# Breka out of while loop
|
||||||
|
last;
|
||||||
} elsif ( $command eq 'check' ) {
|
} elsif ( $command eq 'check' ) {
|
||||||
check($daemon, @args);
|
check($daemon, @args);
|
||||||
} elsif ( $command eq 'status' ) {
|
} elsif ( $command eq 'status' ) {
|
||||||
|
@ -362,7 +372,9 @@ sub run {
|
||||||
#print( "Select timed out\n" );
|
#print( "Select timed out\n" );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Debug("restartPending");
|
||||||
restartPending();
|
restartPending();
|
||||||
|
Debug("check_for_processes_to_kill");
|
||||||
check_for_processes_to_kill();
|
check_for_processes_to_kill();
|
||||||
|
|
||||||
} # end while
|
} # end while
|
||||||
|
@ -377,9 +389,7 @@ sub run {
|
||||||
Error("Failed Updating status of Server record for Id=$Config{ZM_SERVER_ID}".$dbh->errstr());
|
Error("Failed Updating status of Server record for Id=$Config{ZM_SERVER_ID}".$dbh->errstr());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
unlink(main::SOCK_FILE) or Error('Unable to unlink ' . main::SOCK_FILE .". Error message was: $!") if ( -e main::SOCK_FILE );
|
shutdownAll();
|
||||||
unlink(ZM_PID) or Error('Unable to unlink ' . ZM_PID .". Error message was: $!") if ( -e ZM_PID );
|
|
||||||
exit();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
sub cPrint {
|
sub cPrint {
|
||||||
|
@ -426,10 +436,12 @@ sub start {
|
||||||
}
|
}
|
||||||
|
|
||||||
my $sigset = POSIX::SigSet->new;
|
my $sigset = POSIX::SigSet->new;
|
||||||
my $blockset = POSIX::SigSet->new( SIGCHLD );
|
my $blockset = POSIX::SigSet->new(SIGCHLD);
|
||||||
|
Debug("Blocking SIGCHLD");
|
||||||
sigprocmask(SIG_BLOCK, $blockset, $sigset) or Fatal("Can't block SIGCHLD: $!");
|
sigprocmask(SIG_BLOCK, $blockset, $sigset) or Fatal("Can't block SIGCHLD: $!");
|
||||||
|
Debug("forking");
|
||||||
if ( my $cpid = fork() ) {
|
if ( my $cpid = fork() ) {
|
||||||
logReinit();
|
#logReinit();
|
||||||
|
|
||||||
$process->{pid} = $cpid;
|
$process->{pid} = $cpid;
|
||||||
$process->{started} = time();
|
$process->{started} = time();
|
||||||
|
@ -442,6 +454,7 @@ sub start {
|
||||||
|
|
||||||
$cmd_hash{$process->{command}} = $pid_hash{$cpid} = $process;
|
$cmd_hash{$process->{command}} = $pid_hash{$cpid} = $process;
|
||||||
sigprocmask(SIG_SETMASK, $sigset) or Fatal("Can't restore SIGCHLD: $!");
|
sigprocmask(SIG_SETMASK, $sigset) or Fatal("Can't restore SIGCHLD: $!");
|
||||||
|
Debug("unblocko child");
|
||||||
} elsif ( defined($cpid) ) {
|
} elsif ( defined($cpid) ) {
|
||||||
# Force reconnection to the db.
|
# Force reconnection to the db.
|
||||||
$dbh = zmDbConnect(1);
|
$dbh = zmDbConnect(1);
|
||||||
|
@ -527,16 +540,18 @@ sub check_for_processes_to_kill {
|
||||||
my $sigset = POSIX::SigSet->new;
|
my $sigset = POSIX::SigSet->new;
|
||||||
my $blockset = POSIX::SigSet->new(SIGCHLD);
|
my $blockset = POSIX::SigSet->new(SIGCHLD);
|
||||||
sigprocmask(SIG_BLOCK, $blockset, $sigset) or die "dying at block...\n";
|
sigprocmask(SIG_BLOCK, $blockset, $sigset) or die "dying at block...\n";
|
||||||
foreach my $command ( %terminating_processes ) {
|
foreach my $command ( keys %terminating_processes ) {
|
||||||
my $process = $cmd_hash{$command};
|
my $process = $cmd_hash{$command};
|
||||||
Debug("Have process $command at pid $$process{pid} $$process{term_sent_at}");
|
my $now = time;
|
||||||
if ( $$process{term_sent_at} and ( $$process{term_sent_at} - time > KILL_DELAY ) ) {
|
Debug("Have process $command at pid $$process{pid} $$process{term_sent_at} - $now = " . ( $$process{term_sent_at} - $now ) );
|
||||||
|
if ( $$process{term_sent_at} and ( $$process{term_sent_at} - $now > KILL_DELAY ) ) {
|
||||||
dPrint(ZoneMinder::Logger::WARNING, "'$$process{command}' has not stopped at "
|
dPrint(ZoneMinder::Logger::WARNING, "'$$process{command}' has not stopped at "
|
||||||
.strftime('%y/%m/%d %H:%M:%S', localtime())
|
.strftime('%y/%m/%d %H:%M:%S', localtime())
|
||||||
.' after ' . KILL_DELAY . ' seconds.'
|
.' after ' . KILL_DELAY . ' seconds.'
|
||||||
." Sending KILL to pid $$process{pid}\n"
|
." Sending KILL to pid $$process{pid}\n"
|
||||||
);
|
);
|
||||||
kill('KILL', $$process{pid});
|
kill('KILL', $$process{pid});
|
||||||
|
delete $terminating_processes{$command};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
sigprocmask(SIG_UNBLOCK, $blockset) or die "dying at unblock...\n";
|
sigprocmask(SIG_UNBLOCK, $blockset) or die "dying at unblock...\n";
|
||||||
|
@ -595,8 +610,14 @@ sub logrot {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sub shutdown_sig_handler {
|
||||||
|
$zm_terminate = 1;
|
||||||
|
}
|
||||||
|
|
||||||
sub reaper {
|
sub reaper {
|
||||||
my $saved_status = $!;
|
my $saved_status = $!;
|
||||||
|
|
||||||
|
# Wait for a child to terminate
|
||||||
while ( (my $cpid = waitpid(-1, WNOHANG)) > 0 ) {
|
while ( (my $cpid = waitpid(-1, WNOHANG)) > 0 ) {
|
||||||
my $status = $?;
|
my $status = $?;
|
||||||
|
|
||||||
|
@ -620,8 +641,8 @@ sub reaper {
|
||||||
|
|
||||||
my $out_str = "'$process->{command}' ";
|
my $out_str = "'$process->{command}' ";
|
||||||
if ( $exit_signal ) {
|
if ( $exit_signal ) {
|
||||||
|
# 15 == TERM, 14 == ALARM
|
||||||
if ( $exit_signal == 15 || $exit_signal == 14 ) {
|
if ( $exit_signal == 15 || $exit_signal == 14 ) {
|
||||||
# TERM or ALRM
|
|
||||||
$out_str .= 'exited';
|
$out_str .= 'exited';
|
||||||
} else {
|
} else {
|
||||||
$out_str .= 'crashed';
|
$out_str .= 'crashed';
|
||||||
|
@ -659,22 +680,26 @@ sub reaper {
|
||||||
$process->{delay} = $Config{ZM_MAX_RESTART_DELAY};
|
$process->{delay} = $Config{ZM_MAX_RESTART_DELAY};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Debug("Delay for $$process{command} is now $$process{delay}");
|
||||||
} else {
|
} else {
|
||||||
delete $cmd_hash{$$process{command}};
|
delete $cmd_hash{$$process{command}};
|
||||||
}
|
}
|
||||||
}
|
} # end while waitpid
|
||||||
$SIG{CHLD} = \&reaper;
|
$SIG{CHLD} = \&reaper;
|
||||||
$! = $saved_status;
|
$! = $saved_status;
|
||||||
|
Debug("Leaving reaper");
|
||||||
}
|
}
|
||||||
|
|
||||||
sub restartPending {
|
sub restartPending {
|
||||||
# Restart any pending processes
|
# Restart any pending processes, we list them first because cmd_hash may change in foreach
|
||||||
foreach my $process ( values( %cmd_hash ) ) {
|
my @processes = values %cmd_hash;
|
||||||
|
foreach my $process ( @processes ) {
|
||||||
if ( $process->{pending} && $process->{pending} <= time() ) {
|
if ( $process->{pending} && $process->{pending} <= time() ) {
|
||||||
dPrint(ZoneMinder::Logger::INFO, "Starting pending process, $process->{command}\n");
|
dPrint(ZoneMinder::Logger::INFO, "Starting pending process, $process->{command}\n");
|
||||||
start($process->{daemon}, @{$process->{args}});
|
start($process->{daemon}, @{$process->{args}});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
dPrint(ZoneMinder::Logger::INFO, "done restartPending");
|
||||||
}
|
}
|
||||||
|
|
||||||
sub shutdownAll {
|
sub shutdownAll {
|
||||||
|
@ -683,9 +708,14 @@ sub shutdownAll {
|
||||||
next if ! $pid_hash{$pid};
|
next if ! $pid_hash{$pid};
|
||||||
send_stop(1, $pid_hash{$pid});
|
send_stop(1, $pid_hash{$pid});
|
||||||
}
|
}
|
||||||
while ( %terminating_processes ) {
|
my $count= KILL_DELAY;
|
||||||
|
while ( (keys %terminating_processes) and $count) {
|
||||||
check_for_processes_to_kill();
|
check_for_processes_to_kill();
|
||||||
sleep(1) if %terminating_processes;
|
if ( %terminating_processes ) {
|
||||||
|
Debug("Still " . %terminating_processes . ' to die. count is: ' . $count . ' sleeping');
|
||||||
|
sleep(1);
|
||||||
|
$count --;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
dPrint(ZoneMinder::Logger::INFO, "Server shutdown at "
|
dPrint(ZoneMinder::Logger::INFO, "Server shutdown at "
|
||||||
.strftime('%y/%m/%d %H:%M:%S', localtime())
|
.strftime('%y/%m/%d %H:%M:%S', localtime())
|
||||||
|
|
|
@ -94,7 +94,7 @@ use constant EVENT_PATH => ($Config{ZM_DIR_EVENTS}=~m|/|)
|
||||||
: ($Config{ZM_PATH_WEB}.'/'.$Config{ZM_DIR_EVENTS})
|
: ($Config{ZM_PATH_WEB}.'/'.$Config{ZM_DIR_EVENTS})
|
||||||
;
|
;
|
||||||
|
|
||||||
logInit();
|
logInit($filter_id?(id=>'zmfilter_'.$filter_id.'.log'):());
|
||||||
sub HupHandler {
|
sub HupHandler {
|
||||||
Info("Received HUP, reloading");
|
Info("Received HUP, reloading");
|
||||||
&ZoneMinder::Logger::logHupHandler();
|
&ZoneMinder::Logger::logHupHandler();
|
||||||
|
|
|
@ -259,7 +259,7 @@ Event::~Event() {
|
||||||
"UPDATE Events SET Name='%s %" PRIu64 "', EndTime = from_unixtime( %ld ), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d, DefaultVideo = '%s' WHERE Id = %" PRIu64,
|
"UPDATE Events SET Name='%s %" PRIu64 "', EndTime = from_unixtime( %ld ), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d, DefaultVideo = '%s' WHERE Id = %" PRIu64,
|
||||||
monitor->EventPrefix(), id, end_time.tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec, frames, alarm_frames, tot_score, (int)(alarm_frames?(tot_score/alarm_frames):0), max_score, video_name, id );
|
monitor->EventPrefix(), id, end_time.tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec, frames, alarm_frames, tot_score, (int)(alarm_frames?(tot_score/alarm_frames):0), max_score, video_name, id );
|
||||||
db_mutex.lock();
|
db_mutex.lock();
|
||||||
while ( mysql_query(&dbconn, sql) ) {
|
while ( mysql_query(&dbconn, sql) && !zm_terminate ) {
|
||||||
Error("Can't update event: %s reason: %s", sql, mysql_error(&dbconn));
|
Error("Can't update event: %s reason: %s", sql, mysql_error(&dbconn));
|
||||||
db_mutex.unlock();
|
db_mutex.unlock();
|
||||||
sleep(1);
|
sleep(1);
|
||||||
|
@ -424,16 +424,16 @@ void Event::updateNotes( const StringSetMap &newNoteSetMap ) {
|
||||||
#else
|
#else
|
||||||
static char escapedNotes[ZM_SQL_MED_BUFSIZ];
|
static char escapedNotes[ZM_SQL_MED_BUFSIZ];
|
||||||
|
|
||||||
mysql_real_escape_string( &dbconn, escapedNotes, notes.c_str(), notes.length() );
|
mysql_real_escape_string(&dbconn, escapedNotes, notes.c_str(), notes.length());
|
||||||
|
|
||||||
snprintf( sql, sizeof(sql), "UPDATE Events SET Notes = '%s' WHERE Id = %" PRIu64, escapedNotes, id );
|
snprintf(sql, sizeof(sql), "UPDATE Events SET Notes = '%s' WHERE Id = %" PRIu64, escapedNotes, id);
|
||||||
db_mutex.lock();
|
db_mutex.lock();
|
||||||
if ( mysql_query( &dbconn, sql ) ) {
|
if ( mysql_query(&dbconn, sql) ) {
|
||||||
Error( "Can't insert event: %s", mysql_error( &dbconn ) );
|
Error("Can't insert event: %s", mysql_error(&dbconn));
|
||||||
}
|
}
|
||||||
db_mutex.unlock();
|
db_mutex.unlock();
|
||||||
#endif
|
#endif
|
||||||
}
|
} // end if update
|
||||||
}
|
}
|
||||||
|
|
||||||
void Event::AddFrames( int n_frames, Image **images, struct timeval **timestamps ) {
|
void Event::AddFrames( int n_frames, Image **images, struct timeval **timestamps ) {
|
||||||
|
@ -487,7 +487,7 @@ void Event::AddFramesInternal( int n_frames, int start_frame, Image **images, st
|
||||||
snprintf( sql+sql_len, sizeof(sql)-sql_len, "( %" PRIu64 ", %d, from_unixtime(%ld), %s%ld.%02ld ), ", id, frames, timestamps[i]->tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec );
|
snprintf( sql+sql_len, sizeof(sql)-sql_len, "( %" PRIu64 ", %d, from_unixtime(%ld), %s%ld.%02ld ), ", id, frames, timestamps[i]->tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec );
|
||||||
|
|
||||||
frameCount++;
|
frameCount++;
|
||||||
}
|
} // end foreach frame
|
||||||
|
|
||||||
if ( frameCount ) {
|
if ( frameCount ) {
|
||||||
Debug( 1, "Adding %d/%d frames to DB", frameCount, n_frames );
|
Debug( 1, "Adding %d/%d frames to DB", frameCount, n_frames );
|
||||||
|
@ -545,7 +545,10 @@ Debug(3, "Writing video");
|
||||||
|
|
||||||
Debug( 1, "Adding frame %d of type \"%s\" to DB", frames, Event::frame_type_names[frame_type] );
|
Debug( 1, "Adding frame %d of type \"%s\" to DB", frames, Event::frame_type_names[frame_type] );
|
||||||
static char sql[ZM_SQL_MED_BUFSIZ];
|
static char sql[ZM_SQL_MED_BUFSIZ];
|
||||||
snprintf(sql, sizeof(sql), "INSERT INTO Frames ( EventId, FrameId, Type, TimeStamp, Delta, Score ) values ( %" PRIu64 ", %d, '%s', from_unixtime( %ld ), %s%ld.%02ld, %d )", id, frames, frame_type_names[frame_type], timestamp.tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec, score);
|
snprintf(sql, sizeof(sql),
|
||||||
|
"INSERT INTO Frames ( EventId, FrameId, Type, TimeStamp, Delta, Score )"
|
||||||
|
" VALUES ( %" PRIu64 ", %d, '%s', from_unixtime( %ld ), %s%ld.%02ld, %d )",
|
||||||
|
id, frames, frame_type_names[frame_type], timestamp.tv_sec, delta_time.positive?"":"-", delta_time.sec, delta_time.fsec, score);
|
||||||
db_mutex.lock();
|
db_mutex.lock();
|
||||||
if ( mysql_query(&dbconn, sql) ) {
|
if ( mysql_query(&dbconn, sql) ) {
|
||||||
Error("Can't insert frame: %s", mysql_error(&dbconn));
|
Error("Can't insert frame: %s", mysql_error(&dbconn));
|
||||||
|
@ -558,7 +561,7 @@ Debug(3, "Writing video");
|
||||||
|
|
||||||
// We are writing a Bulk frame
|
// We are writing a Bulk frame
|
||||||
if ( frame_type == BULK ) {
|
if ( frame_type == BULK ) {
|
||||||
snprintf( sql, sizeof(sql),
|
snprintf(sql, sizeof(sql),
|
||||||
"UPDATE Events SET Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d where Id = %" PRIu64,
|
"UPDATE Events SET Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d where Id = %" PRIu64,
|
||||||
( delta_time.positive?"":"-" ),
|
( delta_time.positive?"":"-" ),
|
||||||
delta_time.sec, delta_time.fsec,
|
delta_time.sec, delta_time.fsec,
|
||||||
|
@ -570,7 +573,7 @@ Debug(3, "Writing video");
|
||||||
id
|
id
|
||||||
);
|
);
|
||||||
db_mutex.lock();
|
db_mutex.lock();
|
||||||
while ( mysql_query(&dbconn, sql) ) {
|
while ( mysql_query(&dbconn, sql) && !zm_terminate ) {
|
||||||
Error("Can't update event: %s", mysql_error(&dbconn));
|
Error("Can't update event: %s", mysql_error(&dbconn));
|
||||||
db_mutex.unlock();
|
db_mutex.unlock();
|
||||||
sleep(1);
|
sleep(1);
|
||||||
|
|
|
@ -543,7 +543,7 @@ void Logger::logPrint( bool hex, const char * const filepath, const int line, co
|
||||||
mysql_real_escape_string( &dbconn, escapedString, syslogStart, strlen(syslogStart) );
|
mysql_real_escape_string( &dbconn, escapedString, syslogStart, strlen(syslogStart) );
|
||||||
|
|
||||||
snprintf( sql, sizeof(sql), "insert into Logs ( TimeKey, Component, ServerId, Pid, Level, Code, Message, File, Line ) values ( %ld.%06ld, '%s', %d, %d, %d, '%s', '%s', '%s', %d )", timeVal.tv_sec, timeVal.tv_usec, mId.c_str(), staticConfig.SERVER_ID, tid, level, classString, escapedString, file, line );
|
snprintf( sql, sizeof(sql), "insert into Logs ( TimeKey, Component, ServerId, Pid, Level, Code, Message, File, Line ) values ( %ld.%06ld, '%s', %d, %d, %d, '%s', '%s', '%s', %d )", timeVal.tv_sec, timeVal.tv_usec, mId.c_str(), staticConfig.SERVER_ID, tid, level, classString, escapedString, file, line );
|
||||||
if (mysql_query(&dbconn, sql)) {
|
if ( mysql_query(&dbconn, sql) ) {
|
||||||
Level tempDatabaseLevel = mDatabaseLevel;
|
Level tempDatabaseLevel = mDatabaseLevel;
|
||||||
databaseLevel(NOLOG);
|
databaseLevel(NOLOG);
|
||||||
Error("Can't insert log entry: sql(%s) error(%s)", sql, mysql_error(&dbconn));
|
Error("Can't insert log entry: sql(%s) error(%s)", sql, mysql_error(&dbconn));
|
||||||
|
|
|
@ -1246,9 +1246,9 @@ bool Monitor::Analyse() {
|
||||||
Info("%s: %d - Analysing at %.2f fps", name, image_count, new_fps);
|
Info("%s: %d - Analysing at %.2f fps", name, image_count, new_fps);
|
||||||
if ( fps != new_fps ) {
|
if ( fps != new_fps ) {
|
||||||
fps = new_fps;
|
fps = new_fps;
|
||||||
|
db_mutex.lock();
|
||||||
static char sql[ZM_SQL_SML_BUFSIZ];
|
static char sql[ZM_SQL_SML_BUFSIZ];
|
||||||
snprintf(sql, sizeof(sql), "INSERT INTO Monitor_Status (MonitorId,AnalysisFPS) VALUES (%d, %.2lf) ON DUPLICATE KEY UPDATE AnalysisFPS = %.2lf", id, fps, fps);
|
snprintf(sql, sizeof(sql), "INSERT INTO Monitor_Status (MonitorId,AnalysisFPS) VALUES (%d, %.2lf) ON DUPLICATE KEY UPDATE AnalysisFPS = %.2lf", id, fps, fps);
|
||||||
db_mutex.lock();
|
|
||||||
if ( mysql_query(&dbconn, sql) ) {
|
if ( mysql_query(&dbconn, sql) ) {
|
||||||
Error("Can't run query: %s", mysql_error(&dbconn));
|
Error("Can't run query: %s", mysql_error(&dbconn));
|
||||||
}
|
}
|
||||||
|
|
|
@ -1 +1 @@
|
||||||
Subproject commit c3976f1478c681b0bbc132ec3a3e82c3984eeed5
|
Subproject commit 0bd63fb464957080ead342db58ca9e01532cf1ef
|
|
@ -451,6 +451,11 @@ class Event {
|
||||||
$values[] = $this->{'Id'};
|
$values[] = $this->{'Id'};
|
||||||
dbQuery( $sql, $values );
|
dbQuery( $sql, $values );
|
||||||
}
|
}
|
||||||
|
public function link_to($text=null) {
|
||||||
|
if ( !$text )
|
||||||
|
$text = $this->{'Id'};
|
||||||
|
return '<a href="?view=event&eid='. $this->{'Id'}.'">'.$text.'</a>';
|
||||||
|
}
|
||||||
|
|
||||||
} # end class
|
} # end class
|
||||||
|
|
||||||
|
|
|
@ -102,6 +102,7 @@ while( $event = $result->fetch(PDO::FETCH_ASSOC) ) {
|
||||||
|
|
||||||
if ( count($EventsByMonitor[$event['MonitorId']]['Events']) ) {
|
if ( count($EventsByMonitor[$event['MonitorId']]['Events']) ) {
|
||||||
$last_event = end($EventsByMonitor[$event['MonitorId']]['Events']);
|
$last_event = end($EventsByMonitor[$event['MonitorId']]['Events']);
|
||||||
|
#Logger::Debug(print_r($last_event,true));
|
||||||
$gap = $last_event->EndTimeSecs() - $event['StartTimeSecs'];
|
$gap = $last_event->EndTimeSecs() - $event['StartTimeSecs'];
|
||||||
|
|
||||||
if ( $gap < $EventsByMonitor[$event['MonitorId']]['MinGap'] )
|
if ( $gap < $EventsByMonitor[$event['MonitorId']]['MinGap'] )
|
||||||
|
@ -140,7 +141,10 @@ while( $event = $result->fetch(PDO::FETCH_ASSOC) ) {
|
||||||
<tr>
|
<tr>
|
||||||
<th class="colId"><?php echo translate('Id') ?></th>
|
<th class="colId"><?php echo translate('Id') ?></th>
|
||||||
<th class="colName"><i class="material-icons md-18">videocam</i> <?php echo translate('Name') ?></th>
|
<th class="colName"><i class="material-icons md-18">videocam</i> <?php echo translate('Name') ?></th>
|
||||||
|
<th class="colServer"><?php echo translate('Server') ?></th>
|
||||||
<th class="colEvents"><?php echo translate('Events') ?></th>
|
<th class="colEvents"><?php echo translate('Events') ?></th>
|
||||||
|
<th class="colFirstEvent"><?php echo translate('FirstEvent') ?></th>
|
||||||
|
<th class="colLastEvent"><?php echo translate('LastEvent') ?></th>
|
||||||
<th class="colMinGap"><?php echo translate('MinGap') ?></th>
|
<th class="colMinGap"><?php echo translate('MinGap') ?></th>
|
||||||
<th class="colMaxGap"><?php echo translate('MaxGap') ?></th>
|
<th class="colMaxGap"><?php echo translate('MaxGap') ?></th>
|
||||||
<th class="colMissingFiles"><?php echo translate('MissingFiles') ?></th>
|
<th class="colMissingFiles"><?php echo translate('MissingFiles') ?></th>
|
||||||
|
@ -152,8 +156,25 @@ while( $event = $result->fetch(PDO::FETCH_ASSOC) ) {
|
||||||
for( $monitor_i = 0; $monitor_i < count($displayMonitors); $monitor_i += 1 ) {
|
for( $monitor_i = 0; $monitor_i < count($displayMonitors); $monitor_i += 1 ) {
|
||||||
$monitor = $displayMonitors[$monitor_i];
|
$monitor = $displayMonitors[$monitor_i];
|
||||||
$Monitor = new Monitor($monitor);
|
$Monitor = new Monitor($monitor);
|
||||||
|
|
||||||
$montagereview_link = "?view=montagereview&live=0&MonitorId=". $monitor['Id'] . '&minTime='.$minTime.'&maxTime='.$maxTime;
|
$montagereview_link = "?view=montagereview&live=0&MonitorId=". $monitor['Id'] . '&minTime='.$minTime.'&maxTime='.$maxTime;
|
||||||
|
|
||||||
|
if ( isset($EventsByMonitor[$Monitor->Id()]) ) {
|
||||||
|
$EventCounts = $EventsByMonitor[$Monitor->Id()];
|
||||||
|
$MinGap = $EventCounts['MinGap'];
|
||||||
|
$MaxGap = $EventCounts['MaxGap'];
|
||||||
|
$FileMissing = $EventCounts['FileMissing'];
|
||||||
|
$ZeroSize = $EventCounts['ZeroSize'];
|
||||||
|
$FirstEvent = $EventCounts['Events'][0];
|
||||||
|
$LastEvent = end($EventCounts['Events']);
|
||||||
|
} else {
|
||||||
|
$MinGap = 0;
|
||||||
|
$MaxGap = 0;
|
||||||
|
$FileMissing = 0;
|
||||||
|
$ZeroSize = 0;
|
||||||
|
$FirstEvent = 0;
|
||||||
|
$LastEvent = 0;
|
||||||
|
}
|
||||||
|
|
||||||
?>
|
?>
|
||||||
<tr id="<?php echo 'monitor_id-'.$monitor['Id'] ?>" title="<?php echo $monitor['Id'] ?>">
|
<tr id="<?php echo 'monitor_id-'.$monitor['Id'] ?>" title="<?php echo $monitor['Id'] ?>">
|
||||||
<td class="colId"><a href="<?php echo $montagereview_link ?>"><?php echo $monitor['Id'] ?></a></td>
|
<td class="colId"><a href="<?php echo $montagereview_link ?>"><?php echo $monitor['Id'] ?></a></td>
|
||||||
|
@ -168,11 +189,14 @@ for( $monitor_i = 0; $monitor_i < count($displayMonitors); $monitor_i += 1 ) {
|
||||||
}, $Monitor->GroupIds() ) );
|
}, $Monitor->GroupIds() ) );
|
||||||
?>
|
?>
|
||||||
</div></td>
|
</div></td>
|
||||||
|
<td class="colServer"><?php echo $Monitor->Server()->Name()?></td>
|
||||||
<td class="colEvents"><?php echo isset($EventsByMonitor[$Monitor->Id()])?count($EventsByMonitor[$Monitor->Id()]['Events']):0 ?></td>
|
<td class="colEvents"><?php echo isset($EventsByMonitor[$Monitor->Id()])?count($EventsByMonitor[$Monitor->Id()]['Events']):0 ?></td>
|
||||||
<td class="colMinGap"><?php echo isset($EventsByMonitor[$Monitor->Id()])?$EventsByMonitor[$Monitor->Id()]['MinGap']:0 ?></td>
|
<td class="colFirstEvent"><?php echo $FirstEvent ? $FirstEvent->link_to($FirstEvent->Id().' at ' . $FirstEvent->StartTime()) : 'none'?></td>
|
||||||
<td class="colMaxGap"><?php echo isset($EventsByMonitor[$Monitor->Id()])?$EventsByMonitor[$Monitor->Id()]['MaxGap']:0 ?></td>
|
<td class="colLastEvent"><?php echo $LastEvent ? $LastEvent->link_to($LastEvent->Id().' at ' . $LastEvent->StartTime()) : 'none'?></td>
|
||||||
<td class="colFileMissing"><?php echo isset($EventsByMonitor[$Monitor->Id()])?$EventsByMonitor[$Monitor->Id()]['FileMissing']:0 ?></td>
|
<td class="colMinGap"><?php echo $MinGap ?></td>
|
||||||
<td class="colZeroSize"><?php echo isset($EventsByMonitor[$Monitor->Id()])?$EventsByMonitor[$Monitor->Id()]['ZeroSize']:0 ?></td>
|
<td class="colMaxGap"><?php echo $MaxGap ?></td>
|
||||||
|
<td class="colFileMissing<?php echo $FileMissing ? ' errorText' : ''?>"><?php echo $FileMissing ?></td>
|
||||||
|
<td class="colZeroSize<?php echo $ZeroSize ? ' errorText' : ''?>"><?php echo $ZeroSize ?></td>
|
||||||
</tr>
|
</tr>
|
||||||
<?php
|
<?php
|
||||||
} # end for each monitor
|
} # end for each monitor
|
||||||
|
|
Loading…
Reference in New Issue