PTLib  Version 2.10.4
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
pprocess.h
Go to the documentation of this file.
1 /*
2  * pprocess.h
3  *
4  * Operating System Process (running program executable) class.
5  *
6  * Portable Windows Library
7  *
8  * Copyright (c) 1993-1998 Equivalence Pty. Ltd.
9  *
10  * The contents of this file are subject to the Mozilla Public License
11  * Version 1.0 (the "License"); you may not use this file except in
12  * compliance with the License. You may obtain a copy of the License at
13  * http://www.mozilla.org/MPL/
14  *
15  * Software distributed under the License is distributed on an "AS IS"
16  * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
17  * the License for the specific language governing rights and limitations
18  * under the License.
19  *
20  * The Original Code is Portable Windows Library.
21  *
22  * The Initial Developer of the Original Code is Equivalence Pty. Ltd.
23  *
24  * Portions are Copyright (C) 1993 Free Software Foundation, Inc.
25  * All Rights Reserved.
26  *
27  * Contributor(s): ______________________________________.
28  *
29  * $Revision: 26758 $
30  * $Author: rjongbloed $
31  * $Date: 2011-12-06 18:52:22 -0600 (Tue, 06 Dec 2011) $
32  */
33 
34 #ifndef PTLIB_PROCESS_H
35 #define PTLIB_PROCESS_H
36 
37 #ifdef P_USE_PRAGMA
38 #pragma interface
39 #endif
40 
41 #include <ptlib/mutex.h>
43 #include <ptlib/thread.h>
44 #include <ptlib/pfactory.h>
45 
46 #include <queue>
47 #include <set>
48 
55 #ifdef P_VXWORKS
56 #define PCREATE_PROCESS(cls) \
57  cls instance; \
58  instance.InternalMain();
59 #elif defined(P_RTEMS)
60 #define PCREATE_PROCESS(cls) \
61 extern "C" {\
62  void* POSIX_Init( void* argument) \
63  { \
64  static cls instance; \
65  exit( instance.InternalMain() ); \
66  } \
67 }
68 #elif defined(_WIN32_WCE)
69 #define PCREATE_PROCESS(cls) \
70  PDEFINE_WINMAIN(hInstance, , lpCmdLine, ) \
71  { \
72  cls *pInstance = new cls(); \
73  pInstance->GetArguments().SetArgs(lpCmdLine); \
74  int terminationValue = pInstance->InternalMain(hInstance); \
75  delete pInstance; \
76  return terminationValue; \
77  }
78 #else
79 #define PCREATE_PROCESS(cls) \
80  int main(int argc, char ** argv, char ** envp) \
81  { \
82  cls *pInstance = new cls(); \
83  pInstance->PreInitialise(argc, argv, envp); \
84  int terminationValue = pInstance->InternalMain(); \
85  delete pInstance; \
86  return terminationValue; \
87  }
88 #endif // P_VXWORKS
89 
90 /*$MACRO PDECLARE_PROCESS(cls,ancestor,manuf,name,major,minor,status,build)
91  This macro is used to declare the components necessary for a user PWLib
92  process. This will declare the PProcess descendent class, eg PApplication,
93  and create an instance of the class. See the <code>PCREATE_PROCESS</code> macro
94  for more details.
95  */
96 #define PDECLARE_PROCESS(cls,ancestor,manuf,name,major,minor,status,build) \
97  class cls : public ancestor { \
98  PCLASSINFO(cls, ancestor); \
99  public: \
100  cls() : ancestor(manuf, name, major, minor, status, build) { } \
101  private: \
102  virtual void Main(); \
103  };
104 
105 
106 class PTimerList : public PObject
107 /* This class defines a list of <code>PTimer</code> objects. It is primarily used
108  internally by the library and the user should never create an instance of
109  it. The <code>PProcess</code> instance for the application maintains an instance
110  of all of the timers created so that it may decrements them at regular
111  intervals.
112  */
113 {
114  PCLASSINFO(PTimerList, PObject);
115 
116  public:
117  // Create a new timer list
118  PTimerList();
119 
120  /* Decrement all the created timers and dispatch to their callback
121  functions if they have expired. The <code>PTimer::Tick()</code> function
122  value is used to determine the time elapsed since the last call to
123  Process().
124 
125  The return value is the number of milliseconds until the next timer
126  needs to be despatched. The function need not be called again for this
127  amount of time, though it can (and usually is).
128 
129  @return
130  maximum time interval before function should be called again.
131  */
133 
134  PTimer::IDType GetNewTimerId() const { return ++timerId; }
135 
136  class RequestType {
137  public:
138  enum Action {
141  } m_action;
142 
144  : m_action(act)
145  , m_timer(t)
146  , m_id(t->GetTimerId())
147  , m_absoluteTime(t->GetAbsoluteTime())
148  , m_serialNumber(t->GetNextSerialNumber())
149  , m_sync(NULL)
150  { }
151 
157  };
158 
159  void QueueRequest(RequestType::Action action, PTimer * timer, bool isSync = true);
160 
161  void ProcessTimerQueue();
162 
163  private:
164  // queue of timer action requests
165  PMutex m_queueMutex;
166  typedef std::queue<RequestType> RequestQueueType;
167  RequestQueueType m_requestQueue;
168 
169  // add an active timer to the lists
170  void AddActiveTimer(const RequestType & request);
171 
172  // counter to keep track of timer IDs
173  mutable PAtomicInteger timerId;
174 
175  // map used to store active timer information
176  struct ActiveTimerInfo {
177  ActiveTimerInfo(PTimer * t, PAtomicInteger::IntegerType serialNumber)
178  : m_timer(t), m_serialNumber(serialNumber) { }
179  PTimer * m_timer;
180  PAtomicInteger::IntegerType m_serialNumber;
181  };
182  typedef std::map<PTimer::IDType, ActiveTimerInfo> ActiveTimerInfoMap;
183  ActiveTimerInfoMap m_activeTimers;
184 
185  // set used to store timer expiry times, in order
186  struct TimerExpiryInfo {
187  TimerExpiryInfo(PTimer::IDType id, PInt64 expireTime, PAtomicInteger::IntegerType serialNumber)
188  : m_timerId(id), m_expireTime(expireTime), m_serialNumber(serialNumber) { }
189  PTimer::IDType m_timerId;
190  PInt64 m_expireTime;
191  PAtomicInteger::IntegerType m_serialNumber;
192  };
193 
194  struct TimerExpiryInfo_compare
195  : public binary_function<TimerExpiryInfo, TimerExpiryInfo, bool>
196  {
197  bool operator()(const TimerExpiryInfo & _Left, const TimerExpiryInfo & _Right) const
198  { return (_Left.m_expireTime < _Right.m_expireTime); }
199  };
200 
201  typedef std::multiset<TimerExpiryInfo, TimerExpiryInfo_compare> TimerExpiryInfoList;
202  TimerExpiryInfoList m_expiryList;
203 
204  // The last system timer tick value that was used to process timers.
205  PTimeInterval m_lastSample;
206 
207  // thread that handles the timer stuff
208  PThread * m_timerThread;
209 };
210 
211 
213 // PProcess
214 
227 class PProcess : public PThread
228 {
229  PCLASSINFO(PProcess, PThread);
230 
231  public:
234 
235  enum CodeStatus {
243  };
244 
247  PProcess(
248  const char * manuf = "",
249  const char * name = "",
250  WORD majorVersion = 1,
251  WORD minorVersion = 0,
253  WORD buildNumber = 1,
254  bool library = false
255  );
257 
267  const PObject & obj
268  ) const;
270 
275  virtual void Terminate();
276 
282  virtual PString GetThreadName() const;
283 
289  virtual void SetThreadName(
290  const PString & name
291  );
293 
302  static PProcess & Current();
303 
307  virtual void OnThreadStart(
308  PThread & thread
309  );
310 
314  virtual void OnThreadEnded(
315  PThread & thread
316  );
317 
330  virtual bool OnInterrupt(
331  bool terminating
332  );
333 
340  static PBoolean IsInitialised();
341 
348  void SetTerminationValue(
349  int value
350  );
351 
361  int GetTerminationValue() const;
362 
370 
380  virtual const PString & GetManufacturer() const;
381 
391  virtual const PString & GetName() const;
392 
407  virtual PString GetVersion(
408  PBoolean full = true
409  ) const;
410 
416  const PFilePath & GetFile() const;
417 
425  DWORD GetProcessID() const;
426 
429  PTime GetStartTime() const;
430 
439  PString GetUserName() const;
440 
464  const PString & username,
465  PBoolean permanent = false
466  );
467 
476  PString GetGroupName() const;
477 
503  const PString & groupname,
504  PBoolean permanent = false
505  );
506 
513  int GetMaxHandles() const;
514 
525  int newLimit
526  );
527 
528 #ifdef P_CONFIG_FILE
529 
531  virtual PString GetConfigurationFile();
532 #endif
533 
548  const PString & path
549  );
551 
560  static PString GetOSClass();
561 
568  static PString GetOSName();
569 
575  static PString GetOSHardware();
576 
583  static PString GetOSVersion();
584 
590  static bool IsOSVersion(
591  unsigned major,
592  unsigned minor = 0,
593  unsigned build = 0
594  );
595 
603  static PDirectory GetOSConfigDir();
604 
611  static PString GetLibVersion();
613 
621 
625  void PreInitialise(
626  int argc, // Number of program arguments.
627  char ** argv, // Array of strings for program arguments.
628  char ** envp // Array of string for the system environment
629  );
630 
634  static void PreShutdown();
635  static void PostShutdown();
636 
638  virtual int InternalMain(void * arg = NULL);
639 
662  {
663  public:
665  { }
666 
668  : type(t)
669  { }
670 
671  static bool RegisterTypes(const PString & types, bool force = true);
672 
673  void SetIcon(const PString & icon);
674  PString GetIcon() const;
675 
676  void SetCommand(const PString & key, const PString & command);
677  PString GetCommand(const PString & key) const;
678 
679  bool GetFromSystem();
680  bool CheckIfRegistered();
681 
682  bool Register();
683 
685 
686  #if _WIN32
687  PString iconFileName;
688  PStringToString cmds;
689  #endif
690  };
692 
693  protected:
694  void Construct();
695 
696  // Member variables
698  // Application return value
699 
701  // Application manufacturer name.
702 
704  // Application executable base name from argv[0]
705 
707  // Major version number of the product
708 
710  // Minor version number of the product
711 
713  // Development status of the product
714 
716  // Build number of the product
717 
719  // Application executable file from argv[0] (not open)
720 
722  // Explicit file or set of directories to find default PConfig
723 
725  // The list of arguments
726 
728  // List of active timers in system
729 
731  // time at which process was intantiated, i.e. started
732 
734  // Maximum number of file handles process can open.
735 
736  bool m_library;
737 
739 
740  typedef std::map<PThreadIdentifier, PThread *> ThreadMap;
743 
744  friend class PThread;
745 
746 
747 // Include platform dependent part of class
748 #ifdef _WIN32
749 #include "msos/ptlib/pprocess.h"
750 #else
751 #include "unix/ptlib/pprocess.h"
752 #endif
753 };
754 
755 
758  class PLibraryProcess : public PProcess
759  {
760  PCLASSINFO(PLibraryProcess, PProcess);
761 
762  public:
768  const char * manuf = "",
769  const char * name = "",
770  WORD majorVersionNum = 1,
771  WORD minorVersionNum = 0,
772  CodeStatus statusCode = ReleaseCode,
773  WORD buildNum = 1
774  ) : PProcess(manuf, name, majorVersionNum, minorVersionNum, statusCode, buildNum, true) { }
776 
778  virtual void Main() { }
779 };
780 
781 
782 /*
783  * one instance of this class (or any descendants) will be instantiated
784  * via PGenericFactory<PProessStartup> one "main" has been started, and then
785  * the OnStartup() function will be called. The OnShutdown function will
786  * be called after main exits, and the instances will be destroyed if they
787  * are not singletons
788  */
789 class PProcessStartup : public PObject
790 {
792  public:
793  virtual void OnStartup() { }
794  virtual void OnShutdown() { }
795 };
796 
798 
799 #if PTRACING
800 
801 // using an inline definition rather than a #define crashes gcc 2.95. Go figure
802 #define P_DEFAULT_TRACE_OPTIONS ( PTrace::Blocks | PTrace::Timestamp | PTrace::Thread | PTrace::FileAndLine )
803 
804 template <unsigned level, unsigned options = P_DEFAULT_TRACE_OPTIONS >
805 class PTraceLevelSetStartup : public PProcessStartup
806 {
807  public:
808  void OnStartup()
809  { PTrace::Initialise(level, NULL, options); }
810 };
811 
812 #endif // PTRACING
813 
814 
815 #endif // PTLIB_PROCESS_H
816 
817 
818 // End Of File ///////////////////////////////////////////////////////////////