Create daemon process in linux

Daemonizing a Process in Linux

Most of the times when we need to run some Java, Node.js or python program in background, so it could stay running even after you leave console all we do is put “&” in the end of the command.

$java -jar SimpleService.jar &

The problem here is that when you leave the bash shell your process will become “Orphan” and it’s up to the OS if INIT should adopt the process or kill the process.

To fix this we can force the process to be detached from your shell and become child process of INIT by putting nohup in front of command.

$nohup java -jar SimpleService.jar &

It’s all good for testing purposes, but services are supposed to run as “daemons” under some service supervisor. You can find many service supervisors with which you manage your services on Linux and we will cover few of the defaults that come with Linux.

Why do you need it ?

a. auto start/stop the service on startup/shutdown
b. controlling which service should start first
c. controlling which service should stop first is equally important
d. INIT controlled processes directly which provides more options like respawn, post-start, etc..

Ubuntu services using Upstart

Modify the script according to your setup:

$sudo vi /etc/init/java-app.conf

[js]author «nitin»
description «start and stop java-app for Ubuntu (upstart)»
version «1.0»

start on started networking
stop on runlevel [!2345]

# Automatically Respawn a process if fails, try max 5 times in 60 sec then give up
respawn
respawn limit 5 60

# Open files Limit
limit nofile 32768 32768

env APPUSER=»admin»
env APPBIN=»/usr/bin/java»
env APPARGS=»-jar /opt/app/SimpleService.jar»

script
exec su – $APPUSER -c «$APPBIN $APPARGS»
end script

post-stop script
sleep 2
end script[/js]

Check the configuration:
$init-checkconf /etc/init/java-app.conf

Reload New configuration:
$sudo initctl reload-configuration

Check is service is known to Upstart:
$sudo initctl list |grep java

Start the service with:
$sudo start java-app

Note: For any errors look into /var/log/syslog and /var/log/upstart/*

Debian and Ubuntu services using SysVinit

Modify the script according to your setup.

### BEGIN INIT INFO
# Provides: daemon
# Required-Start: $local_fs $network $syslog
# Required-Stop: $local_fs $network $syslog
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
# Short-Description: Java-app
# Description: Java-app start-stop-daemon – Debian
### END INIT INFO

NAME=»java-app»
PATH=»/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin»
APPDIR=»/opt/app»
APPBIN=»/usr/bin/java»
APPARGS=»-jar /opt/app/SimpleService.jar»
USER=»admin»
GROUP=»admin»

# Include functions
set -e
. /lib/lsb/init-functions

start() printf «Starting ‘$NAME’… »
start-stop-daemon –start –chuid «$USER:$GROUP» –background –make-pidfile –pidfile /var/run/$NAME.pid –chdir «$APPDIR» –exec «$APPBIN» — $APPARGS || true
printf «done\n»
>

#We need this function to ensure the whole process tree will be killed
killtree() local _pid=$1
local _sig=$
for _child in $(ps -o pid –no-headers –ppid $); do
killtree $ $
done
kill -$ $
>

stop() printf «Stopping ‘$NAME’… »
[ -z `cat /var/run/$NAME.pid 2>/dev/null` ] || \
while test -d /proc/$(cat /var/run/$NAME.pid); do
killtree $(cat /var/run/$NAME.pid) 15
sleep 0.5
done
[ -z `cat /var/run/$NAME.pid 2>/dev/null` ] || rm /var/run/$NAME.pid
printf «done\n»
>

Читайте также:  Linux vlc no audio

status() status_of_proc -p /var/run/$NAME.pid «» $NAME && exit 0 || exit $?
>

Make sure the script is executable:
$chmod +x /etc/init.d/java-app

Enable the service to auto start in runlevel 2345:
$update-rc.d java-app defaults

Start the service with:
$service java-app start

CentOS/Redhat services using SysVinit

Modify the parameter according to your setup:
$sudo vi /etc/init.d/example

[js]#!/bin/sh
#
# example start stop daemon for CentOS (sysvinit)
#
# chkconfig: – 64 36
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 2 3 4 6
# Required-Start:
# description: java-app start stop daemon for CentOS
# processname: java-app
# pidfile: none
# lockfile: /var/lock/subsys/java-app

# Source function library.
. /etc/rc.d/init.d/functions

# Source networking configuration.
. /etc/sysconfig/network

# Check that networking is up.
[ «$NETWORKING» = «no» ] && exit 0

USER=»admin»
APPNAME=»java-app»
APPBIN=»/usr/bin/java»
APPARGS=»-jar /opt/app/SimpleService.jar»
LOGFILE=»/var/log/$APPNAME/error.log»
LOCKFILE=»/var/lock/subsys/$APPNAME»

start() [ -x $prog ] || exit 5
[ -d $LOGPATH ] || mkdir $LOGPATH
[ -f $LOGFILE ] || touch $LOGFILE

echo -n $»Starting $APPNAME: »
daemon –user=$USER «$APPBIN $APPARGS >>$LOGFILE &»
RETVAL=$?
echo
[ $RETVAL -eq 0 ] && touch $LOCKFILE
return $RETVAL
>

stop() echo -n $»Stopping $APPNAME: »
killproc $APPBIN
RETVAL=$?
echo
[ $RETVAL -eq 0 ] && rm -f $LOCKFILE
return $RETVAL
>

Make sure the script is marked as executable:
$sudo chmod +x /etc/init.d/java-app

Enable the service to auto start at runlevels 2345:
$sudo chkconfig java-app on

Start the service with:
$sudo service java-app start

This is how simple it is to daemonize a process. In my next blog, I will talk about more interesting features available in Linux OS.

Источник

Beginners Guide to creating a daemon in Linux

Before reading this please note this is a beginners guide and does not go in detail about the content. However if this is the first time you are creating a daemon in linux you have come to the right place.

What do you need to know.

A basic understanding of C++ and some bare know how about using linux, and by linux we mean knowing how to start a process and kill a process. Using eclipse in Linux with C++.

What am i using

I’m currently running Fedora 13 with eclipse installed. You can however program the below in Ubuntu and test your deamon out in both platforms.

Now that we have discussed the requirements lets breeze through some local knowledge

Understanding how Linux handles services

To run any daemon you have to create a init script. this scripts control the start stop and restart functionality of the process. Init scripts control the services Start and Stops, And they also don’t let a service start when it is already running. I will talk more about init scripts in part 2 of this tutorial.

Lets Begin — Two Birds, One Stone

I’ve learned before creating daemons its always good to get the process part of it working. So first lets set-up a test program. For this example we are going to write to the syslog daemon. The reason why I do this is because there is a lot of code that goes above and below in our main file to setup a daemon. So i leave my processing to be done in another function.

Daemon and Programs are fairly similar to each other, however daemons don’t output their outward code to the console. So its a good idea to get into grips with logging your outputs rather than using cout or printf . Below we are going to add a syslog entry into our process function.

#include void process() < syslog(LOG_NOTICE, "Writing to my Syslog"); >int main (int argc, char *argv[])

What have we done above. Well simply put we have opened a connection to syslog (openlog()) then we wrote to syslog using (syslog()) and finally we close the connection (closelog()) . You might mention what is setlogmask and all the input parameters such as LOG_INFO , LOG_NOTICE . Well a lets go through with the basics. setlogmask() lets us choose what to log and what not to log even if the syslog() function is called. This is handy as we leave alot of messages when debugging but we want to turn off the messages when we go live with our daemon. Therefore instead of going through your code and commenting out all the notice entries, we just change the log mask.

Читайте также:  Включить turbo boost linux

If you have never worked with syslog in C++, its a good idea to familiarize yourself with it. You can find more about syslog commands Here if you are interested.

Ok so now you have logged your messages where to find them. In Ubuntu or Fedora logs are located under /var/logs/messages so once you have compiled your program and ran it try this command(Last 100 lines of the file message ).

tail -n 100 /var/log/messages 

The Daemon

We have established our process and managed our logging, now we want to add some daemon code. The best place to start is by looking at our daemon code below.

#include #include #include #include #include #include #include #include #include using namespace std; #define DAEMON_NAME "vdaemon" void process() < syslog (LOG_NOTICE, "Writing to my Syslog"); >int main(int argc, char *argv[]) < //Set our Logging Mask and open the Log setlogmask(LOG_UPTO(LOG_NOTICE)); openlog(DAEMON_NAME, LOG_CONS | LOG_NDELAY | LOG_PERROR | LOG_PID, LOG_USER); syslog(LOG_INFO, "Entering Daemon"); pid_t pid, sid; //Fork the Parent Process pid = fork(); if (pid < 0) < exit(EXIT_FAILURE); >//We got a good pid, Close the Parent Process if (pid > 0) < exit(EXIT_SUCCESS); >//Change File Mask umask(0); //Create a new Signature Id for our child sid = setsid(); if (sid < 0) < exit(EXIT_FAILURE); >//Change Directory //If we cant find the directory we exit with failure. if ((chdir("/")) < 0) < exit(EXIT_FAILURE); >//Close Standard File Descriptors close(STDIN_FILENO); close(STDOUT_FILENO); close(STDERR_FILENO); //---------------- //Main Process //---------------- while(true) < process(); //Run our Process sleep(60); //Sleep for 60 seconds >//Close the log closelog (); > 

Looks like alot of code but lets look at some key factors. If you note that our actual daemon code is only three lines long. Basically an infinite loop with our process function, and a sleep command. Where as the rest of the code is preparing our application to run as a daemon. Lets walk through some of the commands in brief.

fork

Forking is a method of creating a child process. When we run the command fork() we are actually creating a child clone of our program. From our above code we try to fork our parent process. If the return value is less than 0 then something went wrong. Therefore we exit our program, otherwise we exit our parent and continue on with our child process. This can get confusing, For more information refer to the reference in the bottom of the tutorial.

Читайте также:  Команда удаления приложения linux

umask

When ever you create a new file in linux, you need premissions to read or write them. The umask command specifies this processes permissions. This is a complicated one to dig into. You can read more in the reference page.

setsid

setsid is otherwise short for Set Session Id. Because we have fork-ed our process we need to give our new process its own unique process-id, therefore we run this function to determine a new process-id.

chdir

This command changes the current working directory. In linux an equivilent to this function will be cd / . This will be the working directory of the process. The reason we choose / or root as a working directory is because, it is the one directory that globally exists throughout all linux types. You can however change the directory to your suiting.

close

Because daemon is a background process we want to close all Input and Output. So if you look at the close function we have closed all standard file descriptors.

sleep

The sleep command sends the process to sleep for the defined number of seconds. Think about this number whenever you are designing your daemon. A small number will require more processing power as your CPU, is dealing with more processes in a short space of time.

Fin

Im sure before you get to this part. you have already tested your daemon, so I leave you with some final words of advice.

Learn more, Use the Devon Watson Guide to writing a Daemon, to fill in some black holes that I may have left out. Also not a bad idea to try the Peter Lambardo example to understanding how to handle signals and making sure your daemon always shuts down cleanly.

Whenever creating your process function: be defensive, be defensive and be more defensive; and when you have secured it try going back and be very very defensive. And Enjoy

Hope the above helps in some way of understanding about daemons in Linux based operating system. However this doesn’t end here. Part 2 explains how to create a init.d script to control the starting and stopping of this daemon.

Resources

By Shahmir Javaid

Next

Delete Query with Limit in Mysql

Ever wondered how to perform a delete query with limit in MySQL, I finally had some time to solve this problem, and posted it for the world to see. Improvement and suggestions are highly recommended.

Previous

Syntax Highlighter Code

A JavaScript based syntax highlighter library, developed by Alex Gorbatchev.

© 2011 Shahmir Javaid — http://shahmirj.com/blog/9

Danilo Carvalho

Hi, Shahmir, very nice guide. Any chance the Part 2 explaining about the init.d scripts is coming out soon? Haven’t been able to find a decent guide on it. Either way, thanks for this one.

Shahmir Javaid

I can do that, give me the weekend. Il muster an easy init.d script which you can transfer easily to your daemon.

Источник

Оцените статью
Adblock
detector