1 /*
2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de.
3 * Distributed under the terms of the MIT License.
4 */
5 #ifndef THREAD_MODEL_H
6 #define THREAD_MODEL_H
7
8
9 #include <string.h>
10
11 #include "Model.h"
12
13
14 class ThreadModel {
15 public:
16 struct type_and_name;
17 class WaitObjectGroup;
18
19 public:
20 ThreadModel(Model* model,
21 Model::Thread* thread);
22 ~ThreadModel();
23
GetModel()24 Model* GetModel() const { return fModel; }
GetThread()25 Model::Thread* GetThread() const { return fThread; }
26
27 WaitObjectGroup* AddWaitObjectGroup(
28 const BObjectList<Model::ThreadWaitObject>&
29 waitObjects,
30 int32 start, int32 end);
31 inline int32 CountWaitObjectGroups() const;
32 inline WaitObjectGroup* WaitObjectGroupAt(int32 index) const;
33
34 bool AddSchedulingEvent(
35 const system_profiler_event_header*
36 eventHeader);
37 inline int32 CountSchedulingEvents() const;
38 inline const system_profiler_event_header* SchedulingEventAt(
39 int32 index) const;
40 int32 FindSchedulingEvent(nanotime_t time);
41
42 private:
43 typedef BObjectList<WaitObjectGroup> WaitObjectGroupList;
44 typedef BObjectList<const system_profiler_event_header> EventList;
45
46 private:
47 Model* fModel;
48 Model::Thread* fThread;
49 WaitObjectGroupList fWaitObjectGroups;
50 EventList fSchedulingEvents;
51 };
52
53
54 struct ThreadModel::type_and_name {
55 uint32 type;
56 const char* name;
57 };
58
59
60 class ThreadModel::WaitObjectGroup {
61 public:
62 WaitObjectGroup(
63 Model::ThreadWaitObject** waitObjects,
64 int32 count);
65 ~WaitObjectGroup();
66
67 inline uint32 Type() const;
68 inline const char* Name() const;
69 inline addr_t Object() const;
70
71 inline int64 Waits() const;
72 inline nanotime_t TotalWaitTime() const;
73
74 inline int32 CountWaitObjects() const;
75 inline Model::ThreadWaitObject* WaitObjectAt(int32 index) const;
76
77 static inline int CompareByTypeName(const WaitObjectGroup* a,
78 const WaitObjectGroup* b);
79 static inline int CompareWithTypeName(
80 const type_and_name* key,
81 const WaitObjectGroup* group);
82
83 private:
84 Model::ThreadWaitObject** fWaitObjects;
85 int32 fCount;
86 int64 fWaits;
87 nanotime_t fTotalWaitTime;
88 };
89
90
91 // #pragma mark - ThreadModel
92
93
94 int32
CountWaitObjectGroups()95 ThreadModel::CountWaitObjectGroups() const
96 {
97 return fWaitObjectGroups.CountItems();
98 }
99
100
101 ThreadModel::WaitObjectGroup*
WaitObjectGroupAt(int32 index)102 ThreadModel::WaitObjectGroupAt(int32 index) const
103 {
104 return fWaitObjectGroups.ItemAt(index);
105 }
106
107
108 int32
CountSchedulingEvents()109 ThreadModel::CountSchedulingEvents() const
110 {
111 return fSchedulingEvents.CountItems();
112 }
113
114
115 const system_profiler_event_header*
SchedulingEventAt(int32 index)116 ThreadModel::SchedulingEventAt(int32 index) const
117 {
118 return fSchedulingEvents.ItemAt(index);
119 }
120
121
122 // #pragma mark - WaitObjectGroup
123
124
125 uint32
Type()126 ThreadModel::WaitObjectGroup::Type() const
127 {
128 return fWaitObjects[0]->Type();
129 }
130
131
132 const char*
Name()133 ThreadModel::WaitObjectGroup::Name() const
134 {
135 return fWaitObjects[0]->Name();
136 }
137
138
139 addr_t
Object()140 ThreadModel::WaitObjectGroup::Object() const
141 {
142 return fWaitObjects[0]->Object();
143 }
144
145
146 int64
Waits()147 ThreadModel::WaitObjectGroup::Waits() const
148 {
149 return fWaits;
150 }
151
152
153 nanotime_t
TotalWaitTime()154 ThreadModel::WaitObjectGroup::TotalWaitTime() const
155 {
156 return fTotalWaitTime;
157 }
158
159
160 int32
CountWaitObjects()161 ThreadModel::WaitObjectGroup::CountWaitObjects() const
162 {
163 return fCount;
164 }
165
166
167 Model::ThreadWaitObject*
WaitObjectAt(int32 index)168 ThreadModel::WaitObjectGroup::WaitObjectAt(int32 index) const
169 {
170 return index >= 0 && index < fCount ? fWaitObjects[index] : NULL;
171 }
172
173
174 /*static*/ int
CompareByTypeName(const WaitObjectGroup * a,const WaitObjectGroup * b)175 ThreadModel::WaitObjectGroup::CompareByTypeName(const WaitObjectGroup* a,
176 const WaitObjectGroup* b)
177 {
178 type_and_name key;
179 key.type = a->Type();
180 key.name = a->Name();
181 return CompareWithTypeName(&key, b);
182 }
183
184
185 /*static*/ int
CompareWithTypeName(const type_and_name * key,const WaitObjectGroup * group)186 ThreadModel::WaitObjectGroup::CompareWithTypeName(const type_and_name* key,
187 const WaitObjectGroup* group)
188 {
189 if (key->type != group->Type())
190 return key->type < group->Type() ? -1 : 1;
191
192 return strcmp(key->name, group->Name());
193 }
194
195
196 #endif // THREAD_MODEL_h
197