I’ve written small gui-frontend in Python that lets users play internet radio channels. The program uses Pythons subprocess() to initizalize mplayer in order to tune into a channel, e.g.:
runn = "mplayer http://77.111.88.131:8010"
p = subprocess.Popen(runn, shell=True)
pid = int(p.pid)
wait = os.waitpid(p.pid, 1)
Then saves p.pid, and when a user wants to stop listening the following code is used:
os.kill(p.pid, 9)
This works perfectly in OpenSUSE, but not in Ubuntu. It seems that Ubuntu actually starts two separate processes. Terminal output:
Opensuse 11.3:
$ pgrep mplayer
22845
Ubuntu 10.04:
$ pgrep mplayer
22846
22847
This also applies when running other programs. Does anyone know why? I really want this app to run on all distros, so any help is deeply appreciated.
Try this:
My guess as to what’s going on is this…
When you say
shell=Truesubprocess actually starts this commandsh -c "your string". Theshcommand then interprets your string and runs the command as if you’d typed that in at the shell prompt (more or less). Normally this would result in two processes. One would besh -c "your string"and the other would be it’s child,your string.Some versions of
shhave an optimization in which they will automaticallyexecthe command under certain conditions. They do it if it’s the last commandshis going to run andshhas no other reason to stick around. When usingsh -cto run a command, this will almost always result in that invocation ofshreplacing itself with the command it’s running, thereby resulting in one process.In my opinion it’s a really, really bad idea to ever invoke
subprocess.Popenwithshell=True. You are opening yourself up for a ton of security issues by doing that, and generally less predictable behavior because shell metacharacters are interpreted bysh -c.