src/ident/Makefile \
src/ip/Makefile \
src/log/Makefile \
+ src/ipc/Makefile \
contrib/Makefile \
snmplib/Makefile \
icons/Makefile \
LoadableModules.h \
LoadableModules.cc
-SUBDIRS = base comm eui acl fs repl auth ip icmp ident log
+SUBDIRS = base comm eui acl fs repl auth ip icmp ident log ipc
if USE_ADAPTATION
SUBDIRS += adaptation
auth/libauth.la \
acl/libapi.la \
ip/libip.la \
- fs/libfs.la
+ fs/libfs.la \
+ ipc/libipc.la
EXTRA_PROGRAMS = \
DiskIO/DiskDaemon/diskd \
#include "StoreFileSystem.h"
#include "SwapDir.h"
#include "wordlist.h"
+#include "ipc/Kids.h"
#if HAVE_GLOB_H
#include <glob.h>
self_destruct();
}
- extern void update_port(unsigned short* port);
- update_port(&port);
-
if (NULL == host) {
s->s.SetAnyAddr();
s->s.SetPort(port);
extern const char *external_acl_message; /* NULL */
extern int opt_send_signal; /* -1 */
extern int opt_no_daemon; /* 0 */
- extern char KidName[NAME_MAX];
- extern int KidIdentifier; /* 0 */
#ifdef __cplusplus
--- /dev/null
+/*
+ * $Id$
+ *
+ * DEBUG: section 54 Interprocess Communication
+ *
+ */
+
+#include "config.h"
+#include "ipc/Kid.h"
+
+Kid::Kid():
+ badFailures(0),
+ pid(-1),
+ startTime(0),
+ isRunning(false)
+{
+}
+
+Kid::Kid(const String& kid_name):
+ theName(kid_name),
+ badFailures(0),
+ pid(-1),
+ startTime(0),
+ isRunning(false)
+{
+}
+
+/// called when this kid got started, records PID
+void Kid::start(pid_t cpid)
+{
+ assert(!running());
+ assert(cpid > 0);
+
+ isRunning = true;
+ pid = cpid;
+ time(&startTime);
+}
+
+/// called when kid terminates, sets exiting status
+void Kid::stop(status_type exitStatus)
+{
+ assert(running());
+ assert(startTime != 0);
+
+ isRunning = false;
+
+ time_t stop_time;
+ time(&stop_time);
+ if ((stop_time - startTime) < fastFailureTimeLimit)
+ badFailures++;
+ else
+ badFailures = 0; // the failures are not "frequent" [any more]
+
+ status = exitStatus;
+}
+
+/// returns true if tracking of kid is stopped
+bool Kid::running() const
+{
+ return isRunning;
+}
+
+/// returns current pid for a running kid and last pid for a stopped kid
+pid_t Kid::getPid() const
+{
+ assert(pid > 0);
+ return pid;
+}
+
+/// whether the failures are "repeated and frequent"
+bool Kid::hopeless() const
+{
+ return badFailures > badFailureLimit;
+}
+
+/// returns true if the process terminated normally
+bool Kid::calledExit() const
+{
+ return (pid > 0) && !running() && WIFEXITED(status);
+}
+
+/// returns the exit status of the process
+int Kid::exitStatus() const
+{
+ return WEXITSTATUS(status);
+}
+
+/// whether the process exited with a given exit status code
+bool Kid::calledExit(int code) const
+{
+ return calledExit() && (exitStatus() == code);
+}
+
+/// whether the process exited with code 0
+bool Kid::exitedHappy() const
+{
+ return calledExit(0);
+}
+
+/// returns true if the kid was terminated by a signal
+bool Kid::signaled() const
+{
+ return (pid > 0) && !running() && WIFSIGNALED(status);
+}
+
+/// returns the number of the signal that caused the kid to terminate
+int Kid::termSignal() const
+{
+ return WTERMSIG(status);
+}
+
+/// whether the process was terminated by a given signal
+bool Kid::signaled(int sgnl) const
+{
+ return signaled() && (termSignal() == sgnl);
+}
+
+/// returns kid name
+const String& Kid::name() const
+{
+ return theName;
+}
--- /dev/null
+/*
+ * $Id$
+ *
+ */
+
+#ifndef SQUID_IPC_KID_H
+#define SQUID_IPC_KID_H
+
+#include "SquidString.h"
+
+
+/// Squid child, including current forked process info and
+/// info persistent across restarts
+class Kid
+{
+public:
+#ifdef _SQUID_NEXT_
+ typedef union wait status_type;
+#else
+ typedef int status_type;
+#endif
+
+ /// keep restarting until the number of bad failures exceed this limit
+ enum { badFailureLimit = 4 };
+
+ /// slower start failures are not "frequent enough" to be counted as "bad"
+ enum { fastFailureTimeLimit = 10 }; // seconds
+
+public:
+ Kid();
+
+ Kid(const String& kid_name);
+
+ /// called when this kid got started, records PID
+ void start(pid_t cpid);
+
+ /// called when kid terminates, sets exiting status
+ void stop(status_type exitStatus);
+
+ /// returns true if tracking of kid is stopped
+ bool running() const;
+
+ /// returns current pid for a running kid and last pid for a stopped kid
+ pid_t getPid() const;
+
+ /// whether the failures are "repeated and frequent"
+ bool hopeless() const;
+
+ /// returns true if the process terminated normally
+ bool calledExit() const;
+
+ /// returns the exit status of the process
+ int exitStatus() const;
+
+ /// whether the process exited with a given exit status code
+ bool calledExit(int code) const;
+
+ /// whether the process exited with code 0
+ bool exitedHappy() const;
+
+ /// returns true if the kid was terminated by a signal
+ bool signaled() const;
+
+ /// returns the number of the signal that caused the kid to terminate
+ int termSignal() const;
+
+ /// whether the process was terminated by a given signal
+ bool signaled(int sgnl) const;
+
+ /// returns kid name
+ const String& name() const;
+
+private:
+ // Information preserved across restarts
+ String theName; ///< process name
+ int badFailures; ///< number of "repeated frequent" failures
+
+ // Information specific to a running or stopped kid
+ pid_t pid; ///< current (for a running kid) or last (for stopped kid) PID
+ time_t startTime; ///< last start time
+ bool isRunning; ///< whether the kid is assumed to be alive
+ status_type status; ///< exit status of a stopped kid
+};
+
+#endif /* SQUID_IPC_KID_H */
--- /dev/null
+/*
+ * $Id$
+ *
+ * DEBUG: section 54 Interprocess Communication
+ *
+ */
+
+#include "config.h"
+#include "ipc/Kids.h"
+
+Kids TheKids;
+char KidName[NAME_MAX];
+int KidIdentifier;
+
+Kids::Kids()
+{
+}
+
+/// maintain n kids
+void Kids::init(size_t n)
+{
+ assert(n > 0);
+
+ if (storage.size() > 0)
+ storage.clean();
+
+ storage.reserve(n);
+
+ for (size_t i = 1; i <= n; ++i) {
+ char kid_name[32];
+ snprintf(kid_name, sizeof(kid_name), "(squid-%d)", (int)i);
+ storage.push_back(Kid(kid_name));
+ }
+}
+
+/// returns kid by pid
+Kid* Kids::find(pid_t pid)
+{
+ assert(pid > 0);
+ assert(count() > 0);
+
+ for (size_t i = 0; i < storage.size(); ++i) {
+ if (storage[i].getPid() == pid)
+ return &storage[i];
+ }
+ return NULL;
+}
+
+/// returns the kid by index, useful for kids iteration
+Kid& Kids::get(size_t i)
+{
+ assert(i >= 0 && i < count());
+ return storage[i];
+}
+
+/// whether all kids are hopeless
+bool Kids::allHopeless() const
+{
+ for (size_t i = 0; i < storage.size(); ++i) {
+ if (!storage[i].hopeless())
+ return false;
+ }
+ return true;
+}
+
+/// whether all kids called exited happy
+bool Kids::allExitedHappy() const
+{
+ for (size_t i = 0; i < storage.size(); ++i) {
+ if (!storage[i].exitedHappy())
+ return false;
+ }
+ return true;
+}
+
+/// whether all kids died from a given signal
+bool Kids::allSignaled(int sgnl) const
+{
+ for (size_t i = 0; i < storage.size(); ++i) {
+ if (!storage[i].signaled(sgnl))
+ return false;
+ }
+ return true;
+}
+
+/// returns the number of kids
+size_t Kids::count() const
+{
+ return storage.size();
+}
--- /dev/null
+/*
+ * $Id$
+ *
+ */
+
+#ifndef SQUID_IPC_KIDS_H
+#define SQUID_IPC_KIDS_H
+
+#include "Array.h"
+#include "ipc/Kid.h"
+
+
+/// a collection of kids
+class Kids
+{
+public:
+ Kids ();
+
+private:
+ Kids (const Kids&); ///< not implemented
+ Kids& operator= (const Kids&); ///< not implemented
+
+public:
+ /// maintain n kids
+ void init(size_t n);
+
+ /// returns kid by pid
+ Kid* find(pid_t pid);
+
+ /// returns the kid by index, useful for kids iteration
+ Kid& get(size_t i);
+
+ /// whether all kids are hopeless
+ bool allHopeless() const;
+
+ /// whether all kids called exited happy
+ bool allExitedHappy() const;
+
+ /// whether all kids died from a given signal
+ bool allSignaled(int sgnl) const;
+
+ /// returns the number of kids
+ size_t count() const;
+
+private:
+ Vector<Kid> storage;
+};
+
+extern Kids TheKids; ///< All kids being maintained
+
+extern char KidName[NAME_MAX]; ///< current Squid process name (e.g., squid2)
+extern int KidIdentifier; ///< current Squid process number (e.g., 4)
+
+
+#endif /* SQUID_IPC_KIDS_H */
--- /dev/null
+include $(top_srcdir)/src/Common.am
+include $(top_srcdir)/src/TestHeaders.am
+
+noinst_LTLIBRARIES = libipc.la
+
+libipc_la_SOURCES = \
+ Kid.cc \
+ Kid.h \
+ Kids.cc \
+ Kids.h
#include "StoreFileSystem.h"
#include "DiskIO/DiskIOModule.h"
#include "comm.h"
+#include "ipc/Kids.h"
#if USE_EPOLL
#include "comm_epoll.h"
#endif
return 1;
}
-/// XXX: temporary hack to avoid http_port conflicts among listening kids
-void update_port(unsigned short* port)
-{
- if (KidIdentifier > 0)
- *port += KidIdentifier - 1;
-}
-
-/// Squid child, including current forked process info and
-/// info persistent across restarts
-class Kid
-{
-public:
-#ifdef _SQUID_NEXT_
- typedef union wait status_type;
-#else
- typedef int status_type;
-#endif
-
- /// keep restarting until the number of bad failures exceed this limit
- enum { badFailureLimit = 4 };
-
- /// slower start failures are not "frequent enough" to be counted as "bad"
- enum { fastFailureTimeLimit = 10 }; // seconds
-
-public:
- Kid():
- badFailures(0),
- pid(-1),
- startTime(0),
- isRunning(false)
- {
- }
-
- Kid(const String& kid_name):
- theName(kid_name),
- badFailures(0),
- pid(-1),
- startTime(0),
- isRunning(false)
- {
- }
-
- /// called when this kid got started, records PID
- void start(pid_t cpid)
- {
- assert(!running());
- assert(cpid > 0);
-
- isRunning = true;
- pid = cpid;
- time(&startTime);
- }
-
- /// called when kid terminates, sets exiting status
- void stop(status_type exitStatus)
- {
- assert(running());
- assert(startTime != 0);
-
- isRunning = false;
-
- time_t stop_time;
- time(&stop_time);
- if ((stop_time - startTime) < fastFailureTimeLimit)
- badFailures++;
- else
- badFailures = 0; // the failures are not "frequent" [any more]
-
- status = exitStatus;
- }
-
- /// returns true if tracking of kid is stopped
- bool running() const
- {
- return isRunning;
- }
-
- /// returns current pid for a running kid and last pid for a stopped kid
- pid_t getPid() const
- {
- assert(pid > 0);
- return pid;
- }
-
- /// whether the failures are "repeated and frequent"
- bool hopeless() const
- {
- return badFailures > badFailureLimit;
- }
-
- /// returns true if the process terminated normally
- bool calledExit() const
- {
- return (pid > 0) && !running() && WIFEXITED(status);
- }
-
- /// returns the exit status of the process
- int exitStatus() const
- {
- return WEXITSTATUS(status);
- }
-
- /// whether the process exited with a given exit status code
- bool calledExit(int code) const
- {
- return calledExit() && (exitStatus() == code);
- }
-
- /// whether the process exited with code 0
- bool exitedHappy() const
- {
- return calledExit(0);
- }
-
- /// returns true if the kid was terminated by a signal
- bool signaled() const
- {
- return (pid > 0) && !running() && WIFSIGNALED(status);
- }
-
- /// returns the number of the signal that caused the kid to terminate
- int termSignal() const
- {
- return WTERMSIG(status);
- }
-
- /// whether the process was terminated by a given signal
- bool signaled(int sgnl) const
- {
- return signaled() && (termSignal() == sgnl);
- }
-
- /// returns kid name
- const String& name() const
- {
- return theName;
- }
-
-private:
- // Information preserved across restarts
- String theName; ///< process name
- int badFailures; ///< number of "repeated frequent" failures
-
- // Information specific to a running or stopped kid
- pid_t pid; ///< current (for a running kid) or last (for stopped kid) PID
- time_t startTime; ///< last start time
- bool isRunning; ///< whether the kid is assumed to be alive
- status_type status; ///< exit status of a stopped kid
-};
-
-/// a collection of kids
-class Kids
-{
-public:
- Kids ():
- storage()
- {
- }
-
-private:
- Kids (const Kids&); ///< not implemented
- Kids& operator= (const Kids&); ///< not implemented
-
-public:
- /// maintain n kids
- void init(size_t n)
- {
- assert(n > 0);
-
- if (storage.size() > 0)
- storage.clean();
-
- storage.reserve(n);
-
- for (size_t i = 1; i <= n; ++i) {
- char kid_name[32];
- snprintf(kid_name, sizeof(kid_name), "(squid-%d)", (int)i);
- storage.push_back(Kid(kid_name));
- }
- }
-
- /// returns kid by pid
- Kid* find(pid_t pid)
- {
- assert(pid > 0);
- assert(count() > 0);
-
- for (size_t i = 0; i < storage.size(); ++i) {
- if (storage[i].getPid() == pid)
- return &storage[i];
- }
- return NULL;
- }
-
- /// returns the kid by index, useful for kids iteration
- Kid& get(size_t i)
- {
- assert(i >= 0 && i < count());
- return storage[i];
- }
-
- /// whether all kids are hopeless
- bool allHopeless() const
- {
- for (size_t i = 0; i < storage.size(); ++i) {
- if (!storage[i].hopeless())
- return false;
- }
- return true;
- }
-
- /// whether all kids called exited happy
- bool allExitedHappy() const
- {
- for (size_t i = 0; i < storage.size(); ++i) {
- if (!storage[i].exitedHappy())
- return false;
- }
- return true;
- }
-
- /// whether all kids died from a given signal
- bool allSignaled(int sgnl) const
- {
- for (size_t i = 0; i < storage.size(); ++i) {
- if (!storage[i].signaled(sgnl))
- return false;
- }
- return true;
- }
-
- /// returns the number of kids
- size_t count() const
- {
- return storage.size();
- }
-
-private:
- Vector<Kid> storage;
-};
-
-static Kids TheKids; ///< All kids being maintained
-
static void
watch_child(char *argv[])
{