1 /*---------------------------------------------------------------------------*
2 Project: Horizon
3 File: fnd_DetailList.cpp
4
5 Copyright (C)2009 Nintendo Co., Ltd. All rights reserved.
6
7 These coded instructions, statements, and computer programs contain
8 proprietary information of Nintendo of America Inc. and/or Nintendo
9 Company Ltd., and are protected by Federal copyright law. They may
10 not be disclosed to third parties or copied or duplicated in any form,
11 in whole or in part, without the prior written consent of Nintendo.
12
13 $Rev: 12449 $
14 *---------------------------------------------------------------------------*/
15
16 #include "./fnd_DetailList.h"
17
18 namespace nn { namespace fnd { namespace detail {
19
20 #define OBJ_TO_LINK(list,obj) ((NNSFndLink*)(((u32)(obj))+(list)->offset))
21
22 /*---------------------------------------------------------------------------*
23 Name: InitList
24
25 Description: リスト構造体を初期化します。
26
27 Arguments: list: リスト構造体へのポインタ。
28 offset: リストに繋げたい構造体の中に存在する、NNSFndLink型の
29 メンバ変数の構造体内でのオフセットを指定します。
30 stddef.hで定義されているoffsetofマクロを使用すると、
31 便利です。
32
33 Returns: なし。
34 *---------------------------------------------------------------------------*/
35 void
InitList(NNSFndList * list,u16 offset)36 InitList(NNSFndList* list, u16 offset)
37 {
38 NN_TASSERT_(list);
39
40 list->headObject = NULL;
41 list->tailObject = NULL;
42 list->numObjects = 0;
43 list->offset = offset;
44 }
45
46 /*---------------------------------------------------------------------------*
47 Name: SetFirstObject [static]
48
49 Description: 最初のオブジェクトをリストに加えます。
50
51 Arguments: list: リスト構造体へのポインタ。
52 object: リストに繋げたいオブジェクトへのポインタ。
53
54 Returns: なし。
55 *---------------------------------------------------------------------------*/
56 static void
SetFirstObject(NNSFndList * list,void * object)57 SetFirstObject(NNSFndList* list, void* object)
58 {
59 NNSFndLink* link;
60
61 NN_TASSERT_(list );
62 NN_TASSERT_(object);
63
64 link = OBJ_TO_LINK(list, object);
65
66 link->nextObject = NULL;
67 link->prevObject = NULL;
68 list->headObject = object;
69 list->tailObject = object;
70 list->numObjects++;
71 }
72
73 /*---------------------------------------------------------------------------*
74 Name: AppendListObject
75
76 Description: オブジェクトをリストの最後に追加します。
77
78 Arguments: list: リスト構造体へのポインタ。
79 object: リストに繋げたいオブジェクトへのポインタ。
80
81 Returns: なし。
82 *---------------------------------------------------------------------------*/
83 void
AppendListObject(NNSFndList * list,void * object)84 AppendListObject(NNSFndList* list, void* object)
85 {
86 NN_TASSERT_(list );
87 NN_TASSERT_(object);
88
89 if (list->headObject == NULL)
90 {
91 // リストが空の時。
92 SetFirstObject(list, object);
93 }
94 else
95 {
96 NNSFndLink* link = OBJ_TO_LINK(list, object);
97
98 link->prevObject = list->tailObject;
99 link->nextObject = NULL;
100
101 OBJ_TO_LINK(list, list->tailObject)->nextObject = object;
102 list->tailObject = object;
103 list->numObjects++;
104 }
105 }
106
107 /*---------------------------------------------------------------------------*
108 Name: PrependListObject
109
110 Description: オブジェクトをリストの先頭に挿入します。
111
112 Arguments: list: リスト構造体へのポインタ。
113 object: リストに繋げたいオブジェクトへのポインタ。
114
115 Returns: なし。
116 *---------------------------------------------------------------------------*/
117 void
PrependListObject(NNSFndList * list,void * object)118 PrependListObject(NNSFndList* list, void* object)
119 {
120 NN_TASSERT_(list );
121 NN_TASSERT_(object);
122
123 if (list->headObject == NULL)
124 {
125 // リストが空の時。
126 SetFirstObject(list, object);
127 }
128 else
129 {
130 NNSFndLink* link = OBJ_TO_LINK(list, object);
131
132 link->prevObject = NULL;
133 link->nextObject = list->headObject;
134
135 OBJ_TO_LINK(list, list->headObject)->prevObject = object;
136 list->headObject = object;
137 list->numObjects++;
138 }
139 }
140
141 /*---------------------------------------------------------------------------*
142 Name: InsertListObject
143
144 Description: オブジェクトを指定された位置に挿入します。オブジェクトは、
145 targetで指定されたオブジェクトの前に挿入されます。挿入先が指
146 定されていない場合(targetがNULLの場合)、オブジェクトはリス
147 トの最後に追加されます。
148
149 Arguments: list: リスト構造体へのポインタ。
150 target: 挿入したい位置にあるオブジェクトへのポインタ。
151 object: リストに繋げたいオブジェクトへのポインタ。
152
153 Returns: なし。
154 *---------------------------------------------------------------------------*/
155 void
InsertListObject(NNSFndList * list,void * target,void * object)156 InsertListObject(NNSFndList* list, void* target, void* object)
157 {
158 NN_TASSERT_(list );
159 NN_TASSERT_(object);
160
161 if (target == NULL)
162 {
163 // targetが指定されていない場合は、AppendListObject()と同じ。
164 AppendListObject(list, object);
165 }
166 else if (target == list->headObject)
167 {
168 // targetがリストの先頭である場合はPrependListObject()と同じ。
169 PrependListObject(list, object);
170 }
171 else
172 {
173 NNSFndLink* link = OBJ_TO_LINK(list, object);
174 void* prevObj = OBJ_TO_LINK(list, target)->prevObject;
175 NNSFndLink* prevLnk = OBJ_TO_LINK(list, prevObj);
176
177 link->prevObject = prevObj;
178 link->nextObject = target;
179 prevLnk->nextObject = object;
180 OBJ_TO_LINK(list, target)->prevObject = object;
181 list->numObjects++;
182 }
183 }
184
185 /*---------------------------------------------------------------------------*
186 Name: RemoveListObject
187
188 Description: オブジェクトをリストから削除します。
189
190 Arguments: list: リスト構造体へのポインタ。
191 object: リストから削除したいオブジェクトへのポインタ。
192
193 Returns: なし。
194 *---------------------------------------------------------------------------*/
195 void
RemoveListObject(NNSFndList * list,void * object)196 RemoveListObject(NNSFndList* list, void* object)
197 {
198 NNSFndLink* link;
199
200 NN_TASSERT_(list );
201 NN_TASSERT_(object);
202
203 link = OBJ_TO_LINK(list, object);
204
205 if (link->prevObject == NULL)
206 {
207 list->headObject = link->nextObject;
208 }
209 else
210 {
211 OBJ_TO_LINK(list, link->prevObject)->nextObject = link->nextObject;
212 }
213 if (link->nextObject == NULL)
214 {
215 list->tailObject = link->prevObject;
216 }
217 else
218 {
219 OBJ_TO_LINK(list, link->nextObject)->prevObject = link->prevObject;
220 }
221 link->prevObject = NULL;
222 link->nextObject = NULL;
223 list->numObjects--;
224 }
225
226 /*---------------------------------------------------------------------------*
227 Name: GetNextListObject
228
229 Description: objectで指定されたオブジェクトの次に繋がれているオブジェクト
230 を返します。objectにNULLが指定されていた場合には、リストの先
231 頭に繋がれているオブジェクトを返します。
232
233 Arguments: list: リスト構造体へのポインタ。
234 object: リスト中のオブジェクトへのポインタ。
235
236 Returns: 指定されたオブジェクトの次のオブジェクトへのポインタを返しま
237 す。もし、次のオブジェクトが無ければ、NULLを返します。
238 *---------------------------------------------------------------------------*/
239 void*
GetNextListObject(const NNSFndList * list,const void * object)240 GetNextListObject(const NNSFndList* list, const void* object)
241 {
242 NN_TASSERT_(list);
243
244 if (object == NULL)
245 {
246 return list->headObject;
247 }
248 return OBJ_TO_LINK(list, object)->nextObject;
249 }
250
251 /*---------------------------------------------------------------------------*
252 Name: GetPrevListObject
253
254 Description: objectで指定されたオブジェクトの前に繋がれているオブジェクト
255 を返します。objectにNULLが指定されていた場合には、リストの後
256 尾に繋がれているオブジェクトを返します。
257
258 Arguments: list: リスト構造体へのポインタ。
259 object: リスト中のオブジェクトへのポインタ。
260
261 Returns: 指定されたオブジェクトの前のオブジェクトへのポインタを返しま
262 す。もし、前のオブジェクトが無ければ、NULLを返します。
263 *---------------------------------------------------------------------------*/
264 void*
GetPrevListObject(const NNSFndList * list,const void * object)265 GetPrevListObject(const NNSFndList* list, const void* object)
266 {
267 NN_TASSERT_(list);
268
269 if (object == NULL)
270 {
271 return list->tailObject;
272 }
273 return OBJ_TO_LINK(list, object)->prevObject;
274 }
275
276 /*---------------------------------------------------------------------------*
277 Name: GetNthListObject
278
279 Description: リストのN番目に繋がれているオブジェクトへのポインタを返しま
280 す。先頭から順番にリストをたどる為、リストの後部に繋がれてい
281 オブジェクト程、時間がかかります。
282
283 Arguments: index: オブジェクトのインデックス。
284
285 Returns: オブジェクトへのポインタを返します。もし、指定されたインデッ
286 クスのオブジェクトが無かった場合には、NULLが返ります。
287 *---------------------------------------------------------------------------*/
288 void*
GetNthListObject(const NNSFndList * list,u16 index)289 GetNthListObject(const NNSFndList* list, u16 index)
290 {
291 int count = 0;
292 NNSFndLink* object = NULL;
293
294 NN_TASSERT_(list);
295
296 // while ((object = GetNextListObject(list, object)) != NULL)
297 // for Horizon
298 while ((object = reinterpret_cast<NNSFndLink*>(
299 GetNextListObject(list, object))) != NULL)
300 {
301 if (index == count)
302 {
303 return object;
304 }
305 count++;
306 }
307 return NULL;
308 }
309
310 }}} // namespace nn::os::fnd
311
312