mirror of
https://github.com/ChronosX88/psyced.git
synced 2024-12-04 16:12:20 +00:00
872 lines
24 KiB
Perl
Executable File
872 lines
24 KiB
Perl
Executable File
#!/usr/bin/env perl
|
|
### -I/opt/psyced/utility
|
|
# the include path would help finding INI.pm, but what if you the user
|
|
# have decided to install psyced elsewhere?
|
|
#
|
|
# psyconf(8) - tool that generates psyc configuration
|
|
# files out of a common psyced.ini
|
|
#
|
|
# $Id: psyconf,v 1.80 2008/10/26 15:24:01 lynx Exp $
|
|
|
|
=head1 NAME
|
|
|
|
psyconf - a configuration tool for PSYCED
|
|
|
|
=head1 SYNOPSIS
|
|
|
|
Usage: psyconf [ <file> ]
|
|
|
|
The default configuration file used is either ./psyced.ini
|
|
or /etc/psyc/psyced.ini
|
|
|
|
=cut
|
|
|
|
use File::Spec;
|
|
|
|
# this approach still doesn't work when installing on gentoo
|
|
# we need a seperate ebuild for INI.pm. until then we will use
|
|
# the stupid parser
|
|
#
|
|
#BEGIN { # BEGIN just in case somebody ever accesses INI::something by hand
|
|
# unless (%INI::) { # get INI, if it isn't in this file (somewhere above)
|
|
# my @dir;
|
|
# my $inilocation;
|
|
#
|
|
# @dir = File::Spec->splitdir($0);
|
|
# pop @dir;
|
|
# $inilocation = File::Spec->catfile(@dir, qw".. utility INI.pm");
|
|
#
|
|
# if (-f $inilocation) {
|
|
# require $inilocation;
|
|
# } else {
|
|
# require INI;
|
|
# }
|
|
# }
|
|
#}
|
|
|
|
sub debug() { 0 }
|
|
|
|
# append something while testing
|
|
#my $test = "-NEW";
|
|
#use Data::Dumper;
|
|
|
|
sub say {
|
|
print join('', @_); # if $test;
|
|
}
|
|
|
|
sub sys {
|
|
print join(' ', @_), "\n" if debug;
|
|
if (system(@_)) {
|
|
if ($? == -1) {
|
|
print "\t{failed to execute: $!}\n";
|
|
} elsif ($? & 127) {
|
|
printf "\t{command died with sig %d, %s core dump}\n",
|
|
($? & 127), ($? & 128) ? 'with' : 'without';
|
|
} else {
|
|
printf "\t{command exited with value %d}\n", $? >> 8;
|
|
}
|
|
exit $? if $?;
|
|
exit $@ if $@;
|
|
}
|
|
}
|
|
|
|
### MAIN ###
|
|
# if you are manually compiling an ldmud, rename it or change here.
|
|
my $driver = 'psyclpc';
|
|
my $newbie = 0;
|
|
|
|
use Getopt::Std;
|
|
&getopt;
|
|
|
|
print STDERR '$Id: psyconf,v 1.80 2008/10/26 15:24:01 lynx Exp $', "\n";
|
|
|
|
my $conf = shift || 'psyced.ini';
|
|
$conf = '/etc/psyc/psyced.ini' unless -r $conf;
|
|
# should we complain if two psyced.ini files exist?
|
|
# lymeca got confused at this point, expecting the systemwide
|
|
# psyced.ini to be used, but actually having a local copy
|
|
say "The PSYCED configuration tool. Looking at $conf\n\n";
|
|
|
|
# this is the super-duper fancy amazing INI handler
|
|
# #use INI; # ":verbose";
|
|
# my %c;
|
|
# tie(%c, INI, $conf, 5);
|
|
|
|
# and this is the stupider INI parser in a couple of lines
|
|
# cute, but we'd like to have the features of INI.pm one happy day
|
|
my %c, $f = "";
|
|
open C, $conf;
|
|
while(<C>) {
|
|
next if /^;/;
|
|
next if /^\s*$/;
|
|
$f = $1, next if /^\[(\w+)\]\s*$/;
|
|
$c{"$f$1"} = $2, next if /^(\w+)\s*=\s*(.+?)\s*$/;
|
|
die "cannot parse line $. in $conf:\n\t$_\n";
|
|
}
|
|
close C;
|
|
|
|
if ($opt_D) {
|
|
if ($c{_basic_list_script_init}) {
|
|
foreach (split /\s+/, $c{_basic_list_script_init}) {
|
|
say "Deinstallation! Removing $_\n";
|
|
unlink $_;
|
|
}
|
|
}
|
|
exit;
|
|
}
|
|
|
|
use POSIX;
|
|
my @uname = POSIX::uname();
|
|
# if POSIX.pm is unavailable, this also works:
|
|
# @uname = split ' ', `uname -s -r -n -m -v`;
|
|
#print Dumper(@uname);
|
|
my $_type_machine = $uname[$#uname];
|
|
$_ = $uname[2];
|
|
/^(\w+\.\w+)\b/ or /^(\w+)\b/;
|
|
my $_type_system = "\L$uname[0]\E";
|
|
my $_version_system = "$uname[0]/$1";
|
|
my $_type_architecture = lc "$_type_machine-$uname[0]";
|
|
say "Machine Type: $_type_machine. OS Type: $_type_system. ",
|
|
"Arch: $_type_architecture\n";
|
|
#Typical outputs:
|
|
# Machine Type: i686. OS Type: linux. Arch: i686-linux
|
|
# Machine Type: x86_64. OS Type: linux. Arch: x86_64-linux
|
|
# Machine Type: Power Macintosh. OS Type: darwin. Arch: power macintosh-darwin
|
|
|
|
my $base = $c{_basic_path_base};
|
|
die "_basic_path_base not defined in config" unless $base;
|
|
die "Base directory $base defined as _basic_path_base not available"
|
|
unless -x $base;
|
|
my $sandbox = "$base/world";
|
|
die "psyced library $sandbox does not exist" unless -x $sandbox;
|
|
my $execs = "$base/bin-$_type_architecture";
|
|
my $config = $c{_basic_path_configuration} || $base;
|
|
# this isn't taking $ARCH_DIR from install.sh into account
|
|
# but maybe it shouldn't anyway..
|
|
say "Looking for driver in $execs/$driver\n";
|
|
unless (-x $execs && -x "$execs/$driver") {
|
|
$execs = "$base/bin-$_type_system";
|
|
say "Looking for driver in $execs/$driver\n";
|
|
unless (-x $execs && -x "$execs/$driver") {
|
|
$execs = "$base/bin-linux";
|
|
say "Looking for driver in $execs/$driver\n";
|
|
unless (-x $execs && -x "$execs/$driver") {
|
|
$execs = "$base/bin";
|
|
say "Looking for driver in $execs/$driver\n";
|
|
unless (-x $execs && -x "$execs/$driver") {
|
|
$execs = "/usr/local/sbin";
|
|
say "Looking for driver in $execs/$driver\n";
|
|
unless (-x $execs && -x "$execs/$driver") {
|
|
$execs = "/usr/sbin";
|
|
say "Looking for driver in $execs/$driver\n";
|
|
die <<X unless -x $execs && -x "$execs/$driver";
|
|
Could not find any directory containing $driver.
|
|
X
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
say "Found driver in $execs/$driver\n";
|
|
# is it really that hard?
|
|
die "but $execs/erq is missing\n" unless -x "$execs/erq";
|
|
|
|
my $user = $c{_basic_system_user} || 'daemon';
|
|
my ($login,$pass,$uid,$gid) = getpwnam($user)
|
|
or die "uid '$user' not defined on this system";
|
|
# this doesn't mean psyconf is intended to run as $user too!!
|
|
say "psyced must later be running as user $user ($uid:$gid)\n";
|
|
# will automatically, when started via etc/init.d but if you
|
|
# start it manually, you have to switch to that user yourself
|
|
|
|
my $ho = $c{_basic_host_name} || $ENV{HOST} || 'psyc';
|
|
my $chatname = $c{_basic_nick_server} ||
|
|
$c{_basic_host_name} || 'psyced';
|
|
$chatname = 'psyced' if $chatname eq 'psyc';
|
|
|
|
my $t = "$base/local";
|
|
unless (-w $t) {
|
|
$newbie = 1;
|
|
say <<X;
|
|
|
|
Welcome new installer!
|
|
Copying (just this time) default configuration into $t ..
|
|
X
|
|
sys("/bin/cp", "-rp", "$base/config/blueprint", $t);
|
|
}
|
|
$t = "$base/data";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/data/person";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/data/place";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/log";
|
|
mkdir($t) unless -w $t;
|
|
|
|
$t = "$base/local/ports.h$test";
|
|
say "Generating control file $t ..\n";
|
|
rename $t, "$t~";
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
|
|
print O <<X;
|
|
// CAUTION! This file has been generated using $0.
|
|
// Don't edit unless you are no longer going to use the configuration tool.
|
|
// Edit $conf instead, then run $0 again.
|
|
|
|
/* the values in here may be the same as in services.h
|
|
* or they may be not. so always be aware which one's you
|
|
* are using to which purpose. -lynX
|
|
*/
|
|
#ifndef PORTS_H
|
|
#define PORTS_H
|
|
|
|
#define PSYC_PORT $c{_protocols_port_PSYC}
|
|
#define PSYCS_PORT $c{_protocols_port_PSYC_encrypted}
|
|
|
|
#define HTTP_PORT $c{_protocols_port_HTTP}
|
|
#define HTTPS_PORT $c{_protocols_port_HTTP_encrypted}
|
|
|
|
#define IRC_PORT $c{_protocols_port_IRC}
|
|
#define IRCS_PORT $c{_protocols_port_IRC_encrypted}
|
|
|
|
#define JABBER_PORT $c{_protocols_port_jabber_clients}
|
|
#define JABBERS_PORT $c{_protocols_port_jabber_clients_encrypted}
|
|
#define JABBER_S2S_PORT $c{_protocols_port_jabber_S2S}
|
|
|
|
#define TELNET_PORT $c{_protocols_port_telnet}
|
|
#define TELNETS_PORT $c{_protocols_port_telnet_encrypted}
|
|
|
|
#define APPLET_PORT $c{_protocols_port_applet}
|
|
|
|
#define POP3_PORT $c{_protocols_port_POP3}
|
|
#define POP3S_PORT $c{_protocols_port_POP3_encrypted}
|
|
|
|
#define SMTP_PORT $c{_protocols_port_SMTP}
|
|
#define SMTPS_PORT $c{_protocols_port_SMTP_encrypted}
|
|
|
|
#define NTTP_PORT $c{_protocols_port_NNTP}
|
|
#define NNTPS_PORT $c{_protocols_port_NNTP_encrypted}
|
|
|
|
// experimental PSYC 1.0 implementation
|
|
#define SPYC_PORT $c{_protocols_port_SPYC}
|
|
|
|
#endif
|
|
X
|
|
close O;
|
|
chmod 0644, $t;
|
|
|
|
my $ports="";
|
|
$ports .= "$c{_protocols_port_PSYC} $c{_protocols_port_jabber_S2S} $c{_protocols_port_applet} $c{_protocols_port_telnet} $c{_protocols_port_HTTP} $c{_protocols_port_IRC} $c{_protocols_port_jabber_clients} $c{_protocols_port_SMTP} $c{_protocols_port_NNTP} $c{_protocols_port_SPYC}" if $c{_protocols_use_encryption} ne 'only';
|
|
$ports .= " $c{_protocols_port_PSYC_encrypted} $c{_protocols_port_telnet_encrypted} $c{_protocols_port_HTTP_encrypted} $c{_protocols_port_IRC_encrypted} $c{_protocols_port_jabber_clients_encrypted} $c{_protocols_port_SMTP_encrypted} $c{_protocols_port_NNTP_encrypted}" if $c{_protocols_use_encryption};
|
|
|
|
my @adm;
|
|
unless ($c{_administrators_list_nicks}) {
|
|
print STDERR <<X;
|
|
|
|
You have decided to run an unadministered psyced. That's a socially quite
|
|
interesting idea, but the software can't deal with that yet.
|
|
Continue nonetheless? (hit ctrl-c for mental sanity)
|
|
X
|
|
<STDIN>;
|
|
} else {
|
|
foreach (split /\s+/, $c{_administrators_list_nicks}) {
|
|
my $ni = lc($_);
|
|
push @adm, $ni;
|
|
|
|
$t = "$base/data/person/$ni.o$test";
|
|
next if -e $t;
|
|
|
|
say "Creating administrator in $t\n";
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
my $pw = $c{_administrators_password_default};
|
|
unless ($pw) {
|
|
print STDERR "Please input a password for $_: ";
|
|
$pw = <STDIN>;
|
|
chomp $pw;
|
|
}
|
|
print O <<X;
|
|
#0:0
|
|
_v (["password":"$pw","name":"$_",])
|
|
X
|
|
close O;
|
|
chmod 0600, $t;
|
|
chown $uid, $gid, $t if $uid;
|
|
}
|
|
}
|
|
my $adm = join '", "', @adm;
|
|
|
|
$t = "$base/local/psyconf.h$test";
|
|
say "Generating control file $t ..\n";
|
|
rename $t, "$t~";
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
|
|
print O <<X;
|
|
// CAUTION! This file has been generated using $0.
|
|
// Don't edit unless you are no longer going to use the configuration tool.
|
|
// Edit $conf instead, then run $0 again.
|
|
// If you want to tune psyced, edit local.h instead!
|
|
|
|
X
|
|
if ( $c{_optional_config_HTTP} ) {
|
|
print O <<X;
|
|
# define WEB_CONFIGURE
|
|
|
|
X
|
|
print STDERR <<X unless $c{_protocols_port_HTTP} or $c{_protocols_port_HTTP_encrypted};
|
|
|
|
Warning: _optional_config_HTTP activated without any HTTP port. You won't be
|
|
able to use the web configuration tool without webserver.
|
|
|
|
X
|
|
}
|
|
print STDERR <<X if $c{_optional_charset_system};
|
|
Warning: _optional_charset_system is obsolete. Please remove it.
|
|
X
|
|
# print O <<X if $c{_optional_charset_system};
|
|
## define SYSTEM_CHARSET "$c{_optional_charset_system}"
|
|
#
|
|
#X
|
|
print O <<X if $c{_optional_charset_console};
|
|
// optional
|
|
# define CONSOLE_CHARSET "$c{_optional_charset_console}"
|
|
|
|
X
|
|
|
|
# if ( $c{_basic_host_domain} ) {
|
|
# print O <<X;
|
|
## undef __DOMAIN_NAME__
|
|
## define __DOMAIN_NAME__ "$c{_basic_host_domain}"
|
|
## define SERVER_HOST "$ho." __DOMAIN_NAME__
|
|
#
|
|
#X
|
|
# } else {
|
|
# print O <<X;
|
|
## if __DOMAIN_NAME__ != "unknown"
|
|
## define SERVER_HOST "$ho." __DOMAIN_NAME__
|
|
## else
|
|
## if __HOST_IP_NUMBER__ == "127.0.0.1"
|
|
## define SERVER_HOST __HOST_NAME__
|
|
## else
|
|
## define SERVER_HOST "$ho"
|
|
## endif
|
|
## endif
|
|
#
|
|
#X
|
|
# }
|
|
print O <<X if $c{_basic_host_domain};
|
|
# define CHATDOMAIN "$c{_basic_host_domain}"
|
|
X
|
|
my $pl = lc($c{_basic_place_default}) || 'rendezvous';
|
|
my $la = lc($c{_basic_language_default}) || 'en';
|
|
|
|
print O <<X;
|
|
# define CHATHOST "$ho"
|
|
# define CHATNAME "$chatname"
|
|
|
|
# define DEFPLACE "$pl"
|
|
# define DEFLANG "$la"
|
|
|
|
// only required field, really
|
|
# define ADMINISTRATORS "$adm"
|
|
|
|
// architecture and operating system (used in PSYC headers etc.)
|
|
# define MACHTYPE "$_type_machine"
|
|
# define OSTYPE "$_version_system"
|
|
X
|
|
close O;
|
|
chmod 0640, $t;
|
|
chown $uid, $gid, $t if $uid;
|
|
|
|
# PSYCED LAUNCHER
|
|
$t = "$base/bin/psyced$test";
|
|
say "Generating control file $t ..\n";
|
|
rename $t, "$t~";
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
|
|
my $db = $c{_optional_level_debug} || '0';
|
|
my $psyced = "$execs/$driver -DDEBUG=$db";
|
|
my $torify = "";
|
|
my $debugfile;
|
|
|
|
if ( $c{_optional_use_file_debug} ) {
|
|
$debugfile = "$sandbox/log/psyced.debug";
|
|
$psyced .= " --debug-file ". $debugfile;
|
|
# since psyclpc 4.0.4 backtraces are also in the regular console log.. yippie!
|
|
# say "ATTENTION: $debugfile will contain runtime error backtraces.\n";
|
|
}
|
|
# else: ldmud tries to create $hostname.debug.log in $sandbox
|
|
# psyclpc is good boy instead. so we can keep this optional.
|
|
|
|
my $hc = 0;
|
|
## ldmud bug number one: you have to provide hostname AFTER hostaddr
|
|
if ($c{_basic_host_IP} =~ /^[0-9\.]+$/) {
|
|
$psyced .= " --hostaddr $c{_basic_host_IP}";
|
|
$hc = 1; # problem?
|
|
}
|
|
if ($c{_basic_host_domain} and $c{_basic_host_name}) {
|
|
my $fqdn = "$c{_basic_host_name}.$c{_basic_host_domain}";
|
|
$psyced .= " --hostname $fqdn";
|
|
$hc = 0; # no problem
|
|
say "Your hostname will be assigned as $fqdn.\n";
|
|
if ($c{_basic_host_domain} eq 'onion') {
|
|
$torify = "torsocks";
|
|
say "Enabling PSYC federation over Tor: Using "
|
|
. "torsocks wrapper around psyced.\n";
|
|
say "Warning: Make sure either dnsmasq.conf or "
|
|
. "unbound.conf are in\n"
|
|
. "place for .onion resolution to function.\n";
|
|
}
|
|
}
|
|
## ldmud bug number two
|
|
#WARNING: Because of some funny bug the driver will probably not bind properly
|
|
#to _basic_host_IP as it also needs _basic_host_name and _basic_host_domain
|
|
#to be provided. Hopefully this shortcoming will soon be history.
|
|
#In the meantime please re-edit the psyced.ini to provide all variables.
|
|
print STDERR <<X if $hc == 1;
|
|
|
|
WARNING: _basic_host_IP, _basic_host_name and _basic_host_domain need to be
|
|
provided together as the driver won't figure out the proper name for the IP
|
|
number or vice versa. Please re-edit the psyced.ini to provide all variables.
|
|
|
|
X
|
|
undef $c{_protocols_use_encryption}
|
|
if $c{_protocols_use_encryption} eq 'no';
|
|
|
|
if ($c{_protocols_use_encryption}) {
|
|
my $t = $c{_basic_path_PEM_key};
|
|
if ($t) {
|
|
$t = "$config/$t" unless $t =~ m#^/#;
|
|
print STDERR <<X unless -r $t;
|
|
WARNING: Key file $t does not exist.
|
|
X
|
|
$psyced .= " --tls-key $t";
|
|
}
|
|
if ($t = $c{_basic_path_PEM_certificate}) {
|
|
$t = "$config/$t" unless $t =~ m#^/#;
|
|
print STDERR <<X unless -r $t;
|
|
WARNING: Certificate file $t does not exist.
|
|
X
|
|
$psyced .= " --tls-cert $t";
|
|
}
|
|
if ($t = $c{_basic_path_trust}) {
|
|
$t = "$config/$t" unless $t =~ m#^/#;
|
|
print STDERR <<X unless -r $t;
|
|
WARNING: Trust directory $t does not exist.
|
|
X
|
|
$psyced .= " --tls-trustdirectory $t";
|
|
}
|
|
# ldmud doesn't support this yet
|
|
# $psyced .= " --tlscrldirectory $config/$c{_basic_path_revocation}"
|
|
# if $c{_basic_path_revocation};
|
|
}
|
|
$psyced .= ' '. $c{_optional_extra_debug} if $c{_optional_extra_debug};
|
|
|
|
# you can divert UDP if you know what you are doing.
|
|
my $portUDP = $c{_protocols_port_UDP} || $c{_protocols_port_PSYC};
|
|
my $umask = $c{_optional_umask} || '007';
|
|
print O <<X;
|
|
#!/bin/sh
|
|
#
|
|
# CAUTION! This file has been generated using $0.
|
|
# Don't edit unless you are no longer going to use the configuration tool.
|
|
# Edit $conf instead, then run $0 again.
|
|
|
|
X
|
|
# if the installation isn't intentionally using root rights
|
|
# make sure the admin won't run psyced or do "psyced -u" as root
|
|
# as it will most probably mess up file permissions and break psyced
|
|
print O <<X if $user ne 'root';
|
|
userid=`id | sed "s/).*//" | sed "s/.*(//"`
|
|
# We could even test for != "x$user" here. Should we?
|
|
if test "x\$userid" = "xroot"
|
|
then
|
|
echo "${hi}ERROR: ${lo}You can't run \$0 with root privileges unintentionally.\nUse 'su $user' or edit psyced.ini."
|
|
exit 2
|
|
fi
|
|
|
|
X
|
|
# it's not a security issue really, but shouldn't control files
|
|
# like status-0-beta-OK be outside the sandbox? -lynX
|
|
|
|
print O <<X;
|
|
umask $umask
|
|
|
|
# with this chdir, old ldmud should be able to find its keys anyhow
|
|
cd $base
|
|
|
|
# available flags: -u, -d and -m
|
|
# TODO: i'd like for -b to make a backup archive of the psyced tree before
|
|
# updating, and -r to revert to the last backupped version. whatchathink?
|
|
|
|
# the following if-block handles the -u option for updating your
|
|
# installation by git. it ensures your installation is still basically
|
|
# compatible with the one in the git or complains.
|
|
#
|
|
if test "\$1" = "-u"
|
|
then
|
|
if test -e $sandbox/status-0-beta-OK
|
|
then
|
|
echo ""
|
|
echo "Fetching update from public git repository..."
|
|
echo ""
|
|
git fetch origin
|
|
echo ""
|
|
echo "You can now look at the changes using ${hi}\$0 -d${lo}"
|
|
echo "or activate the changes using ${hi}\$0 -m${lo}"
|
|
fi
|
|
if ! test -e $sandbox/status-0-beta-OK
|
|
then
|
|
echo ""
|
|
echo "${hi}ATTENTION:${lo}"
|
|
echo "The version of psyced you are using is outdated. You cannot"
|
|
echo "get new updates because of incompatibility."
|
|
echo ""
|
|
echo "More information following.."
|
|
echo ""
|
|
cat $sandbox/status-0-DEPRECATED
|
|
echo ""
|
|
echo "The file you just saw is: ${hi}${lib}/status-0-DEPRECATED${lo}."
|
|
exit 1
|
|
else
|
|
# this \$0 is for psyconf, not for psyced.. don't escape it
|
|
echo ""
|
|
echo "It may be a good idea to run ${hi}$0${lo} again before you continue."
|
|
fi
|
|
exit
|
|
fi
|
|
|
|
if test "\$1" = "-d"
|
|
then
|
|
## cvs -q diff -ur HEAD|\$PAGER
|
|
git diff master..origin/master | \$PAGER
|
|
exit
|
|
fi
|
|
|
|
if test "\$1" = "-m"
|
|
then
|
|
git stash save 'changes stashed automatically by psyced -m'
|
|
git merge -s resolve origin
|
|
# restore local changes?
|
|
# git stash pop
|
|
echo ""
|
|
echo "If you had local changes to your files you can now restore them using"
|
|
echo "${hi}git stash pop${lo}"
|
|
exit
|
|
fi
|
|
|
|
# if your ldmud is too old, it may not understand --pidfile and --tls-*
|
|
commandline="$torify $psyced -s 0 -s v0 --swap-file $base/psyced.swap --erq $execs/erq --pidfile $sandbox/data/$driver.pid -m $sandbox -u $portUDP $ports"
|
|
|
|
# keep the pid of this wrapper process, too
|
|
echo \$\$ >data/psyced.pid
|
|
|
|
# neat feature of gnu mv
|
|
VERSION_CONTROL=numbered;
|
|
export VERSION_CONTROL
|
|
|
|
# rm'ing this allows the administrator commands in psyced to stop the loop
|
|
touch $sandbox/data/.autorestart
|
|
while [ -r $sandbox/data/.autorestart ]
|
|
do
|
|
X
|
|
# we can presume gnu mv on linux
|
|
#my $domv = $_type_system eq 'linux' ? 'mv -b' : 'mv -f';
|
|
# yes, but all these backups are overkill
|
|
# who needs these debug logs archived for all eternity anyway?
|
|
my $domv = 'mv -f';
|
|
# maybe we should develop a strategy for all the OTHER logfiles.....
|
|
# but luckily psyclpc has some support for that itself
|
|
|
|
print O <<X if $debugfile;
|
|
touch $debugfile
|
|
$domv $debugfile $debugfile-old
|
|
X
|
|
if ($c{_optional_console_debug}) {
|
|
print O "\t\$commandline\n";
|
|
} else {
|
|
say "The file $sandbox/log/psyced.out will contain the runtime output.\n";
|
|
say "The file $sandbox/log/psyced.err will contain error messages.\n";
|
|
print O <<X;
|
|
touch $sandbox/log/psyced.out $sandbox/log/psyced.err
|
|
$domv $sandbox/log/psyced.err $sandbox/log/psyced.err-old
|
|
# the gnu date manual doesn't mention if +FORMAT is a posix
|
|
# standard or a gnu extension. is this call going to work
|
|
# in most current environments? it does work on bsd, *phew*
|
|
#$domv $sandbox/log/psyced.out $sandbox/log/`date +%Y-%m-%d`.out
|
|
# ah whatever.. let's not make it too complicated..
|
|
# who needs these debug logs archived for all eternity anyway?
|
|
$domv $sandbox/log/psyced.out $sandbox/log/psyced.out-old
|
|
echo ---------------------------------------- >>$sandbox/log/psyced.out
|
|
date >>$sandbox/log/psyced.out
|
|
echo ---------------------------------------- >>$sandbox/log/psyced.out
|
|
\$commandline >>$sandbox/log/psyced.out 2>>$sandbox/log/psyced.err
|
|
X
|
|
}
|
|
print O <<X;
|
|
sleep 3
|
|
done
|
|
X
|
|
close O;
|
|
chmod 0744, $t;
|
|
chown $uid, $gid, $t if $uid;
|
|
|
|
# TODO: generate a psyced.gdb file kind of like this
|
|
print <<X if 0;
|
|
file /bin/psyclpc
|
|
run -DDEBUG=1 -u 4404 4404 2323 6667 5222 6697 etc. whatever flags necessary
|
|
X
|
|
|
|
# PSYCED INIT.D SCRIPT
|
|
$t = "$base/etc";
|
|
mkdir($t) unless -w $t;
|
|
$t .= "/init.d";
|
|
mkdir($t) unless -w $t;
|
|
$t .= "/psyced$test";
|
|
say "Generating control file $t ..\n";
|
|
rename $t, "$t~";
|
|
|
|
# HerraBRE: the init script uses "su -s" which os x doesn't understand.
|
|
#
|
|
# alright, so now i could let it do something else in case of OS X
|
|
# but I need to know (1) how to recognize OSX (2) what to put here!
|
|
$su = 'su -s';
|
|
|
|
# or die.. mention at this point that we should
|
|
# probably be running as root?
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
print O <<X;
|
|
#!/bin/sh
|
|
#
|
|
# CAUTION! This file has been generated using $0.
|
|
# Don't edit unless you are no longer going to use the configuration tool.
|
|
# Edit $conf instead, then run $0 again.
|
|
#
|
|
### BEGIN INIT INFO
|
|
# Provides: psyced
|
|
# Required-Start: \$local_fs \$remote_fs
|
|
# Required-Stop: \$local_fs \$remote_fs
|
|
# Default-Start: 2 3 4 5
|
|
# Default-Stop: S 0 1 6
|
|
# Short-Description: psyced
|
|
# Description: psyced, the Enhanced PSYC Daemon
|
|
### END INIT INFO
|
|
|
|
test -x $base/bin/psyced || exit 0
|
|
|
|
case "\$1" in
|
|
start)
|
|
echo -n "Starting psyced in background ... "
|
|
# route .onion addresses through Tor
|
|
iptables -t nat -A OUTPUT -p tcp -d 127.192.0.0/10 -j REDIRECT --to-ports 9040
|
|
# in nei's environment a zsh would be started to execute the
|
|
# psyced script. so he suggests to add a -s parameter. in our
|
|
# environment both strategies work.
|
|
$su /bin/sh $user $base/bin/psyced &
|
|
# some distributions no longer have /bin/sh in /etc/shells.
|
|
# use a better distribution if they don't! :)
|
|
# this script has to remain posix compatible. bash is no option here.
|
|
echo "OK"
|
|
;;
|
|
stop)
|
|
rm $sandbox/data/.autorestart
|
|
if test -r $sandbox/data/$driver.pid
|
|
then
|
|
echo -n "Instructing psyced to gently shut down ... "
|
|
kill -1 \`cat $sandbox/data/$driver.pid\`
|
|
# this should be enough ideally
|
|
# but we can remove the pid file so a
|
|
# second stop call will kill bill
|
|
rm $sandbox/data/$driver.pid && echo "OK"
|
|
else
|
|
echo -n "Killing psyced brutally ... "
|
|
kill -3 \`cat $sandbox/data/psyced.pid\` && echo "OK"
|
|
fi
|
|
;;
|
|
kill)
|
|
echo -n "Killing psyced brutally ... "
|
|
kill -3 \`cat $sandbox/data/psyced.pid\` && echo "OK"
|
|
;;
|
|
restart)
|
|
echo -n "Instructing psyced to restart ... "
|
|
kill -1 \`cat $sandbox/data/$driver.pid\` && echo "OK"
|
|
;;
|
|
status)
|
|
;;
|
|
*)
|
|
echo "Usage: \$0 {start|stop|restart|kill}"
|
|
exit 1
|
|
;;
|
|
esac
|
|
|
|
X
|
|
close O;
|
|
chmod 0744, $t;
|
|
|
|
if ($c{_basic_list_script_init}) {
|
|
foreach (split /\s+/, $c{_basic_list_script_init}) {
|
|
say "... copying to $_\n";
|
|
`cp "$t" "$_"`;
|
|
}
|
|
}
|
|
|
|
# TORRC
|
|
$t = "$base/etc/tor";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/var";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/var/tor";
|
|
mkdir($t) unless -w $t;
|
|
$t = "$base/etc/tor/torrc";
|
|
say "Generating optional Tor configuration $t ..\n";
|
|
rename $t, "$t~";
|
|
open O, '>', $t or die "Cannot write to $t";
|
|
|
|
print O <<X;
|
|
# This torrc generated from $0
|
|
# Don't edit unless you are no longer going to use the configuration tool.
|
|
# Edit $conf instead, then run $0 again.
|
|
|
|
ControlSocket $base/var/tor/.control
|
|
DataDirectory $base/var/tor
|
|
AutomapHostsOnResolve 1
|
|
SocksPort 9050
|
|
DNSPort 9053
|
|
|
|
# If your tor executable does not support this feature,
|
|
# .onion domain names will not 'resolve' like normal ones.
|
|
TransPort 9040
|
|
# See also the iptables call in the init script.
|
|
# Both are not fundamentally necessary, you can remove them.
|
|
|
|
HiddenServiceDir $base/etc/tor/.onion
|
|
X
|
|
my $i = 4;
|
|
foreach $n ( %c ) {
|
|
next unless $n =~ /^(_protocols_port_\w+)_hidden/;
|
|
print O "HiddenServicePort $c{$n} 127.0.0.1:$c{$1}\n";
|
|
say "Too many hidden service ports. Please use as few as possible.\n" if $i-- < 0;
|
|
}
|
|
print O <<X;
|
|
|
|
#ControlPort 9051
|
|
#Log notice stdout
|
|
#DirReqStatistics 0
|
|
#SafeSocks 1
|
|
X
|
|
print O <<X if $c{_optional_tor_nodes_entry};
|
|
EntryNodes $c{_optional_tor_nodes_entry}
|
|
X
|
|
close O;
|
|
|
|
# ARCHETYPE
|
|
chdir "$sandbox/net/place" or die "Where is my net/place? $!";
|
|
|
|
## start of former archetype.pl
|
|
|
|
# generate psyced place models using combinations of archetype flags
|
|
|
|
my @opts, @predef, %map;
|
|
open(I, "archetype.gen") or die <<X;
|
|
|
|
$0: Cannot open archetype.gen in $sandbox/net/place.
|
|
|
|
X
|
|
while (<I>) {
|
|
if (m!define\s(\w+)\s*//\s\[(.)\]!) {
|
|
if ($2 eq '+') {
|
|
push @predef, $1;
|
|
} else {
|
|
$map{$2} = $1;
|
|
push(@opts, $2);
|
|
}
|
|
} elsif (/^#endif/) {
|
|
last;
|
|
}
|
|
}
|
|
close I;
|
|
print "Generating archetype place models...\n";
|
|
|
|
# print join("\n", @opts), "\n\n";
|
|
# print "$_\n" foreach ( %map );
|
|
|
|
open (O, ">../include/place.i") or die $!;
|
|
print O <<X;
|
|
// generated by '$0': place.i for place.gen
|
|
|
|
X
|
|
my $file = '';
|
|
foreach $o (@opts) {
|
|
print O <<X;
|
|
#ifdef $map{$o}
|
|
# define O$o "$o"
|
|
#else
|
|
# define O$o ""
|
|
#endif
|
|
|
|
X
|
|
$file .= " O$o";
|
|
}
|
|
print O <<X;
|
|
inherit NET_PATH "place/_"$file;
|
|
X
|
|
$predef = '';
|
|
foreach $p (@predef) {
|
|
$predef .= "#define $p\n";
|
|
}
|
|
|
|
# open(IG, ">.cvsignore") or print <<X;
|
|
#Warning: cannot create .cvsignore. Well, doesn't matter.
|
|
#X
|
|
# # funny how it likes to see itself in there
|
|
# print IG ".cvsignore\n";
|
|
|
|
my $bits = 1 + $#opts;
|
|
for ($v = 1 << $bits; $v;) {
|
|
$v--;
|
|
$f = '';
|
|
$model = '';
|
|
|
|
for ($i = 0; $i < $bits; $i++) {
|
|
if ($v & 1 << $i) {
|
|
my $o = $opts[$i];
|
|
$f .= $o;
|
|
$model .= "#define $map{$o}\n";
|
|
}
|
|
}
|
|
|
|
# special case: skip all exports without history
|
|
next if $f =~ /^e/;
|
|
# same special case is also handled in place.gen
|
|
|
|
printf " (%02d _%s)", $v, $f;
|
|
#print " ($v _$f)";
|
|
|
|
# print IG "_$f.c\n";
|
|
open (O, ">_$f.c") or die $!;
|
|
# proud and noisy.. for a week or two at least ;)
|
|
#echo loading model '_$f' generated by '$0'
|
|
print O <<X;
|
|
// model '_$f' generated by '$0'
|
|
|
|
#define ESSENTIALS
|
|
$model
|
|
#include "archetype.gen"
|
|
X
|
|
# used to output $predef but it's easier to
|
|
# have archetype.gen sort out ESSENTIALS
|
|
close O;
|
|
}
|
|
# close IG;
|
|
|
|
#print "\nModel creation completed successfully.\n";
|
|
print "\n";
|
|
|
|
## end of former archetype.pl
|
|
|
|
unless ($newbie) {
|
|
say "\nCaution: You may have to completely shut down and restart psyced\n";
|
|
say "to ensure the newly generated start-up scripts are actually used.\n";
|
|
}
|
|
|
|
# vim:ts=8
|