First pass at thread_db integration for FreeBSD.
[dyninst.git] / proccontrol / src / int_thread_db.h
1 /*
2  * Copyright (c) 1996-2009 Barton P. Miller
3  * 
4  * We provide the Paradyn Parallel Performance Tools (below
5  * described as "Paradyn") on an AS IS basis, and do not warrant its
6  * validity or performance.  We reserve the right to update, modify,
7  * or discontinue this software at any time.  We shall have no
8  * obligation to supply such updates or modifications or any other
9  * form of support to you.
10  * 
11  * By your use of Paradyn, you understand and agree that we (or any
12  * other person or entity with proprietary rights in Paradyn) are
13  * under no obligation to provide either maintenance services,
14  * update services, notices of latent defects, or correction of
15  * defects for Paradyn.
16  * 
17  * This library is free software; you can redistribute it and/or
18  * modify it under the terms of the GNU Lesser General Public
19  * License as published by the Free Software Foundation; either
20  * version 2.1 of the License, or (at your option) any later version.
21  * 
22  * This library is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
25  * Lesser General Public License for more details.
26  * 
27  * You should have received a copy of the GNU Lesser General Public
28  * License along with this library; if not, write to the Free Software
29  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
30  */
31 #if !defined(INT_THREAD_DB_H_)
32 #define INT_THREAD_DB_H
33
34 #include "proccontrol/h/Generator.h"
35 #include "proccontrol/h/Event.h"
36 #include "proccontrol/h/Decoder.h"
37 #include "proccontrol/h/Handler.h"
38 #include "proccontrol/src/int_process.h"
39 #include "proccontrol/src/sysv.h"
40 #include "proccontrol/src/int_handler.h"
41
42 #include <thread_db.h>
43 #include <proc_service.h>
44
45 #include <map>
46 using std::map;
47 using std::pair;
48
49 #include <vector>
50 using std::vector;
51
52 #include <string>
53 using std::string;
54
55 using namespace Dyninst;
56 using namespace ProcControlAPI;
57
58 class thread_db_thread;
59
60 class thread_db_process : public sysv_process
61 {
62 public:
63     thread_db_process(Dyninst::PID p, std::string e, std::vector<std::string> a);
64     thread_db_process(Dyninst::PID pid_, int_process *p);
65     virtual ~thread_db_process();
66
67     bool getEventsAtAddr(Dyninst::Address addr, thread_db_thread *eventThread,
68             vector<Event::ptr> &threadEvents);
69
70     /* helper functions for thread_db interactions */
71
72     td_thragent_t *getThreadDBAgent();
73     ps_err_e getSymbolAddr(const char *objName, const char *symName, 
74             psaddr_t *symbolAddr);
75     virtual bool initThreadDB();
76     static void addThreadDBHandlers(HandlerPool *hpool);
77
78     /*
79      * When creating a static executable or attaching to a new process,
80      * thread_db initialization needs to occur immediately after
81      * attach or create.
82      *
83      * When creating dynamic executables, initialization needs to happen
84      * when the thread library is loaded.
85      */
86     virtual bool post_attach();
87     virtual bool post_create();
88
89     virtual bool plat_readProcMem(void *local,
90             Dyninst::Address remote, size_t size) = 0;
91     virtual bool plat_writeProcMem(void *local,
92             Dyninst::Address remote, size_t size) = 0;
93     virtual bool plat_getLWPInfo(lwpid_t lwp, void *lwpInfo) = 0;
94     virtual bool plat_contThread(lwpid_t lwp) = 0;
95     virtual bool plat_stopThread(lwpid_t lwp) = 0;
96     virtual string getThreadLibName(const char *symName) = 0;
97     virtual bool isSupportedThreadLib(const string &libName) = 0;
98
99 protected:
100     static volatile bool thread_db_initialized;
101
102     map<Dyninst::Address, pair<int_breakpoint *, EventType> > addr2Event;
103     map<string, pair<LoadedLib *, SymReader *> > symReaders;
104     td_thragent_t *threadAgent;
105
106     struct ps_prochandle *self;
107 };
108
109 /*
110  * libthread_db defines this as opaque. We need to implement it.
111  */
112 struct ps_prochandle {
113     thread_db_process *thread_db_proc;
114 };
115
116 class thread_db_thread : public int_thread
117 {
118 public:
119     thread_db_thread(int_process *p, Dyninst::THR_ID t, Dyninst::LWP l);
120
121     thread_db_thread();
122     virtual ~thread_db_thread();
123
124     Event::ptr getThreadEvent();
125     bool setEventReporting(bool on);
126 };
127
128 class ThreadDBHandleNewThr : public Handler
129 {
130 public:
131     ThreadDBHandleNewThr();
132     virtual ~ThreadDBHandleNewThr();
133     virtual bool handleEvent(Event::ptr ev);
134     virtual int getPriority() const;
135     void getEventTypesHandled(std::vector<EventType> &etypes);
136 };
137
138 class ThreadDBLibHandler : public Handler
139 {
140 public:
141     ThreadDBLibHandler();
142     virtual ~ThreadDBLibHandler();
143     virtual bool handleEvent(Event::ptr ev);
144     virtual int getPriority() const;
145     void getEventTypesHandled(std::vector<EventType> &etypes);
146 };
147 #endif