]> pilppa.com Git - libplpha.git/commitdiff
initial version
authorMika Laitio <lamikr@pilppa.org>
Sat, 2 Oct 2010 10:26:24 +0000 (13:26 +0300)
committerMika Laitio <lamikr@pilppa.org>
Sat, 2 Oct 2010 10:26:24 +0000 (13:26 +0300)
30 files changed:
.cproject [new file with mode: 0644]
.project [new file with mode: 0644]
AUTHORS [new file with mode: 0644]
COPYING [new file with mode: 0644]
ChangeLog [new file with mode: 0644]
INSTALL [new file with mode: 0644]
LICENSE.txt [new file with mode: 0644]
Makefile.am [new file with mode: 0644]
NEWS [new file with mode: 0644]
README [new file with mode: 0644]
autobuild.sh [new file with mode: 0755]
configure.ac [new file with mode: 0644]
data/configs/Makefile.am [new file with mode: 0644]
data/configs/test_client.service.in [new file with mode: 0644]
data/configs/test_client2.service.in [new file with mode: 0644]
libplpha.pc.in [new file with mode: 0644]
src/Makefile.am [new file with mode: 0644]
src/common.h [new file with mode: 0644]
src/launcher.c [new file with mode: 0644]
src/launcher.h [new file with mode: 0644]
src/process_info.h [new file with mode: 0644]
src/process_listener.c [new file with mode: 0644]
src/process_listener.h [new file with mode: 0644]
src/process_parser.c [new file with mode: 0644]
src/process_parser.h [new file with mode: 0644]
src/servicedir_listener.c [new file with mode: 0644]
src/servicedir_listener.h [new file with mode: 0644]
src_test/Makefile.am [new file with mode: 0644]
src_test/test_client.c [new file with mode: 0644]
src_test/test_ha.c [new file with mode: 0644]

diff --git a/.cproject b/.cproject
new file mode 100644 (file)
index 0000000..3f7ebe4
--- /dev/null
+++ b/.cproject
@@ -0,0 +1,210 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<?fileVersion 4.0.0?>
+
+<cproject storage_type_id="org.eclipse.cdt.core.XmlProjectDescriptionStorage">
+<storageModule moduleId="org.eclipse.cdt.core.settings">
+<cconfiguration id="cdt.managedbuild.toolchain.gnu.cross.base.1196063785">
+<storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="cdt.managedbuild.toolchain.gnu.cross.base.1196063785" moduleId="org.eclipse.cdt.core.settings" name="Cross GCC">
+<externalSettings/>
+<extensions>
+<extension id="org.eclipse.cdt.core.ELF" point="org.eclipse.cdt.core.BinaryParser"/>
+<extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+<extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+<extension id="org.eclipse.cdt.core.MakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+</extensions>
+</storageModule>
+<storageModule moduleId="cdtBuildSystem" version="4.0.0">
+<configuration artifactName="libplpha2" buildProperties="" description="" id="cdt.managedbuild.toolchain.gnu.cross.base.1196063785" name="Cross GCC" parent="org.eclipse.cdt.build.core.emptycfg">
+<folderInfo id="cdt.managedbuild.toolchain.gnu.cross.base.1196063785.592276132" name="/" resourcePath="">
+<toolChain id="cdt.managedbuild.toolchain.gnu.cross.base.256416209" name="cdt.managedbuild.toolchain.gnu.cross.base" superClass="cdt.managedbuild.toolchain.gnu.cross.base">
+<option id="cdt.managedbuild.option.gnu.cross.prefix.2096487669" name="Prefix" superClass="cdt.managedbuild.option.gnu.cross.prefix"/>
+<option id="cdt.managedbuild.option.gnu.cross.path.1988795369" name="Path" superClass="cdt.managedbuild.option.gnu.cross.path"/>
+<targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.ELF" id="cdt.managedbuild.targetPlatform.gnu.cross.312022990" isAbstract="false" osList="all" superClass="cdt.managedbuild.targetPlatform.gnu.cross"/>
+<builder id="cdt.managedbuild.toolchain.gnu.cross.base.1196063785.1138409088" keepEnvironmentInBuildfile="false" managedBuildOn="false" name="Gnu Make Builder" superClass="org.eclipse.cdt.build.core.settings.default.builder"/>
+<tool id="cdt.managedbuild.tool.gnu.cross.cpp.compiler.934785405" name="Cross G++ Compiler" superClass="cdt.managedbuild.tool.gnu.cross.cpp.compiler">
+<inputType id="cdt.managedbuild.tool.gnu.cpp.compiler.input.113975571" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.input"/>
+</tool>
+<tool id="cdt.managedbuild.tool.gnu.cross.cpp.linker.1919764139" name="Cross G++ Linker" superClass="cdt.managedbuild.tool.gnu.cross.cpp.linker">
+<inputType id="cdt.managedbuild.tool.gnu.cpp.linker.input.157916714" superClass="cdt.managedbuild.tool.gnu.cpp.linker.input">
+<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
+<additionalInput kind="additionalinput" paths="$(LIBS)"/>
+</inputType>
+</tool>
+</toolChain>
+</folderInfo>
+</configuration>
+</storageModule>
+<storageModule moduleId="org.eclipse.cdt.core.externalSettings"/>
+<storageModule moduleId="org.eclipse.cdt.internal.ui.text.commentOwnerProjectMappings"/>
+<storageModule moduleId="scannerConfiguration">
+<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="org.eclipse.cdt.make.core.GCCStandardMakePerProjectProfile"/>
+<profile id="org.eclipse.cdt.make.core.GCCStandardMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.make.core.GCCStandardMakePerFileProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="makefileGenerator">
+<runAction arguments="-f ${project_name}_scd.mk" command="make" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfileCPP">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.cpp" command="g++" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfileC">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.c" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileCPP">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.cpp" command="g++" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileC">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.c" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<scannerConfigBuildInfo instanceId="cdt.managedbuild.toolchain.gnu.cross.base.1196063785;cdt.managedbuild.toolchain.gnu.cross.base.1196063785.592276132;cdt.managedbuild.tool.gnu.cross.cpp.compiler.934785405;cdt.managedbuild.tool.gnu.cpp.compiler.input.113975571">
+<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfileCPP"/>
+<profile id="org.eclipse.cdt.make.core.GCCStandardMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.make.core.GCCStandardMakePerFileProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="makefileGenerator">
+<runAction arguments="-f ${project_name}_scd.mk" command="make" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfileCPP">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.cpp" command="g++" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCManagedMakePerProjectProfileC">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.c" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfile">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/${specs_file}" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileCPP">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.cpp" command="g++" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+<profile id="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileC">
+<buildOutputProvider>
+<openAction enabled="true" filePath=""/>
+<parser enabled="true"/>
+</buildOutputProvider>
+<scannerInfoProvider id="specsFile">
+<runAction arguments="-E -P -v -dD ${plugin_state_location}/specs.c" command="gcc" useDefault="true"/>
+<parser enabled="true"/>
+</scannerInfoProvider>
+</profile>
+</scannerConfigBuildInfo>
+</storageModule>
+</cconfiguration>
+</storageModule>
+<storageModule moduleId="cdtBuildSystem" version="4.0.0">
+<project id="libplpha2.null.377175162" name="libplpha2"/>
+</storageModule>
+</cproject>
diff --git a/.project b/.project
new file mode 100644 (file)
index 0000000..cfa0f55
--- /dev/null
+++ b/.project
@@ -0,0 +1,78 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+       <name>libplpha</name>
+       <comment></comment>
+       <projects>
+       </projects>
+       <buildSpec>
+               <buildCommand>
+                       <name>org.eclipse.cdt.managedbuilder.core.genmakebuilder</name>
+                       <triggers>clean,full,incremental,</triggers>
+                       <arguments>
+                               <dictionary>
+                                       <key>?name?</key>
+                                       <value></value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.append_environment</key>
+                                       <value>true</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.autoBuildTarget</key>
+                                       <value>all</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.buildArguments</key>
+                                       <value></value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.buildCommand</key>
+                                       <value>make</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.cleanBuildTarget</key>
+                                       <value>clean</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.contents</key>
+                                       <value>org.eclipse.cdt.make.core.activeConfigSettings</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.enableAutoBuild</key>
+                                       <value>false</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.enableCleanBuild</key>
+                                       <value>true</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.enableFullBuild</key>
+                                       <value>true</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.fullBuildTarget</key>
+                                       <value>all</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.stopOnError</key>
+                                       <value>true</value>
+                               </dictionary>
+                               <dictionary>
+                                       <key>org.eclipse.cdt.make.core.useDefaultBuildCmd</key>
+                                       <value>true</value>
+                               </dictionary>
+                       </arguments>
+               </buildCommand>
+               <buildCommand>
+                       <name>org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder</name>
+                       <arguments>
+                       </arguments>
+               </buildCommand>
+       </buildSpec>
+       <natures>
+               <nature>org.eclipse.cdt.core.cnature</nature>
+               <nature>org.eclipse.cdt.core.ccnature</nature>
+               <nature>org.eclipse.cdt.managedbuilder.core.managedBuildNature</nature>
+               <nature>org.eclipse.cdt.managedbuilder.core.ScannerConfigNature</nature>
+       </natures>
+</projectDescription>
diff --git a/AUTHORS b/AUTHORS
new file mode 100644 (file)
index 0000000..0af34e6
--- /dev/null
+++ b/AUTHORS
@@ -0,0 +1 @@
+Mika Laitio <lamikr at pilppa dot org>
diff --git a/COPYING b/COPYING
new file mode 100644 (file)
index 0000000..b2f02dd
--- /dev/null
+++ b/COPYING
@@ -0,0 +1,165 @@
+               GNU LESSER GENERAL PUBLIC LICENSE
+                       Version 3, 29 June 2007
+
+ Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+
+  This version of the GNU Lesser General Public License incorporates
+the terms and conditions of version 3 of the GNU General Public
+License, supplemented by the additional permissions listed below.
+
+  0. Additional Definitions.
+
+  As used herein, "this License" refers to version 3 of the GNU Lesser
+General Public License, and the "GNU GPL" refers to version 3 of the GNU
+General Public License.
+
+  "The Library" refers to a covered work governed by this License,
+other than an Application or a Combined Work as defined below.
+
+  An "Application" is any work that makes use of an interface provided
+by the Library, but which is not otherwise based on the Library.
+Defining a subclass of a class defined by the Library is deemed a mode
+of using an interface provided by the Library.
+
+  A "Combined Work" is a work produced by combining or linking an
+Application with the Library.  The particular version of the Library
+with which the Combined Work was made is also called the "Linked
+Version".
+
+  The "Minimal Corresponding Source" for a Combined Work means the
+Corresponding Source for the Combined Work, excluding any source code
+for portions of the Combined Work that, considered in isolation, are
+based on the Application, and not on the Linked Version.
+
+  The "Corresponding Application Code" for a Combined Work means the
+object code and/or source code for the Application, including any data
+and utility programs needed for reproducing the Combined Work from the
+Application, but excluding the System Libraries of the Combined Work.
+
+  1. Exception to Section 3 of the GNU GPL.
+
+  You may convey a covered work under sections 3 and 4 of this License
+without being bound by section 3 of the GNU GPL.
+
+  2. Conveying Modified Versions.
+
+  If you modify a copy of the Library, and, in your modifications, a
+facility refers to a function or data to be supplied by an Application
+that uses the facility (other than as an argument passed when the
+facility is invoked), then you may convey a copy of the modified
+version:
+
+   a) under this License, provided that you make a good faith effort to
+   ensure that, in the event an Application does not supply the
+   function or data, the facility still operates, and performs
+   whatever part of its purpose remains meaningful, or
+
+   b) under the GNU GPL, with none of the additional permissions of
+   this License applicable to that copy.
+
+  3. Object Code Incorporating Material from Library Header Files.
+
+  The object code form of an Application may incorporate material from
+a header file that is part of the Library.  You may convey such object
+code under terms of your choice, provided that, if the incorporated
+material is not limited to numerical parameters, data structure
+layouts and accessors, or small macros, inline functions and templates
+(ten or fewer lines in length), you do both of the following:
+
+   a) Give prominent notice with each copy of the object code that the
+   Library is used in it and that the Library and its use are
+   covered by this License.
+
+   b) Accompany the object code with a copy of the GNU GPL and this license
+   document.
+
+  4. Combined Works.
+
+  You may convey a Combined Work under terms of your choice that,
+taken together, effectively do not restrict modification of the
+portions of the Library contained in the Combined Work and reverse
+engineering for debugging such modifications, if you also do each of
+the following:
+
+   a) Give prominent notice with each copy of the Combined Work that
+   the Library is used in it and that the Library and its use are
+   covered by this License.
+
+   b) Accompany the Combined Work with a copy of the GNU GPL and this license
+   document.
+
+   c) For a Combined Work that displays copyright notices during
+   execution, include the copyright notice for the Library among
+   these notices, as well as a reference directing the user to the
+   copies of the GNU GPL and this license document.
+
+   d) Do one of the following:
+
+       0) Convey the Minimal Corresponding Source under the terms of this
+       License, and the Corresponding Application Code in a form
+       suitable for, and under terms that permit, the user to
+       recombine or relink the Application with a modified version of
+       the Linked Version to produce a modified Combined Work, in the
+       manner specified by section 6 of the GNU GPL for conveying
+       Corresponding Source.
+
+       1) Use a suitable shared library mechanism for linking with the
+       Library.  A suitable mechanism is one that (a) uses at run time
+       a copy of the Library already present on the user's computer
+       system, and (b) will operate properly with a modified version
+       of the Library that is interface-compatible with the Linked
+       Version.
+
+   e) Provide Installation Information, but only if you would otherwise
+   be required to provide such information under section 6 of the
+   GNU GPL, and only to the extent that such information is
+   necessary to install and execute a modified version of the
+   Combined Work produced by recombining or relinking the
+   Application with a modified version of the Linked Version. (If
+   you use option 4d0, the Installation Information must accompany
+   the Minimal Corresponding Source and Corresponding Application
+   Code. If you use option 4d1, you must provide the Installation
+   Information in the manner specified by section 6 of the GNU GPL
+   for conveying Corresponding Source.)
+
+  5. Combined Libraries.
+
+  You may place library facilities that are a work based on the
+Library side by side in a single library together with other library
+facilities that are not Applications and are not covered by this
+License, and convey such a combined library under terms of your
+choice, if you do both of the following:
+
+   a) Accompany the combined library with a copy of the same work based
+   on the Library, uncombined with any other library facilities,
+   conveyed under the terms of this License.
+
+   b) Give prominent notice with the combined library that part of it
+   is a work based on the Library, and explaining where to find the
+   accompanying uncombined form of the same work.
+
+  6. Revised Versions of the GNU Lesser General Public License.
+
+  The Free Software Foundation may publish revised and/or new versions
+of the GNU Lesser General Public License from time to time. Such new
+versions will be similar in spirit to the present version, but may
+differ in detail to address new problems or concerns.
+
+  Each version is given a distinguishing version number. If the
+Library as you received it specifies that a certain numbered version
+of the GNU Lesser General Public License "or any later version"
+applies to it, you have the option of following the terms and
+conditions either of that published version or of any later version
+published by the Free Software Foundation. If the Library as you
+received it does not specify a version number of the GNU Lesser
+General Public License, you may choose any version of the GNU Lesser
+General Public License ever published by the Free Software Foundation.
+
+  If the Library as you received it specifies that a proxy can decide
+whether future versions of the GNU Lesser General Public License shall
+apply, that proxy's public statement of acceptance of any version is
+permanent authorization for you to choose that version for the
+Library.
diff --git a/ChangeLog b/ChangeLog
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/INSTALL b/INSTALL
new file mode 100644 (file)
index 0000000..7d1c323
--- /dev/null
+++ b/INSTALL
@@ -0,0 +1,365 @@
+Installation Instructions
+*************************
+
+Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002, 2004, 2005,
+2006, 2007, 2008, 2009 Free Software Foundation, Inc.
+
+   Copying and distribution of this file, with or without modification,
+are permitted in any medium without royalty provided the copyright
+notice and this notice are preserved.  This file is offered as-is,
+without warranty of any kind.
+
+Basic Installation
+==================
+
+   Briefly, the shell commands `./configure; make; make install' should
+configure, build, and install this package.  The following
+more-detailed instructions are generic; see the `README' file for
+instructions specific to this package.  Some packages provide this
+`INSTALL' file but do not implement all of the features documented
+below.  The lack of an optional feature in a given package is not
+necessarily a bug.  More recommendations for GNU packages can be found
+in *note Makefile Conventions: (standards)Makefile Conventions.
+
+   The `configure' shell script attempts to guess correct values for
+various system-dependent variables used during compilation.  It uses
+those values to create a `Makefile' in each directory of the package.
+It may also create one or more `.h' files containing system-dependent
+definitions.  Finally, it creates a shell script `config.status' that
+you can run in the future to recreate the current configuration, and a
+file `config.log' containing compiler output (useful mainly for
+debugging `configure').
+
+   It can also use an optional file (typically called `config.cache'
+and enabled with `--cache-file=config.cache' or simply `-C') that saves
+the results of its tests to speed up reconfiguring.  Caching is
+disabled by default to prevent problems with accidental use of stale
+cache files.
+
+   If you need to do unusual things to compile the package, please try
+to figure out how `configure' could check whether to do them, and mail
+diffs or instructions to the address given in the `README' so they can
+be considered for the next release.  If you are using the cache, and at
+some point `config.cache' contains results you don't want to keep, you
+may remove or edit it.
+
+   The file `configure.ac' (or `configure.in') is used to create
+`configure' by a program called `autoconf'.  You need `configure.ac' if
+you want to change it or regenerate `configure' using a newer version
+of `autoconf'.
+
+   The simplest way to compile this package is:
+
+  1. `cd' to the directory containing the package's source code and type
+     `./configure' to configure the package for your system.
+
+     Running `configure' might take a while.  While running, it prints
+     some messages telling which features it is checking for.
+
+  2. Type `make' to compile the package.
+
+  3. Optionally, type `make check' to run any self-tests that come with
+     the package, generally using the just-built uninstalled binaries.
+
+  4. Type `make install' to install the programs and any data files and
+     documentation.  When installing into a prefix owned by root, it is
+     recommended that the package be configured and built as a regular
+     user, and only the `make install' phase executed with root
+     privileges.
+
+  5. Optionally, type `make installcheck' to repeat any self-tests, but
+     this time using the binaries in their final installed location.
+     This target does not install anything.  Running this target as a
+     regular user, particularly if the prior `make install' required
+     root privileges, verifies that the installation completed
+     correctly.
+
+  6. You can remove the program binaries and object files from the
+     source code directory by typing `make clean'.  To also remove the
+     files that `configure' created (so you can compile the package for
+     a different kind of computer), type `make distclean'.  There is
+     also a `make maintainer-clean' target, but that is intended mainly
+     for the package's developers.  If you use it, you may have to get
+     all sorts of other programs in order to regenerate files that came
+     with the distribution.
+
+  7. Often, you can also type `make uninstall' to remove the installed
+     files again.  In practice, not all packages have tested that
+     uninstallation works correctly, even though it is required by the
+     GNU Coding Standards.
+
+  8. Some packages, particularly those that use Automake, provide `make
+     distcheck', which can by used by developers to test that all other
+     targets like `make install' and `make uninstall' work correctly.
+     This target is generally not run by end users.
+
+Compilers and Options
+=====================
+
+   Some systems require unusual options for compilation or linking that
+the `configure' script does not know about.  Run `./configure --help'
+for details on some of the pertinent environment variables.
+
+   You can give `configure' initial values for configuration parameters
+by setting variables in the command line or in the environment.  Here
+is an example:
+
+     ./configure CC=c99 CFLAGS=-g LIBS=-lposix
+
+   *Note Defining Variables::, for more details.
+
+Compiling For Multiple Architectures
+====================================
+
+   You can compile the package for more than one kind of computer at the
+same time, by placing the object files for each architecture in their
+own directory.  To do this, you can use GNU `make'.  `cd' to the
+directory where you want the object files and executables to go and run
+the `configure' script.  `configure' automatically checks for the
+source code in the directory that `configure' is in and in `..'.  This
+is known as a "VPATH" build.
+
+   With a non-GNU `make', it is safer to compile the package for one
+architecture at a time in the source code directory.  After you have
+installed the package for one architecture, use `make distclean' before
+reconfiguring for another architecture.
+
+   On MacOS X 10.5 and later systems, you can create libraries and
+executables that work on multiple system types--known as "fat" or
+"universal" binaries--by specifying multiple `-arch' options to the
+compiler but only a single `-arch' option to the preprocessor.  Like
+this:
+
+     ./configure CC="gcc -arch i386 -arch x86_64 -arch ppc -arch ppc64" \
+                 CXX="g++ -arch i386 -arch x86_64 -arch ppc -arch ppc64" \
+                 CPP="gcc -E" CXXCPP="g++ -E"
+
+   This is not guaranteed to produce working output in all cases, you
+may have to build one architecture at a time and combine the results
+using the `lipo' tool if you have problems.
+
+Installation Names
+==================
+
+   By default, `make install' installs the package's commands under
+`/usr/local/bin', include files under `/usr/local/include', etc.  You
+can specify an installation prefix other than `/usr/local' by giving
+`configure' the option `--prefix=PREFIX', where PREFIX must be an
+absolute file name.
+
+   You can specify separate installation prefixes for
+architecture-specific files and architecture-independent files.  If you
+pass the option `--exec-prefix=PREFIX' to `configure', the package uses
+PREFIX as the prefix for installing programs and libraries.
+Documentation and other data files still use the regular prefix.
+
+   In addition, if you use an unusual directory layout you can give
+options like `--bindir=DIR' to specify different values for particular
+kinds of files.  Run `configure --help' for a list of the directories
+you can set and what kinds of files go in them.  In general, the
+default for these options is expressed in terms of `${prefix}', so that
+specifying just `--prefix' will affect all of the other directory
+specifications that were not explicitly provided.
+
+   The most portable way to affect installation locations is to pass the
+correct locations to `configure'; however, many packages provide one or
+both of the following shortcuts of passing variable assignments to the
+`make install' command line to change installation locations without
+having to reconfigure or recompile.
+
+   The first method involves providing an override variable for each
+affected directory.  For example, `make install
+prefix=/alternate/directory' will choose an alternate location for all
+directory configuration variables that were expressed in terms of
+`${prefix}'.  Any directories that were specified during `configure',
+but not in terms of `${prefix}', must each be overridden at install
+time for the entire installation to be relocated.  The approach of
+makefile variable overrides for each directory variable is required by
+the GNU Coding Standards, and ideally causes no recompilation.
+However, some platforms have known limitations with the semantics of
+shared libraries that end up requiring recompilation when using this
+method, particularly noticeable in packages that use GNU Libtool.
+
+   The second method involves providing the `DESTDIR' variable.  For
+example, `make install DESTDIR=/alternate/directory' will prepend
+`/alternate/directory' before all installation names.  The approach of
+`DESTDIR' overrides is not required by the GNU Coding Standards, and
+does not work on platforms that have drive letters.  On the other hand,
+it does better at avoiding recompilation issues, and works well even
+when some directory options were not specified in terms of `${prefix}'
+at `configure' time.
+
+Optional Features
+=================
+
+   If the package supports it, you can cause programs to be installed
+with an extra prefix or suffix on their names by giving `configure' the
+option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'.
+
+   Some packages pay attention to `--enable-FEATURE' options to
+`configure', where FEATURE indicates an optional part of the package.
+They may also pay attention to `--with-PACKAGE' options, where PACKAGE
+is something like `gnu-as' or `x' (for the X Window System).  The
+`README' should mention any `--enable-' and `--with-' options that the
+package recognizes.
+
+   For packages that use the X Window System, `configure' can usually
+find the X include and library files automatically, but if it doesn't,
+you can use the `configure' options `--x-includes=DIR' and
+`--x-libraries=DIR' to specify their locations.
+
+   Some packages offer the ability to configure how verbose the
+execution of `make' will be.  For these packages, running `./configure
+--enable-silent-rules' sets the default to minimal output, which can be
+overridden with `make V=1'; while running `./configure
+--disable-silent-rules' sets the default to verbose, which can be
+overridden with `make V=0'.
+
+Particular systems
+==================
+
+   On HP-UX, the default C compiler is not ANSI C compatible.  If GNU
+CC is not installed, it is recommended to use the following options in
+order to use an ANSI C compiler:
+
+     ./configure CC="cc -Ae -D_XOPEN_SOURCE=500"
+
+and if that doesn't work, install pre-built binaries of GCC for HP-UX.
+
+   On OSF/1 a.k.a. Tru64, some versions of the default C compiler cannot
+parse its `<wchar.h>' header file.  The option `-nodtk' can be used as
+a workaround.  If GNU CC is not installed, it is therefore recommended
+to try
+
+     ./configure CC="cc"
+
+and if that doesn't work, try
+
+     ./configure CC="cc -nodtk"
+
+   On Solaris, don't put `/usr/ucb' early in your `PATH'.  This
+directory contains several dysfunctional programs; working variants of
+these programs are available in `/usr/bin'.  So, if you need `/usr/ucb'
+in your `PATH', put it _after_ `/usr/bin'.
+
+   On Haiku, software installed for all users goes in `/boot/common',
+not `/usr/local'.  It is recommended to use the following options:
+
+     ./configure --prefix=/boot/common
+
+Specifying the System Type
+==========================
+
+   There may be some features `configure' cannot figure out
+automatically, but needs to determine by the type of machine the package
+will run on.  Usually, assuming the package is built to be run on the
+_same_ architectures, `configure' can figure that out, but if it prints
+a message saying it cannot guess the machine type, give it the
+`--build=TYPE' option.  TYPE can either be a short name for the system
+type, such as `sun4', or a canonical name which has the form:
+
+     CPU-COMPANY-SYSTEM
+
+where SYSTEM can have one of these forms:
+
+     OS
+     KERNEL-OS
+
+   See the file `config.sub' for the possible values of each field.  If
+`config.sub' isn't included in this package, then this package doesn't
+need to know the machine type.
+
+   If you are _building_ compiler tools for cross-compiling, you should
+use the option `--target=TYPE' to select the type of system they will
+produce code for.
+
+   If you want to _use_ a cross compiler, that generates code for a
+platform different from the build platform, you should specify the
+"host" platform (i.e., that on which the generated programs will
+eventually be run) with `--host=TYPE'.
+
+Sharing Defaults
+================
+
+   If you want to set default values for `configure' scripts to share,
+you can create a site shell script called `config.site' that gives
+default values for variables like `CC', `cache_file', and `prefix'.
+`configure' looks for `PREFIX/share/config.site' if it exists, then
+`PREFIX/etc/config.site' if it exists.  Or, you can set the
+`CONFIG_SITE' environment variable to the location of the site script.
+A warning: not all `configure' scripts look for a site script.
+
+Defining Variables
+==================
+
+   Variables not defined in a site shell script can be set in the
+environment passed to `configure'.  However, some packages may run
+configure again during the build, and the customized values of these
+variables may be lost.  In order to avoid this problem, you should set
+them in the `configure' command line, using `VAR=value'.  For example:
+
+     ./configure CC=/usr/local2/bin/gcc
+
+causes the specified `gcc' to be used as the C compiler (unless it is
+overridden in the site shell script).
+
+Unfortunately, this technique does not work for `CONFIG_SHELL' due to
+an Autoconf bug.  Until the bug is fixed you can use this workaround:
+
+     CONFIG_SHELL=/bin/bash /bin/bash ./configure CONFIG_SHELL=/bin/bash
+
+`configure' Invocation
+======================
+
+   `configure' recognizes the following options to control how it
+operates.
+
+`--help'
+`-h'
+     Print a summary of all of the options to `configure', and exit.
+
+`--help=short'
+`--help=recursive'
+     Print a summary of the options unique to this package's
+     `configure', and exit.  The `short' variant lists options used
+     only in the top level, while the `recursive' variant lists options
+     also present in any nested packages.
+
+`--version'
+`-V'
+     Print the version of Autoconf used to generate the `configure'
+     script, and exit.
+
+`--cache-file=FILE'
+     Enable the cache: use and save the results of the tests in FILE,
+     traditionally `config.cache'.  FILE defaults to `/dev/null' to
+     disable caching.
+
+`--config-cache'
+`-C'
+     Alias for `--cache-file=config.cache'.
+
+`--quiet'
+`--silent'
+`-q'
+     Do not print messages saying which checks are being made.  To
+     suppress all normal output, redirect it to `/dev/null' (any error
+     messages will still be shown).
+
+`--srcdir=DIR'
+     Look for the package's source code in directory DIR.  Usually
+     `configure' can determine that directory automatically.
+
+`--prefix=DIR'
+     Use DIR as the installation prefix.  *note Installation Names::
+     for more details, including other options available for fine-tuning
+     the installation locations.
+
+`--no-create'
+`-n'
+     Run the configure checks, but stop before creating any output
+     files.
+
+`configure' also accepts some other, not widely useful, options.  Run
+`configure --help' for more details.
+
diff --git a/LICENSE.txt b/LICENSE.txt
new file mode 100644 (file)
index 0000000..7adfd16
--- /dev/null
@@ -0,0 +1,4 @@
+libplpha is copyrighted software by Mika Laitio <lamikr@pilppa.org>.
+You can redistribute it and/or modify it under either the terms of the LGPL version 3
+(see COPYING.txt file), or by obtaining the license from the author.
+
diff --git a/Makefile.am b/Makefile.am
new file mode 100644 (file)
index 0000000..3fcdfbd
--- /dev/null
@@ -0,0 +1,28 @@
+SUBDIRS = \  
+       src \
+       src_test \
+       data/configs
+pkgconfigdir = $(libdir)/pkgconfig
+EXTRA_DIST = libplpha.pc.in
+pkgconfig_DATA = libplpha.pc 
+DISTCLEANFILES = \
+       aclocal.m4 \
+       config.h \
+       config.h.in \
+       config.log \
+       config.status \
+       config.cache \
+       config.guess \
+       config.sub \
+       configure \
+       depcomp \
+       install-sh \
+       libtool \
+       ltmain.sh \
+       Makefile.in \
+       Makefile \
+       missing \
+       stamp-h \
+       stamp-h1 \
+       autom4te.cache \
+       $(pkgconfig_DATA)
\ No newline at end of file
diff --git a/NEWS b/NEWS
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/README b/README
new file mode 100644 (file)
index 0000000..1afd599
--- /dev/null
+++ b/README
@@ -0,0 +1,29 @@
+Description
+-----------
+This library provides a mechanism to read service files and launch and monitor them.
+
+Dependencies to other libraries
+-------------------------------
+- libuci for reading configuration files
+
+Build, install and clean
+------------------------
+- build with command: ./autobuild.sh (generates required autoconf files)
+- install with command: make install
+- clean source code from generated build files: make distclean 
+
+Examples
+--------
+See the src_test/test_ha
+"test_ha" is a example application which launches the processes defined in the 
+.service files available in the directory "src_test/etc/plp/ha"
+(Note that these files needs to be copied to /etc/plp/ha directory and you must fix from them the ExecStart to executables)
+
+TODO
+----
+- inotify integration
+- process polling
+
+License
+-------
+GNU LESSER GENERAL PUBLIC LICENSE (lgpl) version 3, for details see the COPYING file.
diff --git a/autobuild.sh b/autobuild.sh
new file mode 100755 (executable)
index 0000000..c318591
--- /dev/null
@@ -0,0 +1,12 @@
+#!/bin/sh
+
+if ! [ -e Makefile ] ;
+then
+       echo "No Makefile available, generating it."
+       libtoolize --automake --force --copy
+       autoreconf --force --install
+        PKG_CONFIG_PATH=/usr/local/lib/pkgconfig ./configure --prefix=/usr/local
+else
+       echo "Makefile found, no need to generate it."
+fi
+make
diff --git a/configure.ac b/configure.ac
new file mode 100644 (file)
index 0000000..44c53b1
--- /dev/null
@@ -0,0 +1,36 @@
+AC_INIT(src/launcher.c)
+AM_CONFIG_HEADER(config.h)
+AC_CONFIG_MACRO_DIR([m4])
+
+PACKAGE=libplpha
+VERSION=1.0.0
+
+CFLAGS="$CFLAGS -g -Wall -Werror"
+LDFLAGS="$LDFLAGS -lpthread"
+AC_SUBST(CFLAGS)
+AC_SUBST(LDFLAGS)
+AC_MSG_NOTICE([libplpha Makefile])
+
+AM_INIT_AUTOMAKE($PACKAGE, $VERSION)
+
+#AC_PROG_CXX
+AC_STDC_HEADERS
+AC_PROG_LIBTOOL
+AC_PROG_INSTALL
+#AM_PROG_CC_C_O
+
+PKG_PROG_PKG_CONFIG()
+
+PKG_CHECK_MODULES(SRC, libuci)
+AC_SUBST(SRC_CFLAGS)
+AC_SUBST(SRC_LIBS)
+
+AC_OUTPUT([
+libplpha.pc
+Makefile
+src/Makefile
+src_test/Makefile
+data/configs/Makefile
+data/configs/test_client.service
+data/configs/test_client2.service
+])
diff --git a/data/configs/Makefile.am b/data/configs/Makefile.am
new file mode 100644 (file)
index 0000000..4623749
--- /dev/null
@@ -0,0 +1,6 @@
+configdir =  $(sysconfdir)/plp/ha
+config_in_files = test_client.service.in test_client2.service.in
+config_DATA = $(config_in_files:.service.in=.service)
+EXTRA_DIST = $(config_in_files)
+DISTCLEANFILES = $(config_DATA) Makefile.in
+
diff --git a/data/configs/test_client.service.in b/data/configs/test_client.service.in
new file mode 100644 (file)
index 0000000..d85d75e
--- /dev/null
@@ -0,0 +1,2 @@
+config 'test_client' 'service'
+        option 'ExecStart' '@prefix@/bin/test_client'
diff --git a/data/configs/test_client2.service.in b/data/configs/test_client2.service.in
new file mode 100644 (file)
index 0000000..bd4f582
--- /dev/null
@@ -0,0 +1,3 @@
+config 'hello' 'service'
+        option 'ExecStart' '@prefix@/bin/test_client2'
+
diff --git a/libplpha.pc.in b/libplpha.pc.in
new file mode 100644 (file)
index 0000000..e71e780
--- /dev/null
@@ -0,0 +1,11 @@
+prefix=@prefix@
+exec_prefix=@exec_prefix@
+libdir=@libdir@
+includedir=@includedir@
+
+Name: libplpha
+Description: pilppa communication bus library
+Version: @VERSION@
+Requires: libuci
+Cflags: -I${includedir} -I${includedir}/libplpha
+Libs: -L${libdir}
diff --git a/src/Makefile.am b/src/Makefile.am
new file mode 100644 (file)
index 0000000..40b9e27
--- /dev/null
@@ -0,0 +1,10 @@
+lib_LTLIBRARIES = libplpha.la
+libplpha_la_SOURCES = \
+       launcher.c launcher.h \
+       process_listener.c process_listener.h \
+       process_parser.c process_parser.h \
+       servicedir_listener.c servicedir_listener.h \
+       process_info.h  
+libplpha_la_LDFLAGS = $(SRC_LIBS) $(all_libraries) -version-info 1:0:0 -no-undefined
+AM_CPPFLAGS = $(SRC_CFLAGS)
+DISTCLEANFILES = Makefile.in
diff --git a/src/common.h b/src/common.h
new file mode 100644 (file)
index 0000000..cb99c56
--- /dev/null
@@ -0,0 +1,15 @@
+/*
+ * common.h
+ *
+ *  Created on: Sep 19, 2010
+ *      Author: lamikr
+ */
+
+#ifndef COMMON_H_
+#define COMMON_H_
+
+#define CONST_SERVICE_DIRECTORY_LOCATION       "/etc/plp/ha"
+#define CONST_MAX_INOTIFY_EVENT_COUNT_READ     16
+#define CONST_MAX_EXPECTED_INOTIFY_EVENT_SIZE  1024
+
+#endif /* COMMON_H_ */
diff --git a/src/launcher.c b/src/launcher.c
new file mode 100644 (file)
index 0000000..07f22cc
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * launcher.c
+ *
+ *  Created on: Sep 14, 2010
+ *      Author: lamikr
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+int launch_new_process(char *param_arr[]) {
+       int ret_val;
+       int child_pid;
+
+       child_pid       = fork();
+       if (child_pid == -1) {
+               // failed to fork a new process
+               ret_val = -1;
+       }
+       else if (child_pid == 0) {
+               // code for launched child process
+               //execvp(param_arr[0], param_arr);
+               // first parameter must contain a full path to executable
+               execv(param_arr[0], param_arr);
+               printf("Failed to execute\n");
+               exit(-1);
+       }
+       else {
+               // code for parent process which launched the child
+               ret_val = child_pid;
+       }
+       return ret_val;
+}
diff --git a/src/launcher.h b/src/launcher.h
new file mode 100644 (file)
index 0000000..138d3b8
--- /dev/null
@@ -0,0 +1,13 @@
+/*
+ * launcher.h
+ *
+ *  Created on: Sep 14, 2010
+ *      Author: lamikr
+ */
+
+#ifndef LAUNCHER_H_
+#define LAUNCHER_H_
+
+void launch_new_process(char *param_arr[]);
+
+#endif /* LAUNCHER_H_ */
diff --git a/src/process_info.h b/src/process_info.h
new file mode 100644 (file)
index 0000000..abe374b
--- /dev/null
@@ -0,0 +1,28 @@
+/*
+ * process_info.h
+ *
+ *  Created on: Sep 17, 2010
+ *      Author: lamikr
+ */
+
+#ifndef PROCESS_INFO_H_
+#define PROCESS_INFO_H_
+
+typedef struct t_process_arg_list {
+       int     count;
+       char    **arg_arr;
+} t_process_arg_list;
+
+typedef struct t_process_info {
+       int                     p_id;
+       t_process_arg_list      *arg_list;
+       struct t_process_info   *next;
+} t_process_info;
+
+typedef struct t_process_info_list {
+       int             count;
+       t_process_info  *first_item;
+       t_process_info  *last_item;
+} t_process_info_list;
+
+#endif /* PROCESS_INFO_H_ */
diff --git a/src/process_listener.c b/src/process_listener.c
new file mode 100644 (file)
index 0000000..81ef446
--- /dev/null
@@ -0,0 +1,50 @@
+/*
+ * process_listener.c
+ *
+ *  Created on: Sep 18, 2010
+ *      Author: lamikr
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <pthread.h>
+#include <stdbool.h>
+
+#include "process_listener.h"
+
+static pthread_t       _listener_thread;
+static bool            _continue;
+
+static void *process_listener_thread(void *thread_args_pointer)
+{
+       int     status;
+       int     closed_pid;
+
+       while(_continue) {
+               closed_pid      = wait(&status);
+               if (closed_pid >= 0) {
+                       printf("process closed: %d, status: %d\n", closed_pid, status);
+               }
+       }
+       pthread_exit(NULL);
+}
+
+void start_process_listener() {
+       printf("listen_closed_processes()\n");
+
+       _listener_thread        = 0;
+       _continue               = true;
+       pthread_create(&_listener_thread,
+                      NULL,
+                      process_listener_thread,
+                      (void *)NULL);
+}
+
+void stop_process_listener() {
+       _continue       = false;
+//     pthread_cancel(_listener_thread);
+//     pthread_join(_listener_thread, NULL);
+}
diff --git a/src/process_listener.h b/src/process_listener.h
new file mode 100644 (file)
index 0000000..a82a129
--- /dev/null
@@ -0,0 +1,17 @@
+/*
+ * process_listener.h
+ *
+ *  Created on: Sep 18, 2010
+ *      Author: lamikr
+ */
+
+#ifndef PROCESS_LISTENER_H_
+#define PROCESS_LISTENER_H_
+
+/**
+ * Listens when the launched processes will close.
+ */
+void start_process_listener();
+void stop_process_listener();
+
+#endif /* PROCESS_LISTENER_H_ */
diff --git a/src/process_parser.c b/src/process_parser.c
new file mode 100644 (file)
index 0000000..2dffdda
--- /dev/null
@@ -0,0 +1,186 @@
+/*
+ * process_parser.c
+ *
+ *  Created on: Sep 16, 2010
+ *      Author: lamikr
+ */
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <dirent.h>
+#include <uci.h>
+
+#include "common.h"
+#include "process_parser.h"
+
+t_process_arg_list *parse_command_line_args(char *cmd_line_param) {
+       char                    *line_pointer;
+       char                    *start;
+       int                     len;
+       t_process_arg_list      *ret_val;
+
+       ret_val = NULL;
+       if (cmd_line_param != NULL) {
+               ret_val         = calloc(1, sizeof(t_process_arg_list));
+               line_pointer    = cmd_line_param;
+               while(*line_pointer != '\0') {
+                       while((*line_pointer == ' ') ||
+                             (*line_pointer == '\t')) {
+                               line_pointer++;
+                       }
+                       if (*line_pointer != '\0') {
+                               if (ret_val->arg_arr == NULL) {
+                                       ret_val->arg_arr        = calloc(1, sizeof(char *));
+                               }
+                               else {
+                                       char    **arg_arr;
+
+                                       arg_arr = ret_val->arg_arr;
+                                       arg_arr = realloc(arg_arr, (ret_val->count + 1) * sizeof(char *));
+                                       ret_val->arg_arr        = arg_arr;
+                               }
+                               start           = line_pointer;
+                               len             = 1;
+                               while((*++line_pointer != '\0') &&
+                                     (*line_pointer != ' ') &&
+                                     (*line_pointer != '\t')) {
+                                       len++;
+                               }
+                               ret_val->arg_arr[ret_val->count]        = strndup(start, len);
+                               printf("ret_val[%d] = %s\n", ret_val->count, ret_val->arg_arr[ret_val->count]);
+                               ret_val->count                          = ret_val->count + 1;
+                       }
+                       else {
+                               break;
+                       }
+               }
+               // terminate list with null
+               ret_val->arg_arr                        = realloc(ret_val->arg_arr, (ret_val->count + 1) * sizeof(char *));
+               ret_val->arg_arr[ret_val->count]        = NULL;
+               ret_val->count                          = ret_val->count + 1;
+       }
+       return ret_val;
+}
+
+t_process_info *parse_process_info(struct uci_option *option_param) {
+       t_process_info  *ret_val;
+
+       ret_val = NULL;
+       if (option_param->type == UCI_TYPE_STRING) {
+               ret_val                 = calloc(1, sizeof(t_process_info));
+               ret_val->arg_list       = parse_command_line_args(option_param->v.string);
+       }
+       return ret_val;
+}
+
+int add_process_config(t_process_info_list *list_param, struct uci_option *option_param) {
+       int             ret_val;
+       t_process_info  *new_item;
+
+       ret_val         = -1;
+       new_item        = parse_process_info(option_param);
+       if (new_item != NULL) {
+               if (list_param->last_item != NULL) {
+                       list_param->last_item->next     = new_item;
+                       list_param->last_item           = new_item;
+               }
+               else {
+                       list_param->first_item  = new_item;
+                       list_param->last_item   = new_item;
+               }
+               list_param->count       = list_param->count + 1;
+               ret_val                 = 0;
+       }
+       return ret_val;
+}
+
+t_process_info_list *get_process_config_list() {
+       char                    **config_list;
+       char                    **config_file;
+       int                     err_flg;
+       struct uci_context      *ctx;
+       struct uci_package      *pkg;
+       struct uci_section      *section;
+       struct uci_option       *option;
+       t_process_info_list     *ret_val;
+
+       ret_val = calloc(1, sizeof(t_process_info_list));
+       ctx     = uci_alloc_context();
+       if (ctx != NULL) {
+               uci_set_confdir(ctx, CONST_SERVICE_DIRECTORY_LOCATION);
+               config_list     = NULL;
+               err_flg         = uci_list_configs(ctx, &config_list);
+               if ((err_flg == UCI_OK) &&
+                   (config_list != NULL)) {
+                       for (config_file = config_list; *config_file != NULL; config_file++) {
+                               err_flg = uci_load(ctx, *config_file, &pkg);
+                               if (err_flg == UCI_OK) {
+                                       section = uci_lookup_section(ctx, pkg, "service");
+                                       if (section != NULL) {
+                                               option  = uci_lookup_option(ctx, section, "ExecStart");
+                                               switch (option->type) {
+                                                       case UCI_TYPE_STRING:
+                                                               printf("config file: %s name: %s, value: %s\n", *config_file, option->e.name, option->v.string);
+                                                               add_process_config(ret_val, option);
+                                                               break;
+                                                       default:
+                                                               break;
+                                               }
+                                       }
+                                       //int num_sections = _uci_show_package(*config_file, result);
+                                       //printf("Queried package: %s -> %d\n", *config_file, num_sections);
+                               }
+                               uci_unload(ctx, pkg);
+                       }
+                       // free config_files
+/*
+                       for (config_file = config_list; *config_file != NULL; config_file++) {
+                               free(config_file);
+                       }
+*/
+                       free(config_list);
+               }
+               else {
+                       printf("Failed to read service configurations from directory: %s\n", CONST_SERVICE_DIRECTORY_LOCATION);
+               }
+               uci_free_context(ctx);
+       }
+       else {
+               printf("Failed to read service configurations from directory: %s\n Memory allocation error.", CONST_SERVICE_DIRECTORY_LOCATION);
+       }
+       return ret_val;
+}
+
+void release_process_config_arg_list(t_process_arg_list *arg_list_param) {
+       int     ii;
+
+       for (ii = 0; ii < arg_list_param->count; ii++) {
+               if (arg_list_param->arg_arr[ii] != NULL) {
+                       free(arg_list_param->arg_arr[ii]);
+                       arg_list_param->arg_arr[ii]     = NULL;
+               }
+       }
+       free(arg_list_param->arg_arr);
+       arg_list_param->count   = 0;
+       free(arg_list_param);
+}
+
+void release_process_config_list(t_process_info_list *list_param) {
+       t_process_info          *item;
+       t_process_info          *next;
+
+       if (list_param != NULL) {
+               item    = list_param->first_item;
+               while (item != NULL) {
+                       next            = item->next;
+                       item->next      = NULL;
+                       release_process_config_arg_list(item->arg_list);
+                       item->arg_list  = NULL;
+                       free(item);
+                       item            = next;
+               }
+               list_param->first_item  = NULL;
+               list_param->last_item   = NULL;
+               free(list_param);
+       }
+}
diff --git a/src/process_parser.h b/src/process_parser.h
new file mode 100644 (file)
index 0000000..7f2d0db
--- /dev/null
@@ -0,0 +1,17 @@
+/*
+ * process_parser.h
+ *
+ *  Created on: Sep 16, 2010
+ *      Author: lamikr
+ */
+
+#ifndef INIT_PARSER_H_
+#define INIT_PARSER_H_
+
+#include "process_info.h"
+
+t_process_info_list *get_process_config_list();
+void release_process_config_list(t_process_info_list *list_param);
+void release_process_config_arg_list(t_process_arg_list *arg_list_param);
+
+#endif /* INIT_PARSER_H_ */
diff --git a/src/servicedir_listener.c b/src/servicedir_listener.c
new file mode 100644 (file)
index 0000000..d3d42b2
--- /dev/null
@@ -0,0 +1,170 @@
+/*
+ * servicedir_listener.c
+ *
+ *  Created on: Sep 25, 2010
+ *      Author: lamikr
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+#include <sys/types.h>
+#include <sys/inotify.h>
+#include <stdbool.h>
+#include <pthread.h>
+#include <fcntl.h>
+
+#include "common.h"
+#include "servicedir_listener.h"
+
+static pthread_t       _listener_thread;
+static bool            _listener_stop_requested;
+static bool            _listener_running               = false;
+static int             _dir_handle                     = -1;
+static int             _inotify_handle                 = -1;
+static pthread_mutex_t _listener_mutex;
+
+static void init_servicedir_listener() {
+       //_listener_mutex                       = PTHREAD_MUTEX_INITIALIZER;
+       pthread_mutex_init(&_listener_mutex, NULL);
+}
+
+static void deinit_servicedir_listener() {
+       pthread_mutex_destroy(&_listener_mutex);
+}
+
+static void *servicedir_listener_thread(void *thread_args_pointer)
+{
+       int                     b_count;
+       int                     ii;
+       char                    *buffer;
+       struct inotify_event    *event;
+       int                     buffer_max_size;
+
+       /*
+        * Size of each i-notify event read: size of event structure + filename length that caused the event. (name follows the struct).
+        * We create a buffer that could in theory handle 16 events for files which name would be in maximum 1024 chars. (=CONST_MAX_EXPECTED_INOTIFY_EVENT_SIZE)
+        */
+       buffer_max_size = CONST_MAX_INOTIFY_EVENT_COUNT_READ * (sizeof(struct inotify_event) + CONST_MAX_EXPECTED_INOTIFY_EVENT_SIZE);
+       buffer          = calloc(1, buffer_max_size);
+       if (buffer != NULL) {
+               _inotify_handle = inotify_init();
+               if (_inotify_handle >= 0) {
+                       _dir_handle     = inotify_add_watch(_inotify_handle,
+                                               CONST_SERVICE_DIRECTORY_LOCATION,
+                                               IN_CREATE | IN_ATTRIB | IN_MODIFY | IN_DELETE);
+                       if (_dir_handle >= 0) {
+                               printf("Waiting service directory file events\n");
+                               while (_listener_stop_requested == false) {
+                                       ii      = 0;
+                                       printf("Waiting service directory file event\n");
+                                       b_count = read(_inotify_handle,
+                                                       buffer,
+                                                       buffer_max_size);
+                                       printf("Service directory file event received\n");
+                                       if (b_count >= 0) {
+                                               while (ii < b_count) {
+                                                       event   = (struct inotify_event *)&buffer[ii];
+                                                       printf("event length = %d\n", event->len);
+                                                       if (event->len) {
+                                                               if (event->mask & IN_CREATE) {
+                                                                       if ((event->mask & IN_ISDIR) == 0) {
+                                                                               printf("file create event: %s\n", event->name);
+                                                                       }
+                                                                       else {
+                                                                               printf("sub-directory create event: %s, no need to process\n", event->name);
+                                                                       }
+                                                               }
+                                                               else if (event->mask & IN_ATTRIB) {
+                                                                       if ((event->mask & IN_ISDIR) == 0) {
+                                                                               printf("file attribute change event: %s\n", event->name);
+                                                                       }
+                                                                       else {
+                                                                               printf("sub-directory attribute change event: %s, no need to process\n", event->name);
+                                                                       }
+                                                               }
+                                                               else if (event->mask & IN_MODIFY) {
+                                                                       if ((event->mask & IN_ISDIR) == 0) {
+                                                                               printf("file modify event: %s\n", event->name);
+                                                                       }
+                                                                       else {
+                                                                               printf("sub-directory modify event: %s, no need to process\n", event->name);
+                                                                       }
+                                                               }
+                                                               else if (event->mask & IN_DELETE) {
+                                                                       if ((event->mask & IN_ISDIR) == 0) {
+                                                                               printf("file delete event: %s\n", event->name);
+                                                                       }
+                                                                       else {
+                                                                               printf("sub-directory delete event: %s, no need to process\n", event->name);
+                                                                       }
+                                                               }
+                                                       }
+                                                       ii      = ii + sizeof(struct inotify_event) + event->len;
+                                               }
+                                       }
+                                       else {
+                                               printf("Failed to initialize service directory listener: %s, event read failed.\n", CONST_SERVICE_DIRECTORY_LOCATION);
+                                       }
+                               }
+                               printf("Closing service directory listener: %s, close request received.\n", CONST_SERVICE_DIRECTORY_LOCATION);
+                               pthread_mutex_lock(&_listener_mutex);
+                               if ((_inotify_handle > 0) && (_dir_handle)) {
+                                       inotify_rm_watch(_inotify_handle, _dir_handle);
+                                       _dir_handle     = -1;
+                               }
+                               pthread_mutex_unlock(&_listener_mutex);
+                       }
+                       else {
+                               printf("Failed to initialize service directory listener: %s, event listener start-up error.\n", CONST_SERVICE_DIRECTORY_LOCATION);
+                       }
+                       pthread_mutex_lock(&_listener_mutex);
+                       if (_inotify_handle > 0) {
+                               close(_inotify_handle);
+                               _inotify_handle = -1;
+                       }
+                       pthread_mutex_unlock(&_listener_mutex);
+               }
+               else {
+                       printf("Failed to initialize service directory listener: %s\n", CONST_SERVICE_DIRECTORY_LOCATION);
+               }
+               if (buffer != NULL) {
+                       free(buffer);
+                       buffer  = NULL;
+               }
+       }
+       else {
+               printf("Failed to initialize service directory listener: %s, buffer allocation error.\n", CONST_SERVICE_DIRECTORY_LOCATION);
+       }
+       _listener_running       = false;
+       pthread_exit(NULL);
+}
+
+void start_servicedir_listener() {
+       printf("listen_closed_processes()\n");
+       init_servicedir_listener();
+       if (_listener_running == false) {
+               _listener_thread                = 0;
+               _listener_stop_requested        = false;
+               _listener_running               = true;
+               pthread_create(&_listener_thread,
+                              NULL,
+                              servicedir_listener_thread,
+                              (void *)NULL);
+       }
+}
+
+void stop_servicedir_listener() {
+       _listener_stop_requested        = true;
+       pthread_mutex_lock(&_listener_mutex);
+       if ((_inotify_handle > 0) && (_dir_handle)) {
+               inotify_rm_watch(_inotify_handle, _dir_handle);
+               close(_inotify_handle);
+               _dir_handle     = -1;
+               _inotify_handle = -1;
+       }
+       pthread_mutex_unlock(&_listener_mutex);
+       pthread_join(_listener_thread, NULL);
+       deinit_servicedir_listener();
+}
diff --git a/src/servicedir_listener.h b/src/servicedir_listener.h
new file mode 100644 (file)
index 0000000..377fee4
--- /dev/null
@@ -0,0 +1,17 @@
+/*
+ * servicedir_listener.h
+ *
+ *  Created on: Sep 25, 2010
+ *      Author: lamikr
+ */
+
+#ifndef SERVICEDIR_LISTENER_H_
+#define SERVICEDIR_LISTENER_H_
+
+/**
+ * Listens changes in the service configuration directory.
+ */
+void start_servicedir_listener();
+void stop_servicedir_listener();
+
+#endif /* SERVICEDIR_LISTENER_H_ */
diff --git a/src_test/Makefile.am b/src_test/Makefile.am
new file mode 100644 (file)
index 0000000..5310373
--- /dev/null
@@ -0,0 +1,14 @@
+bin_PROGRAMS = test_ha test_client test_client2
+
+test_ha_SOURCES = test_ha.c
+test_ha_LDADD = $(SRC_LIBS) ../src/.libs/libplpha.a
+
+test_client_SOURCES = test_client.c
+test_client_LDADD = $(SRC_LIBS) ../src/.libs/libplpha.a
+
+test_client2_SOURCES = test_client.c
+test_client2_LDADD = $(SRC_LIBS) ../src/.libs/libplpha.a
+
+AM_CPPFLAGS = $(SRC_CFLAGS) -I../src
+
+DISTCLEANFILES = Makefile.in
\ No newline at end of file
diff --git a/src_test/test_client.c b/src_test/test_client.c
new file mode 100644 (file)
index 0000000..cd2bafe
--- /dev/null
@@ -0,0 +1,46 @@
+/*
+ * test_client.c
+ *
+ *  Created on: Jun 9, 2010
+ *      Author: lamikr
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+#include "common.h"
+#include "process_parser.h"
+#include <string.h>
+
+int main(int argc, char** argv)
+{
+       int sleep_time = 2;
+
+       t_process_arg_list      *ret_val;
+       int     ii;
+
+       ret_val         = calloc(1, sizeof(t_process_arg_list));
+       for (ii = 0; ii < 1; ii++) {
+               if (ret_val->arg_arr == NULL) {
+                       ret_val->arg_arr        = calloc(1, sizeof(char *));
+               }
+               else {
+                       char    **arg_arr;
+
+                       arg_arr = ret_val->arg_arr;
+                       arg_arr = realloc(arg_arr, (ret_val->count + 1) * sizeof(char *));
+                       ret_val->arg_arr        = arg_arr;
+               }
+               ret_val->arg_arr[ii]    = strdup("hello\n");
+               ret_val->count          = ret_val->count + 1;
+       }
+       if (argc > 1) {
+               sleep_time = atoi(argv[1]);
+       }
+       release_process_config_arg_list(ret_val);
+       ret_val = NULL;
+       printf("sleep-time: %d seconds\n", sleep_time);
+       sleep(sleep_time);
+       return 0;
+}
diff --git a/src_test/test_ha.c b/src_test/test_ha.c
new file mode 100644 (file)
index 0000000..e7fe1e7
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * test_ha.c
+ *
+ *  Created on: Sep 16, 2010
+ *      Author: lamikr
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+
+#include "launcher.h"
+#include "process_parser.h"
+#include "process_listener.h"
+#include "servicedir_listener.h"
+
+int main(int argc, char** argv)
+{
+       t_process_info_list     *process_list;
+       t_process_info          *process_item;
+
+       start_process_listener();
+       start_servicedir_listener();
+       process_list    = get_process_config_list();
+       if (process_list != NULL) {
+               printf("process_list->count: %d\n", process_list->count);
+               process_item    = process_list->first_item;
+               if (process_item != NULL) {
+                       if ((process_item->arg_list != NULL) &&
+                           (process_item->arg_list->arg_arr != NULL)) {
+                               launch_new_process(process_item->arg_list->arg_arr);
+                               process_item    = process_item->next;
+                       }
+               }
+               sleep(8);
+               stop_servicedir_listener();
+               release_process_config_list(process_list);
+       }
+       //closed_pid    = wait(&status);
+       //printf("closed process: %d, status: %d\n", closed_pid, status);
+       return 0;
+}