summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorcarlosg <carlosg>2006-11-27 16:36:33 +0000
committercarlosg <carlosg>2006-11-27 16:36:33 +0000
commitb392f28d7265474ec9ae1343fbd566920b629f60 (patch)
tree28270ab245a07586cd014664c451001cbeedd600
parent0da5a0dedd7319aa287c21b536eafb78d7c354d2 (diff)
2006-11-27 Carlos Garnacho <carlosg@gnome.org>
Merge c-dispatcher branch, adds a lightweight dispatcher which raises configuration modules on demand, reducing memory use during inactivity and allowing the development of modules in other languages than Perl. 2006-10-24 Carlos Garnacho <carlosg@gnome.org> * dispatcher/dispatcher.c: exit() on SIGTERM. 2006-10-24 Carlos Garnacho <carlosg@gnome.org> Continued work on the dispatcher, I think it's now feature complete enough to work. * StbObject.pm: base object for s-t-b services, does all initialization and common stuff. * GroupsConfig.pm, HostsConfig.pm, IfacesConfig.pm, NFSConfig.pm, NTPConfig.pm, SMBConfig.pm, ServicesConfig.pm, TimeConfig.pm, UsersConfig.pm: inherit from StbObject, keep message format in a variable to avoid duplicates. * Utils/Platform.pm: move DBus code to Platform.pm. * Platform.pm: added, new DBus object. * Utils/Backend.pm: ensure system and platform. * Init/Services.pm: code improvements for archlinux * dispatcher/dispatcher.c: Add license, make it raise it's own private session bus to spawn configuration modules, cache platform and return it when asked, create a copy of the message to pass around (seems to be necessary by design) * services/*: added, used to raise configuration modules. * configure.in, Makefile.am: added services directory stuff. 2006-10-13 Carlos Garnacho <carlosg@gnome.org> * dispatcher/dispatcher.c (daemonize): added, function to make the dispatcher become a daemon. 2006-10-12 Carlos Garnacho <carlosg@gnome.org> beginnings of a really lightweight dispatcher written in C, this way the modules will only be loaded when necessary, reducing memory usage and allowing to develop modules in other languages than Perl. * dispatcher/dispatcher.c, Makefile.am: added, first draft of the dispatcher, it already forwards messages and sends replies back and tries to raise modules in the session bus * Makefile.am: add the dispatcher directory. * configure.in: require GLib to build the dispatcher, maybe this dep could be dropped at some point in the future, if I don't feel too lazy... * Utils/Backend.pm: remove --no-daemon and --session-bus parameters, should be no longer needed. Add --disable-shutdown for testing purposes, as modules are supposed to shutdown automatically after some inactivity. Add --module parameter to raise a configuration module. * GroupsConfig.pm, HostsConfig.pm, IfacesConfig.pm, NFSConfig.pm, NTPConfig.pm, SMBConfig.pm, ServicesConfig.pm, TimeConfig.pm, UsersConfig.pm: create the DBus object by themselves. * SystemToolsBackends.pl.in: do not create all the DBus objects, just the one we want to raise, this way the script becomes a loader for services instead of a service itself.
-rw-r--r--ChangeLog72
-rw-r--r--GroupsConfig.pm23
-rw-r--r--HostsConfig.pm32
-rw-r--r--IfacesConfig.pm39
-rw-r--r--Makefile.am4
-rw-r--r--NFSConfig.pm22
-rw-r--r--NTPConfig.pm18
-rw-r--r--Platform.pm84
-rw-r--r--SMBConfig.pm23
-rw-r--r--ServicesConfig.pm23
-rw-r--r--StbObject.pm47
-rwxr-xr-xSystemToolsBackends.pl.in30
-rw-r--r--TimeConfig.pm17
-rw-r--r--UsersConfig.pm28
-rw-r--r--Utils/Backend.pm88
-rw-r--r--Utils/Platform.pm57
-rw-r--r--configure.in35
-rw-r--r--dispatcher/Makefile.am9
-rw-r--r--dispatcher/dispatcher.c307
-rw-r--r--services/Makefile.am30
-rw-r--r--services/org.freedesktop.SystemToolsBackends.GroupsConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.HostsConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.IfacesConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.NFSConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.NTPConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.Platform.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.SMBConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.ServicesConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.TimeConfig.service.in4
-rw-r--r--services/org.freedesktop.SystemToolsBackends.UsersConfig.service.in4
30 files changed, 797 insertions, 231 deletions
diff --git a/ChangeLog b/ChangeLog
index f288f5c..be5ae76 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,77 @@
2006-11-27 Carlos Garnacho <carlosg@gnome.org>
+ Merge c-dispatcher branch, adds a lightweight dispatcher which raises
+ configuration modules on demand, reducing memory use during inactivity
+ and allowing the development of modules in other languages than Perl.
+
+ 2006-10-24 Carlos Garnacho <carlosg@gnome.org>
+
+ * dispatcher/dispatcher.c: exit() on SIGTERM.
+
+ 2006-10-24 Carlos Garnacho <carlosg@gnome.org>
+
+ Continued work on the dispatcher, I think it's now feature complete
+ enough to work.
+
+ * StbObject.pm: base object for s-t-b services, does all
+ initialization and common stuff.
+
+ * GroupsConfig.pm, HostsConfig.pm, IfacesConfig.pm, NFSConfig.pm,
+ NTPConfig.pm, SMBConfig.pm, ServicesConfig.pm, TimeConfig.pm,
+ UsersConfig.pm: inherit from StbObject, keep message format in a
+ variable to avoid duplicates.
+
+ * Utils/Platform.pm: move DBus code to Platform.pm.
+ * Platform.pm: added, new DBus object.
+
+ * Utils/Backend.pm: ensure system and platform.
+
+ * Init/Services.pm: code improvements for archlinux
+
+ * dispatcher/dispatcher.c: Add license, make it raise it's own private
+ session bus to spawn configuration modules, cache platform and return
+ it when asked, create a copy of the message to pass around (seems to
+ be necessary by design)
+
+ * services/*: added, used to raise configuration modules.
+ * configure.in, Makefile.am: added services directory stuff.
+
+ 2006-10-13 Carlos Garnacho <carlosg@gnome.org>
+
+ * dispatcher/dispatcher.c (daemonize): added, function to make the
+ dispatcher become a daemon.
+
+ 2006-10-12 Carlos Garnacho <carlosg@gnome.org>
+
+ beginnings of a really lightweight dispatcher written in C, this way
+ the modules will only be loaded when necessary, reducing memory usage
+ and allowing to develop modules in other languages than Perl.
+
+ * dispatcher/dispatcher.c, Makefile.am: added, first draft of the
+ dispatcher, it already forwards messages and sends replies back and
+ tries to raise modules in the session bus
+
+ * Makefile.am: add the dispatcher directory.
+
+ * configure.in: require GLib to build the dispatcher, maybe this dep
+ could be dropped at some point in the future, if I don't feel too
+ lazy...
+
+ * Utils/Backend.pm: remove --no-daemon and --session-bus parameters,
+ should be no longer needed. Add --disable-shutdown for testing
+ purposes, as modules are supposed to shutdown automatically after some
+ inactivity. Add --module parameter to raise a configuration module.
+
+ * GroupsConfig.pm, HostsConfig.pm, IfacesConfig.pm, NFSConfig.pm,
+ NTPConfig.pm, SMBConfig.pm, ServicesConfig.pm, TimeConfig.pm,
+ UsersConfig.pm: create the DBus object by themselves.
+
+ * SystemToolsBackends.pl.in: do not create all the DBus objects, just
+ the one we want to raise, this way the script becomes a loader for
+ services instead of a service itself.
+
+2006-11-27 Carlos Garnacho <carlosg@gnome.org>
+
* Init/Services.pm: add some sanity checks.
2006-11-26 Carlos Garnacho <carlosg@gnome.org>
diff --git a/GroupsConfig.pm b/GroupsConfig.pm
index 650cd43..19b11d7 100644
--- a/GroupsConfig.pm
+++ b/GroupsConfig.pm
@@ -22,36 +22,36 @@
package GroupsConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
-use Utils::Backend;
use Users::Groups;
use Users::Users;
my $OBJECT_NAME = "GroupsConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", [ "struct", "uint32", "string", "string", "int32", [ "array", "string" ]]], "int32", "int32" ];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
- Utils::Monitor::monitor_files (&Users::Groups::get_files (),
- $self, $OBJECT_NAME, "changed");
+# Utils::Monitor::monitor_files (&Users::Groups::get_files (),
+# $self, $OBJECT_NAME, "changed");
return $self;
}
-dbus_method ("get", [], [[ "array", [ "struct", "uint32", "string", "string", "int32", [ "array", "string" ]]], "int32", "int32" ]);
-dbus_method ("set", [[ "array", [ "struct", "uint32", "string", "string", "int32", [ "array", "string" ]]], "int32", "int32" ], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
my $groups, $logindefs;
+ $self->SUPER::reset_counter ();
$groups = Users::Groups::get ();
$logindefs = &Users::Users::get_logindefs ();
@@ -62,8 +62,11 @@ sub get
sub set
{
my ($self, $config) = @_;
+ $self->SUPER::reset_counter ();
Users::Groups::set ($config);
}
+my $config = GroupsConfig->new ();
+
1;
diff --git a/HostsConfig.pm b/HostsConfig.pm
index 53cf877..811d363 100644
--- a/HostsConfig.pm
+++ b/HostsConfig.pm
@@ -22,18 +22,21 @@
package HostsConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
use Network::Hosts;
my $OBJECT_NAME = "HostsConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [ "string", "string",
+ [ "array", [ "struct", "string", [ "array", "string" ]]],
+ [ "array", "string" ],
+ [ "array", "string" ]];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
@@ -43,23 +46,17 @@ sub new
return $self;
}
-dbus_method ("get", [],
- [ "string", "string",
- [ "array", [ "struct", "string", [ "array", "string" ]]],
- [ "array", "string" ],
- [ "array", "string" ]]);
-dbus_method ("set",
- [ "string", "string",
- [ "array", [ "struct", "string", [ "array", "string" ]]],
- [ "array", "string" ],
- [ "array", "string" ]], []);
-
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
my ($hostname, $domainname);
+ $self->SUPER::reset_counter ();
+
+ print "quepapsapsapap\n";
($hostname, $domainname) = Network::Hosts::get_fqdn ();
@@ -72,6 +69,7 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
Network::Hosts::set_hosts ($config[2], $config[0], $config[1]);
Network::Hosts::set_dns ($config[3]);
@@ -79,4 +77,6 @@ sub set
Network::Hosts::set_fqdn ($config[0], $config[1]);
}
+my $config = HostsConfig->new ();
+
1;
diff --git a/IfacesConfig.pm b/IfacesConfig.pm
index 7439a2c..6f09b7b 100644
--- a/IfacesConfig.pm
+++ b/IfacesConfig.pm
@@ -22,19 +22,23 @@
package IfacesConfig;
-use Network::Ifaces;
-
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
+use Network::Ifaces;
my $OBJECT_NAME = "IfacesConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
+ [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string", "string", "int32", "string" ]],
+ [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
+ [ "array", [ "struct", "string", "int32", "int32", "string", "string" ]],
+ [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "int32", "int32", "string", "string", "int32", "int32", "int32", "int32" ]],
+ [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "string", "int32", "int32", "int32", "int32" ]]];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
@@ -44,26 +48,14 @@ sub new
return $self;
}
-dbus_method ("get", [],
- [[ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string", "string", "int32", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "int32", "int32", "string", "string", "int32", "int32", "int32", "int32" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "string", "int32", "int32", "int32", "int32" ]]]);
-dbus_method ("set",
- [[ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string", "string", "int32", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "int32", "string", "string", "string", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "int32", "int32", "string", "string", "int32", "int32", "int32", "int32" ]],
- [ "array", [ "struct", "string", "int32", "int32", "string", "string", "string", "string", "int32", "int32", "int32", "int32" ]]], []);
-
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
+ $self->SUPER::reset_counter ();
return &Network::Ifaces::get ();
}
@@ -71,9 +63,12 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
&Network::Ifaces::set ($config[0], $config[1], $config[2],
$config[3], $config[4], $config[5]);
}
+my $config = IfacesConfig->new ();
+
1;
diff --git a/Makefile.am b/Makefile.am
index 137ef08..3e4905b 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -2,10 +2,12 @@ if INTERNAL_NET_DBUS
net_dbus_SUBDIRS = Net-DBus
endif
-SUBDIRS = files Init Network Shares Time Users Utils $(net_dbus_SUBDIRS)
+SUBDIRS = dispatcher services files Init Network Shares Time Users Utils $(net_dbus_SUBDIRS)
modulesdir = $(scriptsdir)
modules_DATA = \
+ Platform.pm \
+ StbObject.pm \
GroupsConfig.pm \
HostsConfig.pm \
IfacesConfig.pm \
diff --git a/NFSConfig.pm b/NFSConfig.pm
index 583e92f..b8e2037 100644
--- a/NFSConfig.pm
+++ b/NFSConfig.pm
@@ -22,34 +22,35 @@
package NFSConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
use Shares::NFS;
my $OBJECT_NAME = "NFSConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32" ]]]]];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
- Utils::Monitor::monitor_files (&Shares::NFS::get_distro_nfs_file (),
- $self, $OBJECT_NAME, "changed");
+# Utils::Monitor::monitor_files (&Shares::NFS::get_distro_nfs_file (),
+# $self, $OBJECT_NAME, "changed");
return $self;
}
-dbus_method ("get", [], [[ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32" ]]]]]);
-dbus_method ("set", [[ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32" ]]]]], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
my ($shares);
+ $self->SUPER::reset_counter ();
$shares = &Shares::NFS::get ();
@@ -59,8 +60,11 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
&Shares::NFS::set (@config);
}
+my $config = NFSConfig->new ();
+
1;
diff --git a/NTPConfig.pm b/NTPConfig.pm
index ba9ec57..04bd39e 100644
--- a/NTPConfig.pm
+++ b/NTPConfig.pm
@@ -22,19 +22,19 @@
package NTPConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
use Utils::Backend;
use Time::NTP;
my $OBJECT_NAME = "NTPConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", "string" ]];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
@@ -44,13 +44,14 @@ sub new
return $self;
}
-dbus_method ("get", [], [[ "array", "string" ]]);
-dbus_method ("set", [[ "array", "string" ]], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
+ $self->SUPER::reset_counter ();
return &Time::NTP::get ();
}
@@ -58,8 +59,11 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
&Time::NTP::set (@config);
}
+my $config = NTPConfig->new ();
+
1;
diff --git a/Platform.pm b/Platform.pm
new file mode 100644
index 0000000..c2a2ef7
--- /dev/null
+++ b/Platform.pm
@@ -0,0 +1,84 @@
+#-*- Mode: perl; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+
+# DBus object for the Services config
+#
+# Copyright (C) 2005 Carlos Garnacho
+#
+# Authors: Carlos Garnacho Parro <carlosg@gnome.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU Library General Public License as published
+# by the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU Library General Public License for more details.
+#
+# You should have received a copy of the GNU Library General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
+
+package Platform;
+
+use base qw(Net::DBus::Object);
+use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX . ".Platform");
+use Utils::Platform;
+use Utils::Backend;
+
+my $OBJECT_NAME = "Platform";
+my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+
+dbus_method ("getPlatformList", [], [[ "array", [ "struct", "string", "string", "string", "string" ]]]);
+dbus_method ("getPlatform", [], [ "string" ]);
+dbus_method ("setPlatform", [ "string" ], []);
+
+sub new
+{
+ my $class = shift;
+ my $service = shift;
+ my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+
+ bless $self, $class;
+
+ &Utils::Platform::init ();
+ return $self;
+}
+
+sub getPlatformList
+{
+ my ($self) = @_;
+ my ($arr, $hash, $key);
+
+ $hash = &Utils::Platform::get_platform_info ();
+
+ foreach $key (keys %$hash)
+ {
+ push @$arr, [ $$hash{$key}[0],
+ $$hash{$key}[1],
+ $$hash{$key}[2],
+ $key ];
+ }
+
+ return $arr;
+}
+
+sub getPlatform
+{
+ return $Utils::Backend::tool{"platform"};
+}
+
+# A directive handler that sets the currently selected platform.
+sub setPlatform
+{
+ my ($self, $platform) = @_;
+
+ &Utils::Platform::set_platform ($platform);
+}
+
+my $bus = &Utils::Backend::get_bus ();
+my $service = $bus->export_service ($Utils::Backend::DBUS_PREFIX . ".$OBJECT_NAME");
+my $platforms_list = Platform->new ($service);
+
+1;
diff --git a/SMBConfig.pm b/SMBConfig.pm
index 743249c..f6f7cdd 100644
--- a/SMBConfig.pm
+++ b/SMBConfig.pm
@@ -22,35 +22,35 @@
package SMBConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
use Shares::SMB;
my $OBJECT_NAME = "SMBConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", [ "struct", "string", "string", "string", "int32", "int32", "int32", "int32" ]],
+ "string", "string", "int32", "string" ];
sub new
{
my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
- Utils::Monitor::monitor_files (&Shares::SMB::get_distro_smb_file (),
- $self, $OBJECT_NAME, "changed");
+# Utils::Monitor::monitor_files (&Shares::SMB::get_distro_smb_file (),
+# $self, $OBJECT_NAME, "changed");
return $self;
}
-dbus_method ("get", [], [[ "array", [ "struct", "string", "string", "string", "int32", "int32", "int32", "int32" ]],
- "string", "string", "int32", "string" ]);
-dbus_method ("set", [[ "array", [ "struct", "string", "string", "string", "int32", "int32", "int32", "int32" ]],
- "string", "string", "int32", "string" ], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
+ $self->SUPER::reset_counter ();
return &Shares::SMB::get ();
}
@@ -58,8 +58,11 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
&Shares::SMB::set (@config);
}
+my $config = SMBConfig->new ();
+
1;
diff --git a/ServicesConfig.pm b/ServicesConfig.pm
index d98cffc..04a394b 100644
--- a/ServicesConfig.pm
+++ b/ServicesConfig.pm
@@ -22,18 +22,20 @@
package ServicesConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
use Init::Services;
my $OBJECT_NAME = "ServicesConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", "string" ],
+ "string",
+ [ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32", "int32" ]]]]];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
@@ -43,18 +45,14 @@ sub new
return $self;
}
-dbus_method ("get", [],
- [[ "array", "string" ],
- "string",
- [ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32", "int32" ]]]]]);
-dbus_method ("set", [[ "array", "string" ],
- "string",
- [ "array", [ "struct", "string", [ "array", [ "struct", "string", "int32", "int32" ]]]]], []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
+ $self->SUPER::reset_counter ();
return (&Init::Services::get_runlevels (),
&Init::Services::get_default_runlevel (),
@@ -64,8 +62,11 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
&Init::Services::set ($config[2]);
}
+my $config = ServicesConfig->new ();
+
1;
diff --git a/StbObject.pm b/StbObject.pm
new file mode 100644
index 0000000..102c541
--- /dev/null
+++ b/StbObject.pm
@@ -0,0 +1,47 @@
+#-*- Mode: perl; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+#
+# Copyright (C) 2005 Carlos Garnacho
+#
+# Authors: Carlos Garnacho Parro <carlosg@gnome.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU Library General Public License as published
+# by the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU Library General Public License for more details.
+#
+# You should have received a copy of the GNU Library General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
+
+package StbObject;
+
+use base qw(Net::DBus::Object);
+use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
+
+sub new
+{
+ my $class = shift;
+ my $path = shift;
+ my $name = shift;
+
+ my $bus = &Utils::Backend::get_bus ();
+ my $service = $bus->export_service ($Utils::Backend::DBUS_PREFIX . ".$name");
+ my $self = $class->SUPER::new ($service, $path);
+
+ bless $self, $class;
+ &Utils::Backend::ensure_platform ();
+
+ return $self;
+}
+
+sub reset_counter
+{
+ &Utils::Backend::initialize_timer (\%Utils::Backend::tool);
+}
+
+1;
diff --git a/SystemToolsBackends.pl.in b/SystemToolsBackends.pl.in
index f49ea62..597ce5c 100755
--- a/SystemToolsBackends.pl.in
+++ b/SystemToolsBackends.pl.in
@@ -43,34 +43,8 @@ use Utils::Backend;
use Utils::Monitor;
use Utils::Platform;
-use SMBConfig;
-use NFSConfig;
-use UsersConfig;
-use GroupsConfig;
-use TimeConfig;
-use NTPConfig;
-use HostsConfig;
-use IfacesConfig;
-use ServicesConfig;
-
# Initialize tool
&Utils::Backend::init ($name, $version, $description, $directives, @ARGV);
-# Initialize bus
-my $bus = &Utils::Backend::get_bus ();
-my $service = $bus->export_service ($Utils::Backend::DBUS_PREFIX);
-
-#Initialize all objects
-my $platforms_list = Utils::Platform->new ($service);
-my $smb_config = SMBConfig->new ($service);
-my $nfs_config = NFSConfig->new ($service);
-my $users_config = UsersConfig->new ($service);
-my $groups_config = GroupsConfig->new ($service);
-my $time_config = TimeConfig->new ($service);
-my $ntp_config = NTPConfig->new ($service);
-my $hosts_config = HostsConfig->new ($service);
-my $ifaces_config = IfacesConfig->new ($service);
-my $services_config = ServicesConfig->new ($service);
-
-Utils::Monitor::init_file_monitor ();
-Net::DBus::Reactor->main->run ();
+require $Utils::Backend::tool{"module"};
+&Utils::Backend::run ();
diff --git a/TimeConfig.pm b/TimeConfig.pm
index 05d06e2..96ae840 100644
--- a/TimeConfig.pm
+++ b/TimeConfig.pm
@@ -22,19 +22,18 @@
package TimeConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
-use Utils::Backend;
use Time::TimeDate;
my $OBJECT_NAME = "TimeConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [ "int32", "int32", "int32", "int32", "int32", "int32", "string" ];
sub new
{
my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
@@ -44,14 +43,15 @@ sub new
return $self;
}
-dbus_method ("get", [], [ "int32", "int32", "int32", "int32", "int32", "int32", "string" ]);
-dbus_method ("set", [ "int32", "int32", "int32", "int32", "int32", "int32", "string" ], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
my $config;
+ $self->SUPER::reset_counter ();
return Time::TimeDate::get ();
}
@@ -59,8 +59,11 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
Time::TimeDate::set (@config);
}
+my $config = TimeConfig->new ();
+
1;
diff --git a/UsersConfig.pm b/UsersConfig.pm
index 92054c2..505adad 100644
--- a/UsersConfig.pm
+++ b/UsersConfig.pm
@@ -22,40 +22,37 @@
package UsersConfig;
-use base qw(Net::DBus::Object);
+use base qw(StbObject);
use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX);
-use Utils::Backend;
use Users::Users;
use Users::Shells;
my $OBJECT_NAME = "UsersConfig";
my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
+my $format = [[ "array", [ "struct", "uint32", "string", "string", "int32", "int32", [ "array", "string"], "string", "string" ]],
+ ["array", "string" ], "int32", "int32", "int32", "string", "string", "int32" ];
sub new
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
+ my $class = shift;
+ my $self = $class->SUPER::new ($OBJECT_PATH, $OBJECT_NAME);
bless $self, $class;
- Utils::Monitor::monitor_files (&Users::Users::get_files (),
- $self, $OBJECT_NAME, "changed");
+# Utils::Monitor::monitor_files (&Users::Users::get_files (),
+# $self, $OBJECT_NAME, "changed");
return $self;
}
-dbus_method ("get", [],
- [[ "array", [ "struct", "uint32", "string", "string", "int32", "int32", [ "array", "string"], "string", "string" ]],
- ["array", "string" ], "int32", "int32", "int32", "string", "string", "int32" ]);
-dbus_method ("set",
- [[ "array", [ "struct", "uint32", "string", "string", "int32", "int32", [ "array", "string"], "string", "string" ]],
- ["array", "string" ], "int32", "int32", "int32", "string", "string", "int32" ], []);
-dbus_signal ("changed", []);
+dbus_method ("get", [], $format);
+dbus_method ("set", $format, []);
+#dbus_signal ("changed", []);
sub get
{
my ($self) = @_;
my $logindefs, $users, $use_md5, $shells;
+ $self->SUPER::reset_counter ();
$use_md5 = &Users::Users::get_use_md5 ();
$logindefs = &Users::Users::get_logindefs ();
@@ -70,6 +67,7 @@ sub get
sub set
{
my ($self, @config) = @_;
+ $self->SUPER::reset_counter ();
Users::Users::set ($config[0]);
Users::Shells::set ($config[1]);
@@ -80,4 +78,6 @@ sub set
"group" => $config[7]});
}
+my $config = UsersConfig->new ();
+
1;
diff --git a/Utils/Backend.pm b/Utils/Backend.pm
index 98810b3..86f6122 100644
--- a/Utils/Backend.pm
+++ b/Utils/Backend.pm
@@ -113,8 +113,6 @@ end_of_usage_generic;
Modifiers (specify any combination of these):
- -no-daemon Does not daemonize the backend
-
--platform <name-ver> Overrides the detection of your platform\'s
name and version, e.g. redhat-6.2. Use with care. See the
documentation for a full list of supported platforms.
@@ -130,8 +128,6 @@ end_of_usage_generic;
-v --verbose Prints human-readable diagnostic messages to standard
error.
- --session-bus Makes the backends to use the session bus.
-
end_of_usage_generic;
$usage{"get"} =<< "end_of_usage_generic;";
@@ -204,12 +200,16 @@ sub set_with_param
$$tool{$arg_name} = $value;
}
-sub set_no_daemon
+sub set_disable_shutdown
{
my ($tool) = @_;
+ &set_with_param ($tool, "no-shutdown", 1);
+}
- &set_with_param ($tool, "no-daemon", 1);
- $no_daemon = 1;
+sub set_module
+{
+ my ($tool, $module) = @_;
+ &set_with_param ($tool, "module", "$module.pm");
}
sub set_prefix
@@ -223,16 +223,7 @@ sub set_prefix
sub set_dist
{
my ($tool, $dist) = @_;
-
- &Utils::Platform::set_platform ($dist);
-}
-
-sub set_session_bus
-{
- my ($tool) = @_;
-
- &set_with_param ($tool, "session-bus", 1);
- $session_bus = 1;
+ &set_with_param ($tool, "platform", $dist);
}
sub is_backend
@@ -249,6 +240,19 @@ sub is_backend
return 0;
}
+sub ensure_platform
+{
+ if (!$$tool{"platform"})
+ {
+ my $bus = Net::DBus->system;
+ my $service = $bus->get_service("org.freedesktop.SystemToolsBackends");
+ my $obj = $service->get_object ("/org/freedesktop/SystemToolsBackends/Platform");
+ my $platform = $obj->getPlatform ();
+
+ &set_dist (\%tool, $platform) if ($platform);
+ }
+}
+
sub init
{
my ($name, $version, $description, $directives, @args) = @_;
@@ -271,11 +275,11 @@ sub init
while ($arg = shift (@args))
{
if ($arg eq "--help" || $arg eq "-h") { &print_usage (\%tool, 0); }
- elsif ($arg eq "--no-daemon" || $arg eq "-n") { &set_no_daemon (\%tool); }
+ elsif ($arg eq "--module" || $arg eq "-m") { &set_module (\%tool, shift @args); }
elsif ($arg eq "--version") { &print_version (\%tool, 0); }
elsif ($arg eq "--prefix" || $arg eq "-p") { &set_prefix (\%tool, shift @args); }
elsif ($arg eq "--platform") { &set_dist (\%tool, shift @args); }
- elsif ($arg eq "--session-bus") { &set_session_bus (\%tool); }
+ elsif ($arg eq "--disable-shutdown") { &set_disable_shutdown (\%tool); }
elsif ($arg eq "--verbose" || $arg eq "-v")
{
$tool{"do_verbose"} = $do_verbose = 1;
@@ -293,40 +297,42 @@ sub init
}
}
- if (!$no_daemon)
- {
- &daemonize ();
- }
-
# Set up subsystems.
&Utils::Report::begin ();
+ &Utils::Platform::get_system ();
+ &initialize_timer (\%tool);
return \%tool;
}
-sub daemonize
+sub get_bus
{
- chdir '/' or die "Can't chdir to /: $!";
- umask 0;
- open STDIN, '/dev/null' or die "Can't read /dev/null: $!";
- open STDOUT, '>/dev/null' or die "Can't write to /dev/null: $!";
- open STDERR, '>/dev/null' or die "Can't write to /dev/null: $!";
-
- defined (my $pid = fork) or die "Can't fork: $!";
- exit (0) if $pid;
+ return Net::DBus->session
+}
- setsid or die "Can't start a new session: $!";
+sub run
+{
+ Net::DBus::Reactor->main->run ();
+}
- # write pid file
- open (PIDFILE, ">$main::localstatedir/run/system-tools-backends.pid");
- print PIDFILE $$;
- close (PIDFILE);
+sub shutdown
+{
+ # exit the main loop
+ Net::DBus::Reactor->main->shutdown ();
}
-sub get_bus
+sub initialize_timer
{
- return Net::DBus->session if ($session_bus);
- return Net::DBus->system;
+ my ($tool) = @_;
+
+ if (!$$tool{"no-shutdown"})
+ {
+ # remove previous timer
+ Net::DBus::Reactor->main->remove_timeout ($$tool{"timer"}) if ($$tool {"timer"});
+
+ #wait three minutes until shutdown
+ $$tool{"timer"} = Net::DBus::Reactor->main->add_timeout (180000, Net::DBus::Callback->new(method => \&shutdown));
+ }
}
1;
diff --git a/Utils/Platform.pm b/Utils/Platform.pm
index e5c5cd9..989fb19 100644
--- a/Utils/Platform.pm
+++ b/Utils/Platform.pm
@@ -24,21 +24,10 @@
package Utils::Platform;
-use Utils::XML;
use Utils::Parse;
use Utils::Backend;
use Utils::File;
-
-use base qw(Net::DBus::Object);
-use Net::DBus::Exporter ($Utils::Backend::DBUS_PREFIX . ".Platform");
-
-my $OBJECT_NAME = "Platform";
-my $OBJECT_PATH = "$Utils::Backend::DBUS_PATH/$OBJECT_NAME";
-
-dbus_method ("getPlatformList", [], [[ "array", [ "struct", "string", "string", "string", "string" ]]]);
-dbus_method ("getPlatform", [], [ "string" ]);
-dbus_method ("setPlatform", [ "string" ], []);
-dbus_signal ("noPlatformDetected", []);
+use Utils::Replace;
# --- System guessing --- #
@@ -105,6 +94,11 @@ my $PLATFORM_INFO = {
"yellowdog-4.1" => [ "Yellow Dog Linux", "4.1", "Sagitta" ],
};
+sub get_platform_info
+{
+ return $PLATFORM_INFO;
+}
+
sub ensure_distro_map
{
my ($distro) = @_;
@@ -320,7 +314,6 @@ sub set_platform
my ($platform) = @_;
my ($p);
-
if (&ensure_platform ($platform))
{
$platform = &ensure_distro_map ($platform);
@@ -433,13 +426,8 @@ sub cache_platform
&Utils::Replace::set_first_line ($file, $gst_dist);
}
-sub new
+sub init
{
- my $class = shift;
- my $service = shift;
- my $self = $class->SUPER::new ($service, $OBJECT_PATH);
-
- bless $self, $class;
&get_system ();
if (!&get_cached_platform ())
@@ -447,35 +435,6 @@ sub new
&guess ($self) if !$Utils::Backend::tool{"platform"};
&cache_platform ();
}
-
- return $self;
-}
-
-sub getPlatformList
-{
- my ($self) = @_;
- my ($arr, $key);
-
- foreach $key (keys %$PLATFORM_INFO)
- {
- push @$arr, [ $$PLATFORM_INFO{$key}[0],
- $$PLATFORM_INFO{$key}[1],
- $$PLATFORM_INFO{$key}[2],
- $key ];
- }
-
- return $arr;
}
-sub getPlatform
-{
- return $Utils::Backend::tool{"platform"};
-}
-
-# A directive handler that sets the currently selected platform.
-sub setPlatform
-{
- my ($self, $platform) = @_;
-
- &set_platform ($platform);
-}
+1;
diff --git a/configure.in b/configure.in
index 96cd96c..9908bab 100644
--- a/configure.in
+++ b/configure.in
@@ -8,6 +8,9 @@ AC_CONFIG_HEADERS(config.h)
AM_INIT_AUTOMAKE(AC_PACKAGE_NAME, AC_PACKAGE_VERSION)
AC_PROG_LIBTOOL
+DBUS_REQUIRED=0.35
+GLIB_REQUIRED=2.4.0
+
dnl get prefix in $prefix, yes, this sucks
if test "x$prefix" = "xNONE"; then
prefix=$ac_default_prefix;
@@ -97,6 +100,20 @@ if test -z "$PERL_PATH"; then
AC_MSG_ERROR([perl not found, required for SystemToolsBackends])
fi
+dnl check for DBus
+PKG_CHECK_MODULES([DBUS], [dbus-1 >= $DBUS_REQUIRED])
+AC_SUBST([DBUS_CFLAGS])
+AC_SUBST([DBUS_LIBS])
+
+dnl check for the dispatcher deps
+PKG_CHECK_MODULES(DISPATCHER, [
+ dbus-glib-1 >= $DBUS_REQUIRED
+ glib-2.0 >= $GLIB_REQUIRED
+ ])
+DISPATCHER_CFLAGS="-DDBUS_API_SUBJECT_TO_CHANGE $DISPATCHER_CFLAGS"
+AC_SUBST(DISPATCHER_LIBS)
+AC_SUBST(DISPATCHER_CFLAGS)
+
dnl check for Net::DBus
AC_MSG_CHECKING([for Net::DBus])
if `$PERL_PATH -e "use lib '$netdbusdir'; require Net::DBus" 2>/dev/null`; then
@@ -104,14 +121,8 @@ if `$PERL_PATH -e "use lib '$netdbusdir'; require Net::DBus" 2>/dev/null`; then
internalnetdbus=no
else
AC_MSG_RESULT([missing, going for internal copy])
- DBUS_REQUIRED=0.35
- PKG_CHECK_MODULES([DBUS],[dbus-1 >= $DBUS_REQUIRED])
- AC_SUBST([DBUS_CFLAGS])
- AC_SUBST([DBUS_LIBS])
-
netdbusdir="${modulesdir}/lib/perl"
AC_SUBST(netdbusdir)
-
internalnetdbus=yes
fi
@@ -120,6 +131,7 @@ AM_CONDITIONAL(INTERNAL_NET_DBUS, test x$internalnetdbus = xyes)
AC_OUTPUT([
Makefile
system-tools-backends-2.0.pc
+dispatcher/Makefile
files/Makefile
Init/Makefile
Network/Makefile
@@ -129,6 +141,17 @@ Users/Makefile
Utils/Makefile
SystemToolsBackends.pl
test-backends
+services/Makefile
+services/org.freedesktop.SystemToolsBackends.GroupsConfig.service
+services/org.freedesktop.SystemToolsBackends.HostsConfig.service
+services/org.freedesktop.SystemToolsBackends.IfacesConfig.service
+services/org.freedesktop.SystemToolsBackends.NFSConfig.service
+services/org.freedesktop.SystemToolsBackends.NTPConfig.service
+services/org.freedesktop.SystemToolsBackends.Platform.service
+services/org.freedesktop.SystemToolsBackends.ServicesConfig.service
+services/org.freedesktop.SystemToolsBackends.SMBConfig.service
+services/org.freedesktop.SystemToolsBackends.TimeConfig.service
+services/org.freedesktop.SystemToolsBackends.UsersConfig.service
org.freedesktop.SystemToolsBackends.service
system-tools-backends.conf
Net-DBus/Makefile
diff --git a/dispatcher/Makefile.am b/dispatcher/Makefile.am
new file mode 100644
index 0000000..871e6fa
--- /dev/null
+++ b/dispatcher/Makefile.am
@@ -0,0 +1,9 @@
+INCLUDES = \
+ -Wall \
+ $(DISPATCHER_CFLAGS)
+
+bin_PROGRAMS = system-tools-backends
+
+system_tools_backends_LDADD = $(DISPATCHER_LIBS)
+system_tools_backends_SOURCES = \
+ dispatcher.c
diff --git a/dispatcher/dispatcher.c b/dispatcher/dispatcher.c
new file mode 100644
index 0000000..136f8c9
--- /dev/null
+++ b/dispatcher/dispatcher.c
@@ -0,0 +1,307 @@
+/* -*- Mode: C; c-file-style: "gnu"; tab-width: 8 -*- */
+/* Copyright (C) 2006 Carlos Garnacho
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * Authors: Carlos Garnacho Parro <carlosg@gnome.org>
+ */
+
+#include <glib.h>
+#include <glib-object.h>
+#include <dbus/dbus.h>
+#include <dbus/dbus-glib-lowlevel.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <signal.h>
+
+#define DBUS_ADDRESS_ENVVAR "DBUS_SESSION_BUS_ADDRESS"
+#define DBUS_INTERFACE_STB "org.freedesktop.SystemToolsBackends"
+#define DBUS_INTERFACE_STB_PLATFORM "org.freedesktop.SystemToolsBackends.Platform"
+
+/* FIXME: should be inside an object */
+static GPid bus_pid = 0;
+static guint watch_id = 0;
+static gchar *platform = NULL;
+
+typedef struct {
+ DBusConnection *connection;
+ gchar *destination;
+ gint serial;
+} AsyncData;
+
+static void
+async_data_free (AsyncData *data)
+{
+ dbus_connection_unref (data->connection);
+ g_free (data->destination);
+ g_free (data);
+}
+
+static void
+retrieve_platform (DBusMessage *message)
+{
+ DBusMessageIter iter;
+ const gchar *str;
+
+ dbus_message_iter_init (message, &iter);
+ dbus_message_iter_get_basic (&iter, &str);
+
+ if (str && *str)
+ platform = g_strdup (str);
+}
+
+static void
+dispatch_reply (DBusPendingCall *pending_call,
+ gpointer data)
+{
+ DBusMessage *reply;
+ AsyncData *async_data;
+
+ reply = dbus_pending_call_steal_reply (pending_call);
+ async_data = (AsyncData *) data;
+
+ /* get the platform if necessary */
+ if (dbus_message_has_interface (reply, DBUS_INTERFACE_STB_PLATFORM) &&
+ dbus_message_has_member (reply, "getPlatform") && !platform)
+ retrieve_platform (reply);
+
+ /* send the reply back */
+ dbus_message_set_destination (reply, async_data->destination);
+ dbus_message_set_reply_serial (reply, async_data->serial);
+ dbus_connection_send (async_data->connection, reply, NULL);
+
+ dbus_message_unref (reply);
+}
+
+static gchar*
+get_destination (DBusMessage *message)
+{
+ gchar **arr, *destination;
+
+ if (!dbus_message_get_path_decomposed (message, &arr))
+ return NULL;
+
+ destination = g_strdup_printf (DBUS_INTERFACE_STB ".%s", arr[3]);
+ dbus_free_string_array (arr);
+
+ return destination;
+}
+
+static void
+dispatch_stb_message (DBusConnection *connection,
+ DBusConnection *session_connection,
+ DBusMessage *message)
+{
+ DBusMessage *copy;
+ DBusPendingCall *pending_call;
+ AsyncData *async_data;
+ gchar *destination;
+
+ if (dbus_message_has_interface (message, DBUS_INTERFACE_STB_PLATFORM))
+ {
+ if (dbus_message_has_member (message, "getPlatform") && platform)
+ {
+ DBusMessage *reply;
+ DBusMessageIter iter;
+
+ /* create a reply with the stored platform */
+ reply = dbus_message_new_method_return (message);
+ dbus_message_iter_init_append (reply, &iter);
+ dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &platform);
+
+ dbus_connection_send (connection, reply, NULL);
+ dbus_message_unref (reply);
+
+ return;
+ }
+ else if (dbus_message_has_member (message, "setPlatform"))
+ retrieve_platform (message);
+ }
+
+ destination = get_destination (message);
+ copy = dbus_message_copy (message);
+
+ /* there's something wrong with the message */
+ if (!destination)
+ return;
+
+ /* forward the message to the corresponding service */
+ dbus_message_set_destination (copy, destination);
+ dbus_connection_send_with_reply (session_connection, copy, &pending_call, -1);
+
+ if (pending_call)
+ {
+ async_data = g_new0 (AsyncData, 1);
+ async_data->connection = dbus_connection_ref (connection);
+ async_data->destination = g_strdup (dbus_message_get_sender (message));
+ async_data->serial = dbus_message_get_serial (message);
+
+ dbus_pending_call_set_notify (pending_call, dispatch_reply, async_data, (DBusFreeFunction) async_data_free);
+ dbus_pending_call_unref (pending_call);
+ }
+
+ g_free (destination);
+ dbus_message_unref (copy);
+}
+
+static DBusHandlerResult
+dispatcher_filter_func (DBusConnection *connection,
+ DBusMessage *message,
+ void *data)
+{
+ DBusConnection *session_connection = (DBusConnection *) data;
+
+ if (dbus_message_is_signal (message, DBUS_INTERFACE_LOCAL, "Disconnected"))
+ {
+ /* FIXME: handle Disconnect */
+ }
+ else if (dbus_message_is_signal (message, DBUS_INTERFACE_DBUS, "NameOwnerChanged"))
+ {
+ /* FIXME: handle NameOwnerChanged */
+ }
+ else if (dbus_message_has_interface (message, DBUS_INTERFACE_INTROSPECTABLE) ||
+ dbus_message_has_interface (message, DBUS_INTERFACE_STB) ||
+ dbus_message_has_interface (message, DBUS_INTERFACE_STB_PLATFORM))
+ dispatch_stb_message (connection, session_connection, message);
+
+ return DBUS_HANDLER_RESULT_HANDLED;
+}
+
+static void
+daemonize (void)
+{
+ int dev_null_fd, pidfile_fd;
+ gchar *str;
+
+ if (!getenv ("STB_NO_DAEMON"))
+ {
+ dev_null_fd = open ("/dev/null", O_RDWR);
+
+ dup2 (dev_null_fd, 0);
+ dup2 (dev_null_fd, 1);
+ dup2 (dev_null_fd, 2);
+
+ if (fork () != 0)
+ exit (0);
+
+ setsid ();
+
+ if ((pidfile_fd = open ("/var/run/system-tools-backends.pid", O_WRONLY)) != -1)
+ {
+ str = g_strdup_printf ("%d", getpid ());
+ write (pidfile_fd, str, strlen (str));
+ g_free (str);
+ }
+ }
+}
+
+static void
+on_bus_term (GPid pid,
+ gint status,
+ gpointer data)
+{
+ g_spawn_close_pid (pid);
+ bus_pid = 0;
+
+ /* if the bus dies, we screwed up */
+ g_critical ("Can't live without bus.");
+ g_assert_not_reached ();
+}
+
+static DBusConnection*
+get_private_bus (void)
+{
+ DBusConnection *connection = NULL;
+
+ if (!bus_pid)
+ {
+ /* spawn private bus */
+ static gchar *argv[] = { "dbus-daemon", "--session", "--print-address", "--nofork", NULL };
+ gint output_fd;
+ gchar str[300], *envvar;
+
+ if (!g_spawn_async_with_pipes (NULL, argv, NULL,
+ G_SPAWN_SEARCH_PATH | G_SPAWN_DO_NOT_REAP_CHILD,
+ NULL, NULL, &bus_pid,
+ NULL, &output_fd, NULL, NULL))
+ return NULL;
+
+ watch_id = g_child_watch_add (bus_pid, on_bus_term, NULL);
+ read (output_fd, str, sizeof (str));
+ str[strlen(str) - 1] = '\0';
+
+ envvar = g_strdup_printf (DBUS_ADDRESS_ENVVAR "=%s", str);
+ putenv (envvar);
+
+ /* get a connection with the newly created bus */
+ connection = dbus_bus_get (DBUS_BUS_SESSION, NULL);
+ }
+
+ return connection;
+}
+
+void
+on_sigterm (gint signal)
+{
+ /* terminate the private bus */
+ if (bus_pid)
+ {
+ g_source_remove (watch_id);
+ kill (bus_pid, SIGTERM);
+ }
+
+ exit (0);
+}
+
+int
+main (int argc, char *argv[])
+{
+ DBusConnection *connection, *session_connection;
+ GMainLoop *main_loop;
+ DBusError error;
+
+ /* Currently not necessary, we're not using objects */
+ /* g_type_init (); */
+ dbus_error_init (&error);
+
+ daemonize ();
+ signal (SIGTERM, on_sigterm);
+
+ session_connection = get_private_bus ();
+ connection = dbus_bus_get (DBUS_BUS_SYSTEM, &error);
+
+ if (!session_connection || !connection)
+ exit (-1);
+
+ dbus_connection_set_exit_on_disconnect (connection, FALSE);
+ dbus_connection_set_exit_on_disconnect (session_connection, FALSE);
+
+ dbus_bus_request_name (connection, DBUS_INTERFACE_STB, 0, &error);
+ dbus_connection_add_filter (connection, dispatcher_filter_func, session_connection, NULL);
+
+ dbus_connection_setup_with_g_main (connection, NULL);
+ dbus_connection_setup_with_g_main (session_connection, NULL);
+
+ /* FIXME: error checking */
+
+ main_loop = g_main_loop_new (NULL, FALSE);
+ g_main_loop_run (main_loop);
+
+ return 0;
+}
diff --git a/services/Makefile.am b/services/Makefile.am
new file mode 100644
index 0000000..1a096c9
--- /dev/null
+++ b/services/Makefile.am
@@ -0,0 +1,30 @@
+services_in = \
+ org.freedesktop.SystemToolsBackends.GroupsConfig.service.in \
+ org.freedesktop.SystemToolsBackends.HostsConfig.service.in \
+ org.freedesktop.SystemToolsBackends.IfacesConfig.service.in \
+ org.freedesktop.SystemToolsBackends.NFSConfig.service.in \
+ org.freedesktop.SystemToolsBackends.NTPConfig.service.in \
+ org.freedesktop.SystemToolsBackends.Platform.service.in \
+ org.freedesktop.SystemToolsBackends.ServicesConfig.service.in \
+ org.freedesktop.SystemToolsBackends.SMBConfig.service.in \
+ org.freedesktop.SystemToolsBackends.TimeConfig.service.in \
+ org.freedesktop.SystemToolsBackends.UsersConfig.service.in
+
+services = \
+ org.freedesktop.SystemToolsBackends.GroupsConfig.service \
+ org.freedesktop.SystemToolsBackends.HostsConfig.service \
+ org.freedesktop.SystemToolsBackends.IfacesConfig.service \
+ org.freedesktop.SystemToolsBackends.NFSConfig.service \
+ org.freedesktop.SystemToolsBackends.NTPConfig.service \
+ org.freedesktop.SystemToolsBackends.Platform.service \
+ org.freedesktop.SystemToolsBackends.ServicesConfig.service \
+ org.freedesktop.SystemToolsBackends.SMBConfig.service \
+ org.freedesktop.SystemToolsBackends.TimeConfig.service \
+ org.freedesktop.SystemToolsBackends.UsersConfig.service
+
+EXTRA_DIST = $(services_in)
+CLEANFILES = $(services)
+
+# Dbus service files
+servicedir = $(DBUS_SERVICES_DIR)
+service_DATA = $(services)
diff --git a/services/org.freedesktop.SystemToolsBackends.GroupsConfig.service.in b/services/org.freedesktop.SystemToolsBackends.GroupsConfig.service.in
new file mode 100644
index 0000000..4b2a34a
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.GroupsConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.GroupsConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m GroupsConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.HostsConfig.service.in b/services/org.freedesktop.SystemToolsBackends.HostsConfig.service.in
new file mode 100644
index 0000000..3173e7d
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.HostsConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.HostsConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m HostsConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.IfacesConfig.service.in b/services/org.freedesktop.SystemToolsBackends.IfacesConfig.service.in
new file mode 100644
index 0000000..1f46756
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.IfacesConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.IfacesConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m IfacesConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.NFSConfig.service.in b/services/org.freedesktop.SystemToolsBackends.NFSConfig.service.in
new file mode 100644
index 0000000..1bd106b
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.NFSConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.NFSConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m NFSConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.NTPConfig.service.in b/services/org.freedesktop.SystemToolsBackends.NTPConfig.service.in
new file mode 100644
index 0000000..35c1aa3
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.NTPConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.NTPConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m NTPConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.Platform.service.in b/services/org.freedesktop.SystemToolsBackends.Platform.service.in
new file mode 100644
index 0000000..05dcca1
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.Platform.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.Platform
+Exec=@scriptsdir@/SystemToolsBackends.pl -m Platform
+
diff --git a/services/org.freedesktop.SystemToolsBackends.SMBConfig.service.in b/services/org.freedesktop.SystemToolsBackends.SMBConfig.service.in
new file mode 100644
index 0000000..3645543
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.SMBConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.SMBConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m SMBConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.ServicesConfig.service.in b/services/org.freedesktop.SystemToolsBackends.ServicesConfig.service.in
new file mode 100644
index 0000000..0dbfb89
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.ServicesConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.ServicesConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m ServicesConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.TimeConfig.service.in b/services/org.freedesktop.SystemToolsBackends.TimeConfig.service.in
new file mode 100644
index 0000000..f6b1e07
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.TimeConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.TimeConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m TimeConfig
+
diff --git a/services/org.freedesktop.SystemToolsBackends.UsersConfig.service.in b/services/org.freedesktop.SystemToolsBackends.UsersConfig.service.in
new file mode 100644
index 0000000..fbf692a
--- /dev/null
+++ b/services/org.freedesktop.SystemToolsBackends.UsersConfig.service.in
@@ -0,0 +1,4 @@
+[D-BUS Service]
+Name=org.freedesktop.SystemToolsBackends.UsersConfig
+Exec=@scriptsdir@/SystemToolsBackends.pl -m UsersConfig
+