mirror of
https://github.com/xcat2/xcat-core.git
synced 2026-09-04 20:17:55 +00:00
refactor(dhcp): share OMAPI command runner
This commit is contained in:
@@ -0,0 +1,77 @@
|
||||
package xCAT::DHCP::OmapiRunner;
|
||||
|
||||
use strict;
|
||||
use warnings;
|
||||
|
||||
use File::Temp qw(tempfile);
|
||||
use POSIX qw(WNOHANG);
|
||||
use Time::HiRes qw(sleep);
|
||||
|
||||
sub open_command_file {
|
||||
my ($class, $directory) = @_;
|
||||
|
||||
$directory ||= $class->_command_directory();
|
||||
mkdir $directory unless -d $directory;
|
||||
|
||||
my ($handle, $path) = tempfile('omshell.XXXXXX', DIR => $directory, UNLINK => 0);
|
||||
return { handle => $handle, path => $path };
|
||||
}
|
||||
|
||||
sub run_command_file {
|
||||
my ( $class, $command_file, $omshell_path ) = @_;
|
||||
|
||||
my $pid = $class->_fork();
|
||||
return 'fork_error' unless defined $pid;
|
||||
|
||||
if ( $pid == 0 ) {
|
||||
open( STDIN, '<', $command_file ) or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open( STDOUT, '>', '/dev/null' ) or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open( STDERR, '>', '/dev/null' ) or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
exec {$omshell_path} $omshell_path;
|
||||
exit 127;
|
||||
}
|
||||
|
||||
for ( 1 .. $class->_completion_attempts() ) {
|
||||
if ( waitpid( $pid, WNOHANG ) == $pid ) {
|
||||
sleep $class->_completion_delay();
|
||||
return 'completed';
|
||||
}
|
||||
sleep $class->_poll_interval();
|
||||
}
|
||||
|
||||
kill 'TERM', $pid;
|
||||
for ( 1 .. $class->_termination_attempts() ) {
|
||||
return 'terminated' if waitpid( $pid, WNOHANG ) == $pid;
|
||||
sleep $class->_poll_interval();
|
||||
}
|
||||
|
||||
kill 'KILL', $pid;
|
||||
waitpid( $pid, 0 );
|
||||
return 'killed';
|
||||
}
|
||||
|
||||
sub _fork {
|
||||
return fork();
|
||||
}
|
||||
|
||||
sub _completion_attempts {
|
||||
return 100;
|
||||
}
|
||||
|
||||
sub _termination_attempts {
|
||||
return 20;
|
||||
}
|
||||
|
||||
sub _poll_interval {
|
||||
return 0.1;
|
||||
}
|
||||
|
||||
sub _completion_delay {
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
sub _command_directory {
|
||||
return '/tmp/xcat';
|
||||
}
|
||||
|
||||
1;
|
||||
@@ -11,7 +11,6 @@ use strict;
|
||||
use IPC::Open2;
|
||||
use IPC::Open3;
|
||||
use IO::Select;
|
||||
use File::Temp qw(tempfile);
|
||||
use Symbol qw/gensym/;
|
||||
use POSIX qw/WNOHANG/;
|
||||
use Time::HiRes qw(sleep);
|
||||
@@ -36,6 +35,7 @@ use xCAT::SvrUtils;
|
||||
use xCAT::DHCP::BootPolicy;
|
||||
use xCAT::DHCP::Backend;
|
||||
use xCAT::DHCP::OmapiPolicy;
|
||||
use xCAT::DHCP::OmapiRunner;
|
||||
use xCAT::DHCP::Range;
|
||||
use xCAT::TableUtils;
|
||||
use xCAT::NetworkUtils qw/getipaddr/;
|
||||
@@ -412,45 +412,10 @@ sub _open_omshell_writer
|
||||
{
|
||||
my $settings = shift;
|
||||
|
||||
mkdir "/tmp/xcat" unless -d "/tmp/xcat";
|
||||
my ($omshell_stdin, $command_file) = tempfile('omshell.XXXXXX', DIR => '/tmp/xcat', UNLINK => 0);
|
||||
return unless $omshell_stdin;
|
||||
my $command = xCAT::DHCP::OmapiRunner->open_command_file();
|
||||
return unless ref($command) eq 'HASH' && $command->{handle};
|
||||
|
||||
return ($omshell_stdin, { command_file => $command_file, omshell_path => $settings->{omshell_path} });
|
||||
}
|
||||
|
||||
sub _run_omshell_command_file
|
||||
{
|
||||
my ($command_file, $omshell_path) = @_;
|
||||
|
||||
my $pid = fork();
|
||||
return unless defined $pid;
|
||||
|
||||
if ($pid == 0) {
|
||||
open(STDIN, '<', $command_file) or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open(STDOUT, '>', '/dev/null') or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open(STDERR, '>', '/dev/null') or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
exec { $omshell_path } $omshell_path;
|
||||
exit 127;
|
||||
}
|
||||
|
||||
for (1 .. 100) {
|
||||
if (waitpid($pid, WNOHANG) == $pid) {
|
||||
sleep 1.0;
|
||||
return 1;
|
||||
}
|
||||
sleep 0.1;
|
||||
}
|
||||
|
||||
kill 'TERM', $pid;
|
||||
for (1 .. 20) {
|
||||
return if waitpid($pid, WNOHANG) == $pid;
|
||||
sleep 0.1;
|
||||
}
|
||||
|
||||
kill 'KILL', $pid;
|
||||
waitpid($pid, 0);
|
||||
return;
|
||||
return ($command->{handle}, { command_file => $command->{path}, omshell_path => $settings->{omshell_path} });
|
||||
}
|
||||
|
||||
sub _close_omshell_writer
|
||||
@@ -461,9 +426,12 @@ sub _close_omshell_writer
|
||||
|
||||
return unless ref($writer) eq 'HASH';
|
||||
|
||||
my $ok = _run_omshell_command_file($writer->{command_file}, $writer->{omshell_path});
|
||||
my $status = xCAT::DHCP::OmapiRunner->run_command_file(
|
||||
$writer->{command_file}, $writer->{omshell_path}
|
||||
);
|
||||
unlink $writer->{command_file};
|
||||
syslog("local4|err", "omshell did not complete while updating DHCP reservations") unless $ok;
|
||||
syslog("local4|err", "omshell did not complete while updating DHCP reservations")
|
||||
unless $status eq 'completed';
|
||||
}
|
||||
|
||||
######################################################
|
||||
|
||||
@@ -10,13 +10,9 @@ BEGIN
|
||||
use lib "$::XCATROOT/lib/perl";
|
||||
|
||||
use Getopt::Long;
|
||||
use File::Temp qw(tempfile);
|
||||
use Fcntl ':flock';
|
||||
use IPC::Open3;
|
||||
use POSIX qw/WNOHANG/;
|
||||
use Symbol qw/gensym/;
|
||||
use Time::HiRes qw(sleep);
|
||||
use xCAT::DHCP::OmapiPolicy;
|
||||
use xCAT::DHCP::OmapiRunner;
|
||||
use xCAT::Table;
|
||||
|
||||
sub usage{
|
||||
@@ -146,41 +142,17 @@ if($help){
|
||||
$omshell_commands .= "close\n";
|
||||
}
|
||||
|
||||
mkdir "/tmp/xcat" unless -d "/tmp/xcat";
|
||||
my ($omshell, $command_file) = tempfile('omshell.XXXXXX', DIR => '/tmp/xcat', UNLINK => 0);
|
||||
my $command = xCAT::DHCP::OmapiRunner->open_command_file();
|
||||
my $omshell = ref($command) eq 'HASH' ? $command->{handle} : undef;
|
||||
die "Unable to start omshell: $!" unless $omshell;
|
||||
print $omshell $omshell_commands;
|
||||
close($omshell);
|
||||
|
||||
my $pid = fork();
|
||||
die "Unable to start omshell: $!" unless defined $pid;
|
||||
if ($pid == 0) {
|
||||
open(STDIN, '<', $command_file) or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open(STDOUT, '>', '/dev/null') or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
open(STDERR, '>', '/dev/null') or exit 127; ## no critic (InputOutput::RequireCheckedOpen)
|
||||
exec { $settings->{omshell_path} } $settings->{omshell_path};
|
||||
exit 127;
|
||||
}
|
||||
|
||||
for (1 .. 100) {
|
||||
if (waitpid($pid, WNOHANG) == $pid) {
|
||||
sleep 1.0;
|
||||
unlink $command_file;
|
||||
exit 0;
|
||||
}
|
||||
sleep 0.1;
|
||||
}
|
||||
kill 'TERM', $pid;
|
||||
for (1 .. 20) {
|
||||
if (waitpid($pid, WNOHANG) == $pid) {
|
||||
unlink $command_file;
|
||||
exit 0;
|
||||
}
|
||||
sleep 0.1;
|
||||
}
|
||||
kill 'KILL', $pid;
|
||||
waitpid($pid, 0);
|
||||
unlink $command_file;
|
||||
my $status = xCAT::DHCP::OmapiRunner->run_command_file(
|
||||
$command->{path}, $settings->{omshell_path}
|
||||
);
|
||||
die "Unable to start omshell: $!" if $status eq 'fork_error';
|
||||
unlink $command->{path};
|
||||
}else{
|
||||
&usage;
|
||||
exit 1;
|
||||
|
||||
Reference in New Issue
Block a user