Fawkes API  Fawkes Development Version
main_thread.h
00001 
00002 /***************************************************************************
00003  *  main_thread.h - Fawkes main thread
00004  *
00005  *  Created: Thu Nov  2 16:46:37 2006
00006  *  Copyright  2006-2008  Tim Niemueller [www.niemueller.de]
00007  *
00008  ****************************************************************************/
00009 
00010 /*  This program is free software; you can redistribute it and/or modify
00011  *  it under the terms of the GNU General Public License as published by
00012  *  the Free Software Foundation; either version 2 of the License, or
00013  *  (at your option) any later version. A runtime exception applies to
00014  *  this software (see LICENSE.GPL_WRE file mentioned below for details).
00015  *
00016  *  This program is distributed in the hope that it will be useful,
00017  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00018  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00019  *  GNU Library General Public License for more details.
00020  *
00021  *  Read the full text in the LICENSE.GPL_WRE file in the doc directory.
00022  */
00023 
00024 #ifndef __LIBS_BASEAPP_MAIN_THREAD_H_
00025 #define __LIBS_BASEAPP_MAIN_THREAD_H_
00026 
00027 #include <baseapp/thread_manager.h>
00028 #include <core/threading/thread.h>
00029 #include <aspect/mainloop/employer.h>
00030 #include <aspect/blocked_timing.h>
00031 #include <utils/system/signal.h>
00032 #include <logging/multi.h>
00033 
00034 #include <list>
00035 #include <string>
00036 #include <getopt.h>
00037 
00038 namespace fawkes {
00039 #if 0 /* just to make Emacs auto-indent happy */
00040 }
00041 #endif
00042 class Configuration;
00043 class SQLiteConfiguration;
00044 class ConfigNetworkHandler;
00045 class NetworkLogger;
00046 class Clock;
00047 class TimeWait;
00048 class AspectManager;
00049 class PluginManager;
00050 class Time;
00051 class PluginNetworkHandler;
00052 class InterruptibleBarrier;
00053 class Barrier;
00054 class Mutex;
00055 class ThreadManager;
00056 class FawkesNetworkManager;
00057 
00058 class FawkesMainThread
00059 : public Thread,
00060   public MainLoopEmployer
00061 {
00062  public:
00063   FawkesMainThread(SQLiteConfiguration *config,
00064                    MultiLogger *multi_logger,
00065                    ThreadManager *thread_manager,
00066                    PluginManager *plugin_manager,
00067                    const char *load_plugins,
00068                    const char *default_plugin = 0);
00069   virtual ~FawkesMainThread();
00070 
00071   virtual void once();
00072   virtual void loop();
00073 
00074   virtual void set_mainloop_thread(Thread *mainloop_thread);
00075 
00076   void full_start();
00077 
00078   MultiLogger *  logger() const;
00079 
00080   class Runner : public SignalHandler {
00081   public:
00082     Runner(FawkesMainThread *fmt, bool register_signals = true);
00083     ~Runner();
00084     void run();
00085     void handle_signal(int signum);
00086   private:
00087     FawkesMainThread *__fmt;
00088     Mutex            *__init_mutex;
00089     bool              __init_running;
00090     bool              __init_quit;
00091     bool              __sigint_running;
00092     bool              __register_signals;
00093   };
00094 
00095  /** Stub to see name in backtrace for easier debugging. @see Thread::run() */
00096  protected: virtual void run() { Thread::run(); }
00097 
00098  private:
00099   void destruct();
00100 
00101   inline void safe_wake(BlockedTimingAspect::WakeupHook hook, unsigned int timeout_usec)
00102   {
00103     try {
00104       __thread_manager->wakeup_and_wait(hook, timeout_usec);
00105     } catch (Exception &e) {
00106       if (__enable_looptime_warnings) {
00107         //__multi_logger->log_error("FawkesMainThread",
00108         //                          "Error while processing hook %s, exception follows",
00109         //                          BlockedTimingAspect::blocked_timing_hook_to_string(hook));
00110         __multi_logger->log_error("FawkesMainThread", e);
00111       }
00112 
00113     }
00114   }
00115 
00116 
00117   Configuration        *__config;
00118   MultiLogger          *__multi_logger;
00119   NetworkLogger        *__network_logger;
00120   Clock                *__clock;
00121   TimeWait             *__time_wait;
00122   AspectManager        *__aspect_manager;
00123 
00124   Barrier              *__init_barrier;
00125   Thread               *__mainloop_thread;
00126   Mutex                *__mainloop_mutex;
00127   InterruptibleBarrier *__mainloop_barrier;
00128 
00129   char                 *__default_plugin;
00130   char                 *__load_plugins;
00131 
00132   SQLiteConfiguration  *__sqlite_conf;
00133   ThreadManager        *__thread_manager;
00134   PluginManager        *__plugin_manager;
00135   Mutex                *__plugin_mutex;
00136   FawkesNetworkManager *__network_manager;
00137 
00138   std::list<std::string>        __recovered_threads;
00139   unsigned int                  __desired_loop_time_usec;
00140   float                         __desired_loop_time_sec;
00141   unsigned int                  __max_thread_time_usec;
00142   unsigned int                  __max_thread_time_nanosec;
00143   Time                         *__loop_start;
00144   Time                         *__loop_end;
00145   bool                          __enable_looptime_warnings;
00146 
00147 };
00148 
00149 } // end namespace fawkes
00150 
00151 #endif