Minor Windows fixes
[dyninst.git] / proccontrol / h / PCProcess.h
1 /*
2  * See the dyninst/COPYRIGHT file for copyright information.
3  * 
4  * We provide the Paradyn Tools (below described as "Paradyn")
5  * on an AS IS basis, and do not warrant its validity or performance.
6  * We reserve the right to update, modify, or discontinue this
7  * software at any time.  We shall have no obligation to supply such
8  * updates or modifications or any other form of support to you.
9  * 
10  * By your use of Paradyn, you understand and agree that we (or any
11  * other person or entity with proprietary rights in Paradyn) are
12  * under no obligation to provide either maintenance services,
13  * update services, notices of latent defects, or correction of
14  * defects for Paradyn.
15  * 
16  * This library is free software; you can redistribute it and/or
17  * modify it under the terms of the GNU Lesser General Public
18  * License as published by the Free Software Foundation; either
19  * version 2.1 of the License, or (at your option) any later version.
20  * 
21  * This library is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
24  * Lesser General Public License for more details.
25  * 
26  * You should have received a copy of the GNU Lesser General Public
27  * License along with this library; if not, write to the Free Software
28  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
29  */
30
31 #if !defined(PROCESSPC_H_)
32 #define PROCESSPC_H_
33
34 #include <string>
35 #include <vector>
36 #include <map>
37 #include <set>
38
39 #include "dyntypes.h"
40 #include "dyn_regs.h"
41 #include "EventType.h"
42 #include "util.h"
43 #include "PCErrors.h"
44 #include "boost/checked_delete.hpp"
45 #include "boost/shared_ptr.hpp"
46 #include "boost/weak_ptr.hpp"
47 #include "boost/enable_shared_from_this.hpp"
48
49
50 class int_process;
51 class int_breakpoint;
52 class proc_exitstate;
53 class thread_exitstate;
54 class int_library;
55 class int_thread;
56 class int_threadPool;
57 class int_registerPool;
58 class rpc_wrapper;
59 class int_iRPC;
60 class int_notify;
61 class HandlerPool;
62 class MTLock;
63
64 #define PC_VERSION_8_0_0
65
66 #define pc_const_cast boost::const_pointer_cast
67
68 namespace Dyninst {
69
70 class SymbolReaderFactory;
71
72 namespace ProcControlAPI {
73
74 class Process;
75 class ThreadPool;
76 class Thread;
77 class EventDecoder;
78 class EventGenerator;
79 class EventHandler;
80 class Event;
81 class RegisterPool;
82 class Breakpoint;
83 class ProcessSet;
84 class ThreadSet;
85 class LibraryTracking;
86 class ThreadTracking;
87 class LWPTracking;
88 class CallStackUnwinding;
89 class FollowFork;
90 class SignalMask;
91
92 class ExecFileInfo;
93
94 class PC_EXPORT Breakpoint 
95 {
96    friend class ::int_breakpoint;
97    friend void boost::checked_delete<Breakpoint>(Breakpoint *);
98    friend void boost::checked_delete<const Breakpoint>(const Breakpoint *);
99  private:
100    int_breakpoint *llbreakpoint_;
101    Breakpoint();
102    ~Breakpoint();
103  public:
104    static const int BP_X = 1;
105    static const int BP_W = 2;
106    static const int BP_R = 4;
107
108    int_breakpoint *llbp() const;
109    typedef boost::shared_ptr<Breakpoint> ptr;
110    typedef boost::shared_ptr<const Breakpoint> const_ptr;
111    typedef boost::weak_ptr<Breakpoint> weak_ptr;
112
113    static Breakpoint::ptr newBreakpoint();
114    static Breakpoint::ptr newTransferBreakpoint(Dyninst::Address to);
115    static Breakpoint::ptr newTransferOffsetBreakpoint(signed long shift);
116    static Breakpoint::ptr newHardwareBreakpoint(unsigned int mode, unsigned int size);
117
118    void *getData() const;
119    void setData(void *p) const;
120
121    bool isCtrlTransfer() const;
122    Dyninst::Address getToAddress() const;
123
124    void setSuppressCallbacks(bool);
125    bool suppressCallbacks() const;
126 };
127
128 class PC_EXPORT Library
129 {
130    friend class ::int_library;
131    friend void boost::checked_delete<Library>(Library *);
132    friend void boost::checked_delete<const Library>(const Library *);
133  private:
134    int_library *lib;
135    Library();
136    ~Library();
137  public:
138    typedef boost::shared_ptr<Library> ptr;
139    typedef boost::shared_ptr<const Library> const_ptr;
140
141    std::string getName() const;
142    Dyninst::Address getLoadAddress() const;
143    Dyninst::Address getDataLoadAddress() const;
144    Dyninst::Address getDynamicAddress() const;
145    int_library *debug() const { return lib; }
146    bool isSharedLib() const;
147
148    void *getData() const;
149    void setData(void *p) const;
150 };
151
152
153 class PC_EXPORT LibraryPool
154 {
155    friend class ::int_process;
156    friend class Dyninst::ProcControlAPI::Process;
157  private:
158    int_process *proc;
159    LibraryPool();
160    ~LibraryPool();
161  public:
162   class PC_EXPORT iterator {
163       friend class Dyninst::ProcControlAPI::LibraryPool;
164    private:
165       std::set<int_library *>::iterator int_iter;
166    public:
167       iterator();
168       ~iterator();
169       Library::ptr operator*() const;
170       bool operator==(const iterator &i) const;
171       bool operator!=(const iterator &i) const;
172       LibraryPool::iterator operator++();
173       LibraryPool::iterator operator++(int);
174   };
175
176   class PC_EXPORT const_iterator {
177      friend class Dyninst::ProcControlAPI::LibraryPool;
178   private:
179      std::set<int_library *>::iterator int_iter;
180   public:
181      const_iterator();
182      ~const_iterator();
183      Library::const_ptr operator*() const;
184      bool operator==(const const_iterator &i);
185      bool operator!=(const const_iterator &i);
186      LibraryPool::const_iterator operator++();
187      LibraryPool::const_iterator operator++(int);
188   };
189
190   iterator begin();
191   iterator end();
192   const_iterator begin() const;
193   const_iterator end() const;
194
195   size_t size() const;
196
197   Library::ptr getExecutable();
198   Library::const_ptr getExecutable() const;
199
200   Library::ptr getLibraryByName(std::string s);
201   Library::const_ptr getLibraryByName(std::string s) const;
202 };
203
204 class PC_EXPORT IRPC
205 {
206    friend class ::int_iRPC;
207    friend void boost::checked_delete<IRPC>(IRPC *);
208    friend void boost::checked_delete<const IRPC>(const IRPC *);
209  private:
210    rpc_wrapper *wrapper;
211    IRPC(rpc_wrapper *wrapper_);
212    ~IRPC();
213  public:
214          typedef enum {
215           Error = 0,
216           Created = 1,
217           Posted = 2,
218           Running = 3,
219           // Callback = 4,
220           Done = 5 } State;
221
222    typedef boost::shared_ptr<IRPC> ptr;
223    typedef boost::shared_ptr<const IRPC> const_ptr;
224    typedef boost::weak_ptr<IRPC> weak_ptr;
225    
226    static IRPC::ptr createIRPC(void *binary_blob, unsigned size, 
227                                bool non_blocking = false);
228    static IRPC::ptr createIRPC(void *binary_blob, unsigned size,
229                                Dyninst::Address addr, bool non_blocking = false);
230    static IRPC::ptr createIRPC(IRPC::ptr orig);
231    static IRPC::ptr createIRPC(IRPC::ptr orig, Address addr);
232    
233    rpc_wrapper *llrpc() const;
234
235    Dyninst::Address getAddress() const;
236    void *getBinaryCode() const;
237    unsigned getBinaryCodeSize() const;
238    unsigned long getID() const;
239    void setStartOffset(unsigned long);
240    unsigned long getStartOffset() const;
241    bool isBlocking() const;
242
243    // user-defined data retrievable during a callback
244    void *getData() const;
245    void setData(void *p) const;
246
247    State state() const;
248
249    // Continues the thread this RPC is running on.
250    // Useful if you don't know the thread assigned to an IRPC
251    bool continueStoppedIRPC();
252 };
253
254 class PC_EXPORT Process : public boost::enable_shared_from_this<Process>
255 {
256  private:
257    friend class ::int_process;
258    friend class ProcessSet;
259
260    int_process *llproc_;
261    proc_exitstate *exitstate_;
262    
263    Process();
264    ~Process();
265    friend void boost::checked_delete<Process>(Process *);
266    friend void boost::checked_delete<const Process>(const Process *);
267  public:
268    typedef boost::shared_ptr<Process> ptr;
269    typedef boost::shared_ptr<const Process> const_ptr;
270    typedef boost::weak_ptr<Process> weak_ptr;
271    typedef boost::weak_ptr<const Process> const_weak_ptr;
272
273    static void version(int& major, int& minor, int& maintenance);
274
275    //These four functions are not for end-users.  
276    int_process *llproc() const { return llproc_; }
277    proc_exitstate *exitstate() const { return exitstate_; }
278    void setLastError(ProcControlAPI::err_t err_code, const char *err_str) const;
279    void clearLastError() const;
280    
281    /**
282     * Threading modes control
283     **/
284    typedef enum {
285      NoThreads,
286      GeneratorThreading,
287      HandlerThreading,
288      CallbackThreading
289    } thread_mode_t;
290    static bool setThreadingMode(thread_mode_t tm);
291    static thread_mode_t getThreadingMode();
292
293    /**
294     * Create and attach to new processes
295     **/
296    static const std::map<int,int> emptyFDs;
297    static const std::vector<std::string> emptyEnvp;
298    static Process::ptr createProcess(std::string executable,
299                                      const std::vector<std::string> &argv,
300                                      const std::vector<std::string> &envp = emptyEnvp,
301                                      const std::map<int,int> &fds = emptyFDs);
302    static Process::ptr attachProcess(Dyninst::PID pid, std::string executable = "");
303
304    /**
305     * Event Management
306     **/
307    enum cb_action_t {
308      cbDefault,
309      cbThreadContinue,
310      cbThreadStop,
311      cbProcContinue,
312      cbProcStop
313    };
314    struct cb_ret_t {
315       cb_ret_t(cb_action_t p) : parent(p), child(cbDefault) {}
316       cb_ret_t(cb_action_t p, cb_action_t c) : parent(p), child(c) {}
317       cb_action_t parent;
318       cb_action_t child;
319    };
320    
321    //cb_func_t really takes an 'Event::const_ptr' as parameter, but this declaration
322    // defines the shared_ptr declaration due to Event::const_ptr not being defined yet.
323    typedef cb_ret_t(*cb_func_t)(boost::shared_ptr<const Event>);
324
325    static bool handleEvents(bool block);
326    static bool registerEventCallback(EventType evt, cb_func_t cbfunc);
327    static bool removeEventCallback(EventType evt, cb_func_t cbfunc);
328    static bool removeEventCallback(EventType evt);
329    static bool removeEventCallback(cb_func_t cbfunc);
330
331    // user-defined data retrievable during a callback
332    void *getData() const;
333    void setData(void *p) const;
334
335    Dyninst::PID getPid() const;
336
337    /**
338     * Threads
339     **/
340    const ThreadPool &threads() const;
341    ThreadPool &threads();
342    
343    /**
344     * Test state of process
345     **/
346    bool isTerminated() const;
347    bool isExited() const;
348    bool isCrashed() const;
349    bool isDetached() const;
350    int getExitCode() const;
351    int getCrashSignal() const;
352
353    bool hasStoppedThread() const;
354    bool hasRunningThread() const;
355    bool allThreadsStopped() const;
356    bool allThreadsRunning() const;
357    bool allThreadsRunningWhenAttached() const;
358
359    /**
360     * What capabilities do we have on this process
361     **/
362    static const unsigned int pc_read      = (1<<0);
363    static const unsigned int pc_write     = (1<<1);
364    static const unsigned int pc_irpc      = (1<<2);   
365    static const unsigned int pc_control   = (1<<3);
366    unsigned int getCapabilities() const;
367    
368    /**
369     * Queries for machine info
370     **/
371    Dyninst::Architecture getArchitecture() const;
372    Dyninst::OSType getOS() const;
373
374    /**
375     * Query what kind of events this process supports
376     **/
377    bool supportsLWPEvents() const;
378    bool supportsUserThreadEvents() const;
379    bool supportsFork() const;
380    bool supportsExec() const;
381
382    /**
383     * Control process
384     **/
385    bool continueProc();
386    bool stopProc();
387    bool detach(bool leaveStopped = false);
388    bool terminate();
389    bool temporaryDetach();
390    bool reAttach();
391
392    /**
393     * Memory management
394     **/
395    class PC_EXPORT mem_perm {
396        bool read;
397        bool write;
398        bool execute;
399
400        int permVal() const;
401
402    public:
403        mem_perm() : read(false), write(false), execute(false) {} 
404        mem_perm(const mem_perm& p) : read(p.read), write(p.write),
405                                      execute(p.execute) {}
406        mem_perm(bool r, bool w, bool x) : read(r), write(w), execute(x) {} 
407
408        bool getR() const { return read;    }
409        bool getW() const { return write;   }
410        bool getX() const { return execute; }
411
412        bool isNone() const { return !read && !write && !execute; }
413        bool isR()    const { return  read && !write && !execute; }
414        bool isX()    const { return !read && !write &&  execute; }
415        bool isRW()   const { return  read &&  write && !execute; }
416        bool isRX()   const { return  read && !write &&  execute; }
417        bool isRWX()  const { return  read &&  write &&  execute; }
418
419        mem_perm& setR() { read    = true;  return *this; }
420        mem_perm& setW() { write   = true;  return *this; }
421        mem_perm& setX() { execute = true;  return *this; }
422
423        mem_perm& clrR() { read    = false; return *this; }
424        mem_perm& clrW() { write   = false; return *this; }
425        mem_perm& clrX() { execute = false; return *this; }
426
427        bool operator< (const mem_perm& p) const;
428        bool operator==(const mem_perm& p) const;
429        bool operator!=(const mem_perm& p) const;
430
431        std::string getPermName() const;
432    };
433
434    Dyninst::Address mallocMemory(size_t size);
435    Dyninst::Address mallocMemory(size_t size, Dyninst::Address addr);
436    bool freeMemory(Dyninst::Address addr);
437    bool writeMemory(Dyninst::Address addr, const void *buffer, size_t size) const;
438    bool readMemory(void *buffer, Dyninst::Address addr, size_t size) const;
439
440    bool writeMemoryAsync(Dyninst::Address addr, const void *buffer, size_t size, void *opaque_val = NULL) const;
441    bool readMemoryAsync(void *buffer, Dyninst::Address addr, size_t size, void *opaque_val = NULL) const;
442
443    /** 
444     * Currently Windows-only, needed for the test infrastructure but possibly useful elsewhere 
445     **/
446    Dyninst::Address findFreeMemory(size_t size);
447
448    bool getMemoryAccessRights(Dyninst::Address addr, size_t size, mem_perm& rights);
449    bool setMemoryAccessRights(Dyninst::Address addr, size_t size, mem_perm rights, mem_perm& oldRights);
450
451    /**
452     * Libraries
453     **/
454    const LibraryPool &libraries() const;
455    LibraryPool &libraries();
456
457    /**
458     * Breakpoints
459     **/
460    bool addBreakpoint(Dyninst::Address addr, Breakpoint::ptr bp) const;
461    bool rmBreakpoint(Dyninst::Address addr, Breakpoint::ptr bp) const;
462    unsigned numHardwareBreakpointsAvail(unsigned mode);
463
464    /**
465     * Post IRPC.  Use continueProc/continueThread to run it,
466     * and handleEvents to wait for a blocking IRPC to complete
467     **/
468    bool postIRPC(IRPC::ptr irpc) const;
469    bool getPostedIRPCs(std::vector<IRPC::ptr> &rpcs) const;
470
471    /**
472     * Post and run an IRPC; user must wait for completion. Standard 
473     **/
474         bool runIRPCSync(IRPC::ptr irpc);
475
476    /**
477     * Post, run, and wait for an IRPC to complete
478         **/
479         bool runIRPCAsync(IRPC::ptr irpc);
480
481    /**
482     * Symbol access
483     **/
484    void setSymbolReader(SymbolReaderFactory *reader) const;
485    SymbolReaderFactory *getSymbolReader() const;
486    static SymbolReaderFactory *getDefaultSymbolReader();
487    static void setDefaultSymbolReader(SymbolReaderFactory *reader);
488
489    /**
490     * Perform specific operations.  Interface objects will only be returned
491     * on appropriately supported platforms, others will return NULL.
492     **/
493    LibraryTracking *getLibraryTracking();
494    ThreadTracking *getThreadTracking();
495    LWPTracking *getLWPTracking();
496    FollowFork *getFollowFork();
497    SignalMask *getSignalMask();
498    const LibraryTracking *getLibraryTracking() const;
499    const ThreadTracking *getThreadTracking() const;
500    const LWPTracking *getLWPTracking() const;
501    const FollowFork *getFollowFork() const;
502    const SignalMask *getSignalMask() const;
503    
504    /**
505     * Errors that occured on this process
506     **/
507    ProcControlAPI::err_t getLastError() const;
508    const char *getLastErrorMsg() const;
509
510    /**
511     * Executable info
512     **/
513         ExecFileInfo* getExecutableInfo() const;
514 };
515
516 class PC_EXPORT Thread
517 {
518  protected:
519    friend class ::int_thread;
520    int_thread *llthread_;
521    thread_exitstate *exitstate_;
522
523    Thread();
524    ~Thread();
525    friend void boost::checked_delete<Thread>(Thread *);
526    friend void boost::checked_delete<const Thread>(const Thread *);
527
528  public:
529    typedef boost::shared_ptr<Thread> ptr;
530    typedef boost::shared_ptr<const Thread> const_ptr;
531    typedef boost::weak_ptr<Thread> weak_ptr;
532    typedef boost::weak_ptr<const Thread> const_weak_ptr;
533    int_thread *llthrd() const;
534    void setLastError(err_t ec, const char *es) const;
535
536    Dyninst::LWP getLWP() const;
537    Process::ptr getProcess();
538    Process::const_ptr getProcess() const;
539
540    bool isStopped() const;
541    bool isRunning() const;
542    bool isLive() const;
543    bool isDetached() const;
544    bool isInitialThread() const;
545
546    // Added for Windows. Windows creates internal threads which are bound to 
547    // the process but are used for OS-level work. We hide these from the user,
548    // but need to represent them in ProcControlAPI. 
549    bool isUser() const; 
550
551    bool stopThread();
552    bool continueThread();
553
554    void setSingleStepMode(bool s) const;
555    bool getSingleStepMode() const;
556
557    bool getRegister(Dyninst::MachRegister reg, Dyninst::MachRegisterVal &val) const;
558    bool getAllRegisters(RegisterPool &pool) const;
559    bool setRegister(Dyninst::MachRegister reg, Dyninst::MachRegisterVal val) const;
560    bool setAllRegisters(RegisterPool &pool) const;
561    bool getAllRegistersAsync(RegisterPool &pool, void *opaque_val = NULL) const;
562    bool setAllRegistersAsync(RegisterPool &pool, void *opaque_val = NULL) const;
563
564    /**
565     * User level thread info.  Only available after a UserThreadCreate event
566     **/
567    bool haveUserThreadInfo() const;
568    Dyninst::THR_ID getTID() const;
569    Dyninst::Address getStartFunction() const;
570    Dyninst::Address getStackBase() const;
571    unsigned long getStackSize() const;
572    Dyninst::Address getTLS() const;
573
574    /**
575     * IRPC
576     **/
577    bool postIRPC(IRPC::ptr irpc) const;
578    bool runIRPCSync(IRPC::ptr irpc);
579    bool runIRPCAsync(IRPC::ptr irpc);
580
581    bool getPostedIRPCs(std::vector<IRPC::ptr> &rpcs) const;
582    IRPC::const_ptr getRunningIRPC() const;
583
584    /**
585     * Returns a stack unwinder on supported platforms (BlueGene/Q).
586     * Returns NULL on unsupported platforms
587     **/
588    CallStackUnwinding *getCallStackUnwinding();
589
590    void *getData() const;
591    void setData(void *p) const;
592 };
593
594 class PC_EXPORT ThreadPool
595 {
596  private:
597    friend class ::int_threadPool;
598    friend class Dyninst::ProcControlAPI::Process;
599    int_threadPool *threadpool;
600    ThreadPool();
601    ~ThreadPool();
602  public:
603    /**
604     * Iterators
605     **/
606    class PC_EXPORT iterator {
607       friend class Dyninst::ProcControlAPI::ThreadPool;
608    private:
609       static const int uninitialized_val = -1;
610       static const int end_val = -2;
611       int_threadPool *curp;
612       Thread::ptr curh;
613       int curi;
614    public:
615       iterator();
616       ~iterator();
617       Thread::ptr operator*() const;
618       bool operator==(const iterator &i);
619       bool operator!=(const iterator &i);
620       ThreadPool::iterator operator++();
621       ThreadPool::iterator operator++(int);
622    };
623    iterator begin();
624    iterator end();
625    iterator find(Dyninst::LWP lwp);
626
627    class PC_EXPORT const_iterator {
628       friend class Dyninst::ProcControlAPI::ThreadPool;
629    private:
630       static const int uninitialized_val = -1;
631       static const int end_val = -2;
632       int_threadPool *curp;
633       Thread::ptr curh;
634       int curi;
635    public:
636       const_iterator();
637       ~const_iterator();
638       Thread::const_ptr operator*() const;
639       bool operator==(const const_iterator &i);
640       bool operator!=(const const_iterator &i);
641       ThreadPool::const_iterator operator++();
642       ThreadPool::const_iterator operator++(int);
643
644           typedef Thread::const_ptr value_type;
645           typedef int difference_type;
646           typedef Thread::const_ptr *pointer;
647           typedef Thread::const_ptr &reference;
648           typedef std::forward_iterator_tag iterator_category;
649    };
650    const_iterator begin() const;
651    const_iterator end() const;
652    const_iterator find(Dyninst::LWP lwp) const;
653
654    size_t size() const;
655    Process::const_ptr getProcess() const;
656    Process::ptr getProcess();
657    Thread::const_ptr getInitialThread() const;
658    Thread::ptr getInitialThread();
659 };
660
661 class PC_EXPORT RegisterPool
662
663    friend class Dyninst::ProcControlAPI::Thread;
664    friend class Dyninst::ProcControlAPI::ThreadSet;
665  private:
666    int_registerPool *llregpool;
667  public:
668    RegisterPool();
669    RegisterPool(const RegisterPool &rp);
670    ~RegisterPool();
671    
672    class PC_EXPORT iterator {
673       friend class Dyninst::ProcControlAPI::RegisterPool;
674    private:
675       typedef std::map<Dyninst::MachRegister, Dyninst::MachRegisterVal>::iterator int_iter; 
676       int_iter i;
677       iterator(int_iter i_);
678    public:
679       iterator();
680       ~iterator();
681       std::pair<Dyninst::MachRegister, Dyninst::MachRegisterVal> operator*();
682       bool operator==(const iterator &i);
683       bool operator!=(const iterator &i);
684       RegisterPool::iterator operator++();
685       RegisterPool::iterator operator++(int);
686    };
687    iterator begin();
688    iterator end();
689    iterator find(Dyninst::MachRegister r);
690
691    class PC_EXPORT const_iterator {
692       friend class Dyninst::ProcControlAPI::RegisterPool;
693    private:
694       typedef std::map<Dyninst::MachRegister, Dyninst::MachRegisterVal>::const_iterator int_iter; 
695       int_iter i;
696       const_iterator(int_iter i_);
697    public:
698       const_iterator();
699       ~const_iterator();
700       std::pair<Dyninst::MachRegister, Dyninst::MachRegisterVal> operator*() const;
701       bool operator==(const const_iterator &i);
702       bool operator!=(const const_iterator &i);
703       RegisterPool::const_iterator operator++();
704       RegisterPool::const_iterator operator++(int);
705    };
706    const_iterator begin() const;
707    const_iterator end() const;
708    const_iterator find(Dyninst::MachRegister r) const;
709
710    Dyninst::MachRegisterVal& operator[](Dyninst::MachRegister r);
711    const Dyninst::MachRegisterVal& operator[](Dyninst::MachRegister r) const;
712
713    size_t size() const;
714    Thread::const_ptr getThread() const;
715    Thread::ptr getThread();
716 };
717
718 class PC_EXPORT EventNotify
719 {
720  private:
721    friend class ::int_notify;
722    int_notify *llnotify;
723    EventNotify();
724    ~EventNotify();
725  public:
726    typedef void (*notify_cb_t)();
727
728    int getFD();
729    void registerCB(notify_cb_t cb);
730    void removeCB(notify_cb_t cb);
731 };
732 PC_EXPORT EventNotify *evNotify();
733
734 class PC_EXPORT ExecFileInfo
735 {
736   public:
737         void* fileHandle;
738         void* processHandle;
739         Address fileBase;
740 };
741
742
743 }
744 }
745
746 #endif