This is the mail archive of the
frysk@sources.redhat.com
mailing list for the frysk project.
Kill and refresh
- From: Mark Wielaard <mark at klomp dot org>
- To: frysk at sources dot redhat dot com
- Date: Thu, 13 Jul 2006 18:11:04 +0200
- Subject: Kill and refresh
Hi,
I had some issues trying to write some tests that I tracked down to some
TaskStates and the LinuxHost not handling disappearing/killed processes
nicely. I tried to write a self contained test case, but I found it only
triggered when running the EventLoop in its own Thread. This probably
means that I haven't pinned down the real sequence of events causing
this. Or maybe my idea of how process creation, Host process discovery
and process disappearance should interact is not correct.
Attached is a testcase that shows (at least for me) that a Task in the
detached state can get a handleTerminatedEvent() call that it doesn't
know how to handle.
Could someone take a look/try this testcase out?
And tell me whether it also fails for them and/or whether this is
supposed to work or not?
Thanks,
Mark
Index: frysk/proc/TestKill.java
===================================================================
RCS file: frysk/proc/TestKill.java
diff -N frysk/proc/TestKill.java
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ frysk/proc/TestKill.java 13 Jul 2006 16:02:27 -0000
@@ -0,0 +1,187 @@
+// This file is part of the program FRYSK.
+//
+// Copyright 2006, Red Hat Inc.
+//
+// FRYSK is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License as published by
+// the Free Software Foundation; version 2 of the License.
+//
+// FRYSK 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 FRYSK; if not, write to the Free Software Foundation,
+// Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// In addition, as a special exception, Red Hat, Inc. gives You the
+// additional right to link the code of FRYSK with code not covered
+// under the GNU General Public License ("Non-GPL Code") and to
+// distribute linked combinations including the two, subject to the
+// limitations in this paragraph. Non-GPL Code permitted under this
+// exception must only link to the code of FRYSK through those well
+// defined interfaces identified in the file named EXCEPTION found in
+// the source code files (the "Approved Interfaces"). The files of
+// Non-GPL Code may instantiate templates or use macros or inline
+// functions from the Approved Interfaces without causing the
+// resulting work to be covered by the GNU General Public
+// License. Only Red Hat, Inc. may make changes or additions to the
+// list of Approved Interfaces. You must obey the GNU General Public
+// License in all respects for all of the FRYSK code and other code
+// used in conjunction with FRYSK except the Non-GPL Code covered by
+// this exception. If you modify this file, you may extend this
+// exception to your version of the file, but you are not obligated to
+// do so. If you do not wish to provide this exception without
+// modification, you must delete this exception statement from your
+// version and license this file solely under the GPL without
+// exception.
+
+package frysk.proc;
+
+import frysk.sys.*;
+import frysk.event.*;
+
+/**
+ * Check that a program can be killed/disappear without the
+ * core going crazy.
+ */
+public class TestKill
+ extends TestLib
+{
+
+ // The eventloop that needs to be stopped at the end of the test.
+ EventLoopRunner eventloop;
+
+ // Process ids that need to be cleaned up.
+ int pid1, pid2;
+
+ // Monitor that gets notified as soon as some event occured.
+ Object monitor = new Object();
+
+ public void setUp()
+ {
+ pid1 = pid2 = -1;
+ eventloop = new EventLoopRunner();
+ eventloop.start();
+ }
+
+ public void tearDown()
+ {
+ try
+ {
+ if (pid1 != -1)
+ Signal.kill(pid1, Sig.KILL);
+ }
+ catch(Errno e)
+ {
+ // Already killed
+ }
+
+ try
+ {
+ if (pid2 != -1)
+ Signal.kill(pid2, Sig.KILL);
+ }
+ catch(Errno e)
+ {
+ // Already killed
+ }
+
+ eventloop.requestStop();
+ }
+
+ public void testKill()
+ {
+ // Create a detached process.
+ String command = getExecPrefix() + "funit-loop";
+ pid1 = Fork.daemon (null, null, null, new String[] { command });
+ ProcId procId1 = new ProcId(pid1);
+
+ // Try to find it
+ Manager.host.requestRefreshXXX(true);
+
+ // No, lets kill it...
+ Signal.kill(pid1, Sig.KILL);
+
+ // Just create another.
+ command = getExecPrefix() + "funit-loop";
+ pid2 = Fork.daemon (null, null, null, new String[] { command });
+ ProcId procId2 = new ProcId(pid2);
+
+ // Find that...
+ Manager.host.requestRefreshXXX(true);
+
+ // Make sure the event loop has ran at least once.
+ EventTrigger trigger = new EventTrigger();
+ Manager.eventLoop.add(trigger);
+ synchronized(monitor)
+ {
+ while (! trigger.isTriggered())
+ {
+ try
+ {
+ monitor.wait();
+ }
+ catch (InterruptedException ie)
+ {
+ // ignored.
+ }
+ }
+ }
+
+ Proc proc = Manager.host.getProc(procId1);
+ assertNull(proc);
+
+ proc = Manager.host.getProc(procId2);
+ assertNotNull(proc);
+ assertEquals(pid2, proc.getPid());
+ }
+
+ class EventLoopRunner extends Thread
+ {
+ private boolean stopped;
+
+ public void run()
+ {
+ stopped = false;
+ try
+ {
+ Manager.eventLoop.run();
+ }
+ finally
+ {
+ stopped = true;
+ }
+ }
+
+ public void requestStop()
+ {
+ Manager.eventLoop.requestStop();
+ }
+
+ public boolean isStopped()
+ {
+ return stopped;
+ }
+ }
+
+ class EventTrigger implements Event
+ {
+ private boolean triggered;
+ public void execute()
+ {
+ synchronized (monitor)
+ {
+ triggered = true;
+ monitor.notifyAll();
+ }
+ }
+
+ public boolean isTriggered()
+ {
+ return triggered;
+ }
+ }
+
+}
Index: frysk/pkglibexecdir/funit-loop.c
===================================================================
RCS file: frysk/pkglibexecdir/funit-loop.c
diff -N frysk/pkglibexecdir/funit-loop.c
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ frysk/pkglibexecdir/funit-loop.c 13 Jul 2006 16:02:27 -0000
@@ -0,0 +1,52 @@
+// This file is part of the program FRYSK.
+//
+// Copyright 2005, 2006, Red Hat Inc.
+//
+// FRYSK is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License as published by
+// the Free Software Foundation; version 2 of the License.
+//
+// FRYSK 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 FRYSK; if not, write to the Free Software Foundation,
+// Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+//
+// In addition, as a special exception, Red Hat, Inc. gives You the
+// additional right to link the code of FRYSK with code not covered
+// under the GNU General Public License ("Non-GPL Code") and to
+// distribute linked combinations including the two, subject to the
+// limitations in this paragraph. Non-GPL Code permitted under this
+// exception must only link to the code of FRYSK through those well
+// defined interfaces identified in the file named EXCEPTION found in
+// the source code files (the "Approved Interfaces"). The files of
+// Non-GPL Code may instantiate templates or use macros or inline
+// functions from the Approved Interfaces without causing the
+// resulting work to be covered by the GNU General Public
+// License. Only Red Hat, Inc. may make changes or additions to the
+// list of Approved Interfaces. You must obey the GNU General Public
+// License in all respects for all of the FRYSK code and other code
+// used in conjunction with FRYSK except the Non-GPL Code covered by
+// this exception. If you modify this file, you may extend this
+// exception to your version of the file, but you are not obligated to
+// do so. If you do not wish to provide this exception without
+// modification, you must delete this exception statement from your
+// version and license this file solely under the GPL without
+// exception.
+
+#include <stdlib.h>
+#include <unistd.h>
+
+int
+main (int argc, char **argv)
+{
+ // Happily count to infinity
+ int i = 0;
+ while(1)
+ i++;
+
+ return 0;
+}