Net-Daemon
view release on metacpan or search on metacpan
lib/Net/Daemon.pm view on Meta::CPAN
#
# Purpose: Reads the config file.
#
# Inputs: $self - Instance
# $file - config file name
# $options - Hash of command line options; these are not
# really for being processed by this method. We pass
# it just in case. The new() method will process them
# at a later time.
# $args - Array ref of other command line options.
#
############################################################################
sub ReadConfigFile {
my ( $self, $file, $options, $args ) = @_;
if ( !-f $file ) {
$self->Fatal("No such config file: $file");
}
$@ = '';
my $copts = do File::Spec->rel2abs($file);
if ($@) {
$self->Fatal("Error while processing config file $file: $@");
}
if ( !defined($copts) && $! ) {
$self->Fatal("Cannot read config file $file: $!");
}
if ( !$copts || ref($copts) ne 'HASH' ) {
$self->Fatal("Config file $file did not return a hash ref.");
}
# Override current configuration with config file options.
while ( my ( $var, $val ) = each %$copts ) {
$self->{$var} = $val;
}
}
############################################################################
#
# Name: new (Class method)
#
# Purpose: Constructor
#
# Inputs: $class - This class
# $attr - Hash ref of attributes
# $args - Array ref of command line arguments
#
# Result: Server object for success, error message otherwise
#
############################################################################
sub new ($$;$) {
my ( $class, $attr, $args ) = @_;
my ($self) = $attr ? \%$attr : {};
bless( $self, ( ref($class) || $class ) );
my $options = ( $self->{'options'} ||= {} );
$self->{'args'} ||= [];
if ($args) {
my @optList = map { $_->{'template'} } values( %{ $class->Options() } );
local @ARGV = @$args;
if ( !Getopt::Long::GetOptions( $options, @optList ) ) {
$self->Usage();
}
@{ $self->{'args'} } = @ARGV;
if ( $options->{'help'} ) {
$self->Usage();
}
if ( $options->{'version'} ) {
print STDERR $self->Version(), "\n";
exit 1;
}
}
my $file = $options->{'configfile'} || $self->{'configfile'};
if ($file) {
$self->ReadConfigFile( $file, $options, $args );
}
while ( my ( $var, $val ) = each %$options ) {
$self->{$var} = $val;
}
if ( $self->{'childs'} ) {
$self->{'mode'} = 'single';
}
elsif ( !defined( $self->{'mode'} ) ) {
if ( $^O ne 'MSWin32' && $^V ge v5.10.0 && eval { require threads } ) {
$self->{'mode'} = 'ithreads';
}
else {
my $fork = 0;
if ( $^O ne "MSWin32" ) {
my $pid = eval { fork() };
if ( defined($pid) ) {
if ( !$pid ) { exit; } # Child
$fork = 1;
wait;
}
}
if ($fork) {
$self->{'mode'} = 'fork';
}
else {
$self->{'mode'} = 'single';
}
}
}
if ( $self->{'mode'} eq 'ithreads' ) {
no warnings 'redefine';
require threads;
use warnings 'redefine';
}
elsif ( $self->{'mode'} eq 'fork' ) {
# Initialize forking mode ...
}
elsif ( $self->{'mode'} eq 'single' ) {
# Initialize single mode ...
lib/Net/Daemon.pm view on Meta::CPAN
'description' => '--base '
. 'dec (default), hex or oct'
};
$options;
}
# Treat command line option in the constructor
sub new ($$;$) {
my($class, $attr, $args) = @_;
my($self) = $class->SUPER::new($attr, $args);
if ($self->{'options'} && $self->{'options'}->{'base'}) {
$self->{'base'} = $self->{'options'}->{'base'}
}
if (!$self->{'base'}) {
$self->{'base'} = 'dec';
}
$self;
}
# Initialize per-connection state after Clone()
sub post_clone ($) {
my($self) = @_;
$self->{'base'} = $self->{'parent'}->{'base'};
}
sub Run ($) {
my($self) = @_;
my($line, $sock);
$sock = $self->{'socket'};
while (1) {
if (!defined($line = $sock->getline())) {
if ($sock->error()) {
$self->Error("Client connection error %s",
$sock->error());
}
$sock->close();
return;
}
$line =~ s/\s+$//; # Remove CRLF
my($result) = eval $line;
my($rc);
if ($self->{'base'} eq 'hex') {
$rc = printf $sock ("%x\n", $result);
} elsif ($self->{'base'} eq 'oct') {
$rc = printf $sock ("%o\n", $result);
} else {
$rc = printf $sock ("%d\n", $result);
}
if (!$rc) {
$self->Error("Client connection error %s",
$sock->error());
$sock->close();
return;
}
}
}
package main;
my $server = Calculator->new({'pidfile' => 'none',
'localport' => 2000}, \@ARGV);
$server->Bind();
=head1 KNOWN PROBLEMS
Most, or even any, known problems are related to the Sys::Syslog module
which is by default used for logging events under Unix. I'll quote some
examples:
=over
=item Usage: Sys::Syslog::_PATH_LOG at ...
This problem is treated in perl bug 20000712.003. A workaround is
changing line 277 of Syslog.pm to
my $syslog = &_PATH_LOG() || croak "_PATH_LOG not found in syslog.ph";
=back
=head1 AUTHOR AND COPYRIGHT
Net::Daemon is Copyright (C) 1998, Jochen Wiedmann
Am Eisteich 9
72555 Metzingen
Germany
Phone: +49 7123 14887
Email: joe@ispsoft.de
All rights reserved.
You may distribute this package under the terms of either the GNU
General Public License or the Artistic License, as specified in the
Perl README file.
=head1 SEE ALSO
L<RPC::pServer(3)>, L<Netserver::Generic(3)>, L<Net::Daemon::Log(3)>,
L<Net::Daemon::Test(3)>
=cut
( run in 0.593 second using v1.01-cache-2.11-cpan-0bb4e1dffa6 )