xref: /haiku/src/kits/app/LooperList.cpp (revision d5cd5d63ff0ad395989db6cf4841a64d5b545d1d)
1 //------------------------------------------------------------------------------
2 //	Copyright (c) 2001-2002, OpenBeOS
3 //
4 //	Permission is hereby granted, free of charge, to any person obtaining a
5 //	copy of this software and associated documentation files (the "Software"),
6 //	to deal in the Software without restriction, including without limitation
7 //	the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 //	and/or sell copies of the Software, and to permit persons to whom the
9 //	Software is furnished to do so, subject to the following conditions:
10 //
11 //	The above copyright notice and this permission notice shall be included in
12 //	all copies or substantial portions of the Software.
13 //
14 //	THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 //	IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 //	FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 //	AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 //	LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
19 //	FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
20 //	DEALINGS IN THE SOFTWARE.
21 //
22 //	File Name:		LooperList.cpp
23 //	Author(s):		Erik Jaesler (erik@cgsoftware.com)
24 //	Description:	Maintains a global list of all loopers in a given team.
25 //------------------------------------------------------------------------------
26 
27 // Standard Includes -----------------------------------------------------------
28 #include <algorithm>
29 
30 // System Includes -------------------------------------------------------------
31 #include <Autolock.h>
32 #include <Looper.h>
33 
34 // Project Includes ------------------------------------------------------------
35 
36 // Local Includes --------------------------------------------------------------
37 #include "LooperList.h"
38 
39 // Local Defines ---------------------------------------------------------------
40 
41 // Globals ---------------------------------------------------------------------
42 using std::vector;
43 
44 namespace BPrivate {
45 
46 BLooperList gLooperList;
47 
48 typedef vector<BLooperList::LooperData>::iterator LDIter;
49 
50 //------------------------------------------------------------------------------
51 BLooperList::BLooperList()
52 	:	fLooperID(0)
53 {
54 }
55 //------------------------------------------------------------------------------
56 bool BLooperList::Lock()
57 {
58 	return fLock.Lock();
59 }
60 //------------------------------------------------------------------------------
61 void BLooperList::Unlock()
62 {
63 	fLock.Unlock();
64 }
65 //------------------------------------------------------------------------------
66 bool BLooperList::IsLocked()
67 {
68 	return fLock.IsLocked();
69 }
70 //------------------------------------------------------------------------------
71 void BLooperList::AddLooper(BLooper* looper)
72 {
73 	BAutolock Listlock(fLock);
74 	AssertLocked();
75 	if (!IsLooperValid(looper))
76 	{
77 		LDIter i = find_if(fData.begin(), fData.end(), EmptySlotPred);
78 		if (i == fData.end())
79 		{
80 			fData.push_back(LooperData(looper, ++fLooperID));
81 			looper->fLooperID = fLooperID;
82 			looper->Lock();
83 		}
84 		else
85 		{
86 			i->looper = looper;
87 			i->id = ++fLooperID;
88 			looper->fLooperID = fLooperID;
89 			looper->Lock();
90 		}
91 	}
92 }
93 //------------------------------------------------------------------------------
94 bool BLooperList::IsLooperValid(const BLooper* looper)
95 {
96 	BAutolock Listlock(fLock);
97 	AssertLocked();
98 
99 	return find_if(fData.begin(), fData.end(), FindLooperPred(looper)) !=
100 			fData.end();
101 }
102 //------------------------------------------------------------------------------
103 bool BLooperList::RemoveLooper(BLooper* looper)
104 {
105 	BAutolock Listlock(fLock);
106 	AssertLocked();
107 
108 	LDIter i = find_if(fData.begin(), fData.end(), FindLooperPred(looper));
109 	if (i != fData.end())
110 	{
111 		i->looper = NULL;
112 		return true;
113 	}
114 
115 	return false;
116 }
117 //------------------------------------------------------------------------------
118 void BLooperList::GetLooperList(BList* list)
119 {
120 	BAutolock Listlock(fLock);
121 	AssertLocked();
122 	for (uint32 i = 0; i < fData.size(); ++i)
123 	{
124 		list->AddItem(fData[i].looper);
125 	}
126 }
127 //------------------------------------------------------------------------------
128 int32 BLooperList::CountLoopers()
129 {
130 	BAutolock Listlock(fLock);
131 	AssertLocked();
132 	return (int32)fData.size();
133 }
134 //------------------------------------------------------------------------------
135 BLooper* BLooperList::LooperAt(int32 index)
136 {
137 	BAutolock Listlock(fLock);
138 	AssertLocked();
139 
140 	BLooper* Looper = NULL;
141 	if (index < (int32)fData.size())
142 	{
143 		Looper = fData[(uint32)index].looper;
144 	}
145 
146 	return Looper;
147 }
148 //------------------------------------------------------------------------------
149 BLooper* BLooperList::LooperForThread(thread_id tid)
150 {
151 	BAutolock Listlock(fLock);
152 	AssertLocked();
153 	BLooper* looper = NULL;
154 	LDIter i = find_if(fData.begin(), fData.end(), FindThreadPred(tid));
155 	if (i != fData.end())
156 	{
157 		looper = i->looper;
158 	}
159 
160 	return looper;
161 }
162 //------------------------------------------------------------------------------
163 BLooper* BLooperList::LooperForName(const char* name)
164 {
165 	BAutolock Listlock(fLock);
166 	AssertLocked();
167 	BLooper* looper = NULL;
168 	LDIter i = find_if(fData.begin(), fData.end(), FindNamePred(name));
169 	if (i != fData.end())
170 	{
171 		looper = i->looper;
172 	}
173 
174 	return looper;
175 }
176 //------------------------------------------------------------------------------
177 BLooper* BLooperList::LooperForPort(port_id port)
178 {
179 	BAutolock Listlock(fLock);
180 	AssertLocked();
181 	BLooper* looper = NULL;
182 	LDIter i = find_if(fData.begin(), fData.end(), FindPortPred(port));
183 	if (i != fData.end())
184 	{
185 		looper = i->looper;
186 	}
187 
188 	return looper;
189 }
190 //------------------------------------------------------------------------------
191 bool BLooperList::EmptySlotPred(LooperData& Data)
192 {
193 	return Data.looper == NULL;
194 }
195 //------------------------------------------------------------------------------
196 void BLooperList::AssertLocked()
197 {
198 	if (!IsLocked())
199 	{
200 		debugger("looperlist is not locked; proceed at great risk!");
201 	}
202 }
203 //------------------------------------------------------------------------------
204 
205 
206 //------------------------------------------------------------------------------
207 //	#pragma mark -
208 //	#pragma mark BLooperList::LooperData
209 //	#pragma mark -
210 //------------------------------------------------------------------------------
211 BLooperList::LooperData::LooperData()
212 	:	looper(NULL), id(0)
213 {
214 }
215 //------------------------------------------------------------------------------
216 BLooperList::LooperData::LooperData(BLooper* loop, uint32 i)
217 	:	looper(loop), id(i)
218 {
219 	;
220 }
221 //------------------------------------------------------------------------------
222 BLooperList::LooperData::LooperData(const LooperData& rhs)
223 {
224 	*this = rhs;
225 }
226 //------------------------------------------------------------------------------
227 BLooperList::LooperData&
228 BLooperList::LooperData::operator=(const LooperData& rhs)
229 {
230 	if (this != &rhs)
231 	{
232 		looper = rhs.looper;
233 		id = rhs.id;
234 	}
235 
236 	return *this;
237 }
238 //------------------------------------------------------------------------------
239 
240 
241 //------------------------------------------------------------------------------
242 bool BLooperList::FindLooperPred::operator()(BLooperList::LooperData& Data)
243 {
244 	return Data.looper && (looper == Data.looper);
245 }
246 //------------------------------------------------------------------------------
247 bool BLooperList::FindThreadPred::operator()(LooperData& Data)
248 {
249 	return Data.looper && (thread == Data.looper->Thread());
250 }
251 //------------------------------------------------------------------------------
252 bool BLooperList::FindNamePred::operator()(LooperData& Data)
253 {
254 	return Data.looper && (strcmp(name, Data.looper->Name()) == 0);
255 }
256 //------------------------------------------------------------------------------
257 bool BLooperList::FindPortPred::operator()(LooperData& Data)
258 {
259 	return Data.looper && (port == _get_looper_port_(Data.looper));
260 }
261 //------------------------------------------------------------------------------
262 
263 }	// namespace BPrivate
264 
265 /*
266  * $Log $
267  *
268  * $Id  $
269  *
270  */
271 
272