3

I have a simple system (running on Debian) that works by invoking a script from /etc/init.d/rc.local

At the bottom of rc.local I call myScript.sh who sets up some things, and then starts a binary like this:

./myBinary > /dev/null 2>&1 &

It runs fine for a while, but after some time myBinary exits. However if I modify the script to do this:

nohup ./myBinary > /dev/null 2>&1 &

It runs fine (I tested it for about 8 hours).

From my understanding SIGHUP is sent when the terminal that controls the process is closed, and nohup causes that signal to be ignored.

So seemingly, my software is being sent SIGHUP, but I don't understand why. Can someone explain?

Edit: here is the actual script

#!/bin/bash
clear
/home/pi/hdmi-switcher/hdmi-switcher version
/home/pi/hdmi-switcher/update.sh
printf "Starting switching daemon..."
cd /home/pi/hdmi-switcher
./hdmi-switcher > /dev/null 2>&1 &
printf "\tOK\n"
printf "Starting video... "
sleep 5
printf "\tOK\n"
omxplayer --loop --no-osd -b -o both /home/pi/hdmi-switcher/video.mp4 > /dev/null 2>&1
clear

The thing that dies is hdmi-switcher. omxplayer has no problems.

  • Seems that rc.local runs just long enough to call your script and then dies. That means the parent shell is gone and you lose whatever environment variables were set under that parent. Does your script depend on such environment variables? linuxquestions.org/questions/linux-general-1/… – iyrin Apr 17 '15 at 6:23
  • Nope, I've updated the question with the actual script. – Cameron Ball Apr 17 '15 at 6:35
2

If you call the binary in /etc/rc.local, notice that rc.local is called as /bin/sh -e. -e means that the script immediately exits if any untested command fails in it. You call the binary in the background and another command in the script may exit with an exit code that is not 0. That has the effect that your binary is sighup-ed.

An untested command according to the manpage:

The exit status of a command is considered to be explicitly tested if the command is used to control an if, elif, while, or until; or if the command is the left hand operand of an “&&” or “||” operator.

$ command                   # untested
$ command || echo failed    # tested
$ if [ command ]; then...   # tested, also while and until loops
$ [ command ] && echo ...   # tested

Besides, the rc.local file is the wrong place for such a thing, you should not use it anymore, it's deprecated. Instead, you should use your systems startup configuration mechanism. Since you use Debian, it's SysV-init-style. To do that cleanly, create a script in /etc/init.d/ that accepts at least start and stop as argument to start and stop your binary/daemon/task. To begin there is a skeleton script, which you can use as template in /etc/init.d/skeleton to write that script.

  • What is an untested command? – Cameron Ball Apr 17 '15 at 6:36
  • @CameronBall see my edit – chaos Apr 17 '15 at 6:39
  • OK awesome. That makes more sense. Can you see any reason why my binary would die, but not omxplayer (I edited the question with the content of the script). – Cameron Ball Apr 17 '15 at 7:21
  • unix.stackexchange.com/a/480897/5132 /etc/init.d/skeleton is not the way. – JdeBP Nov 10 '18 at 4:51

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.