Merge remote-tracking branch 'redux/master' into sh4-pool
[tamarin-stm.git] / core / avmplusList-inlines.h
blob6049ec65982df40235c150261b8bd32f0a644ae9
1 /* -*- Mode: C++; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 4 -*- */
2 /* vi: set ts=4 sw=4 expandtab: (add to ~/.vimrc: set modeline modelines=5) */
3 /* ***** BEGIN LICENSE BLOCK *****
4 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
6 * The contents of this file are subject to the Mozilla Public License Version
7 * 1.1 (the "License"); you may not use this file except in compliance with
8 * the License. You may obtain a copy of the License at
9 * http://www.mozilla.org/MPL/
11 * Software distributed under the License is distributed on an "AS IS" basis,
12 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
13 * for the specific language governing rights and limitations under the
14 * License.
16 * The Original Code is [Open Source Virtual Machine.].
18 * The Initial Developer of the Original Code is
19 * Adobe System Incorporated.
20 * Portions created by the Initial Developer are Copyright (C) 2004-2006
21 * the Initial Developer. All Rights Reserved.
23 * Contributor(s):
24 * Adobe AS3 Team
26 * Alternatively, the contents of this file may be used under the terms of
27 * either the GNU General Public License Version 2 or later (the "GPL"), or
28 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
29 * in which case the provisions of the GPL or the LGPL are applicable instead
30 * of those above. If you wish to allow use of your version of this file only
31 * under the terms of either the GPL or the LGPL, and not to allow others to
32 * use your version of this file under the terms of the MPL, indicate your
33 * decision by deleting the provisions above and replace them with the notice
34 * and other provisions required by the GPL or the LGPL. If you do not delete
35 * the provisions above, a recipient may use your version of this file under
36 * the terms of any one of the MPL, the GPL or the LGPL.
38 * ***** END LICENSE BLOCK ***** */
40 #ifndef __avmplus_List_inlines__
41 #define __avmplus_List_inlines__
43 namespace avmplus
45 template<>
46 REALLY_INLINE bool TracedListData<Atom>::gcTrace(MMgc::GC* gc, size_t cursor)
48 const size_t work_increment = 2000/sizeof(void*);
49 const size_t work_count = len;
50 if (cursor * work_increment >= work_count)
51 return false;
53 size_t work = work_increment;
54 bool more = true;
55 if ((cursor + 1) * work_increment >= work_count)
57 work = work_count - (cursor * work_increment);
58 more = false;
61 gc->TraceAtoms(entries + (cursor*work_increment), work);
62 return more;
65 template<class T>
66 inline bool TracedListData<T>::gcTrace(MMgc::GC* gc, size_t cursor)
68 const size_t work_increment = 2000/sizeof(void*);
69 const size_t work_count = len;
70 if (cursor * work_increment >= work_count)
71 return false;
73 size_t work = work_increment;
74 bool more = true;
75 if ((cursor + 1) * work_increment >= work_count)
77 work = work_count - (cursor * work_increment);
78 more = false;
81 gc->TraceLocations(entries + (cursor*work_increment), work);
82 return more;
85 // ----------------------------
87 template<class T>
88 REALLY_INLINE /*static*/ void DataListHelper<T>::wbData(const void* /*container*/, LISTDATA** address, LISTDATA* data)
90 *address = data;
93 template<class T>
94 REALLY_INLINE /*static*/ typename DataListHelper<T>::TYPE DataListHelper<T>::load(LISTDATA* data, uint32_t index)
96 AvmAssert(data != NULL);
97 return data->entries[index];
100 template<class T>
101 REALLY_INLINE /*static*/ void DataListHelper<T>::store(LISTDATA* data, uint32_t index, TYPE value)
103 AvmAssert(data != NULL);
104 data->entries[index] = value;
107 template<class T>
108 REALLY_INLINE /*static*/ void DataListHelper<T>::storeInEmpty(LISTDATA* data, uint32_t index, TYPE value)
110 AvmAssert(data != NULL);
111 // This is commented out because it's not necessary for safety of a DataList,
112 // and it can generate an assert in List::insert(), which uses storeInEmpty() for efficiency;
113 // since DataListHelper::moveRange doesn't zero out the cleared space we could get this
114 // assertion firing. Better to neuter this assertion than add a unnecessary zeroing-out
115 // to moveRange() just to pacify it.
116 // AvmAssert(data->entries[index] == 0);
117 data->entries[index] = value;
120 template<class T>
121 REALLY_INLINE /*static*/ void DataListHelper<T>::clearRange(LISTDATA* data, uint32_t start, uint32_t count)
123 AvmAssert(count > 0);
124 VMPI_memset(&data->entries[start], 0, count*sizeof(T));
127 template<class T>
128 REALLY_INLINE /*static*/ void DataListHelper<T>::moveRange(LISTDATA* data, uint32_t srcStart, uint32_t dstStart, uint32_t count)
130 VMPI_memmove(&data->entries[dstStart], &data->entries[srcStart], count * sizeof(T));
133 template<class T>
134 REALLY_INLINE /*static*/ void DataListHelper<T>::gcTrace(MMgc::GC* gc, LISTDATA** loc)
136 AvmAssert(!gc->IsPointerToGCPage(*loc));
137 (void)gc; (void)loc;
140 // ----------------------------
142 REALLY_INLINE /*static*/ void GCListHelper::wbData(const void* container, LISTDATA** address, LISTDATA* data)
144 MMgc::GC* const gc = data->gc();
145 if (gc->IsPointerToGCPage(container))
147 WB(gc, gc->FindBeginningFast(container), address, data);
149 else
151 *address = data;
155 REALLY_INLINE /*static*/ GCListHelper::TYPE GCListHelper::load(LISTDATA* data, uint32_t index)
157 AvmAssert(data != NULL);
158 return data->entries[index];
161 REALLY_INLINE /*static*/ void GCListHelper::store(LISTDATA* data, uint32_t index, TYPE value)
163 AvmAssert(data != NULL);
164 WB(data->gc(), data, &data->entries[index], value);
167 REALLY_INLINE /*static*/ void GCListHelper::storeInEmpty(LISTDATA* data, uint32_t index, TYPE value)
169 AvmAssert(data != NULL);
170 AvmAssert(data->entries[index] == 0);
171 WB(data->gc(), data, &data->entries[index], value);
174 REALLY_INLINE /*static*/ void GCListHelper::clearRange(LISTDATA* data, uint32_t start, uint32_t count)
176 AvmAssert(count > 0);
177 VMPI_memset(&data->entries[start], 0, count*sizeof(MMgc::GCObject*));
180 REALLY_INLINE /*static*/ void GCListHelper::moveRange(LISTDATA* data, uint32_t srcStart, uint32_t dstStart, uint32_t count)
182 AvmAssert(data != NULL);
183 data->gc()->movePointersWithinBlock((void**)data,
184 uint32_t((char*)(&data->entries[dstStart]) - (char*)data),
185 uint32_t((char*)(&data->entries[srcStart]) - (char*)data),
186 count,
187 /*zeroEmptied*/ true);
190 REALLY_INLINE /*static*/ void GCListHelper::gcTrace(MMgc::GC* gc, LISTDATA** loc)
192 gc->TraceLocation(loc);
195 // ----------------------------
197 REALLY_INLINE /*static*/ void RCListHelper::wbData(const void* container, LISTDATA** address, LISTDATA* data)
199 MMgc::GC* const gc = data->gc();
200 if (gc->IsPointerToGCPage(container))
202 WB(gc, gc->FindBeginningFast(container), address, data);
204 else
206 *address = data;
210 REALLY_INLINE /*static*/ RCListHelper::TYPE RCListHelper::load(LISTDATA* data, uint32_t index)
212 AvmAssert(data != NULL);
213 return data->entries[index];
216 REALLY_INLINE /*static*/ void RCListHelper::store(LISTDATA* data, uint32_t index, TYPE value)
218 AvmAssert(data != NULL);
219 WBRC(data->gc(), data, &data->entries[index], value);
222 REALLY_INLINE /*static*/ void RCListHelper::storeInEmpty(LISTDATA* data, uint32_t index, TYPE value)
224 AvmAssert(data != NULL);
225 AvmAssert(data->entries[index] == 0);
226 // We can't use WriteBarrierRC_ctor here, as it will call GetGC() on the address, which might be
227 // wrong if the allocation is large. Instead, replicate the necessary code inline (ugh) in
228 // the tradition of AvmCore::atomWriteBarrier_ctor...
229 if (value)
231 if (data->gc()->BarrierActive())
232 data->gc()->InlineWriteBarrierTrap(data);
233 value->IncrementRef();
234 data->entries[index] = value;
238 REALLY_INLINE /*static*/ void RCListHelper::clearRange(LISTDATA* data, uint32_t start, uint32_t count)
240 AvmAssert(count > 0);
241 for (uint32_t i = start, n = start + count; i < n; i++)
243 if (data->entries[i])
245 data->entries[i]->DecrementRef();
246 data->entries[i] = 0;
251 REALLY_INLINE /*static*/ void RCListHelper::moveRange(LISTDATA* data, uint32_t srcStart, uint32_t dstStart, uint32_t count)
253 AvmAssert(data != NULL);
254 data->gc()->movePointersWithinBlock((void**)data,
255 uint32_t((char*)(&data->entries[dstStart]) - (char*)data),
256 uint32_t((char*)(&data->entries[srcStart]) - (char*)data),
257 count,
258 /*zeroEmptied*/ true);
261 REALLY_INLINE /*static*/ void RCListHelper::gcTrace(MMgc::GC* gc, LISTDATA** loc)
263 gc->TraceLocation(loc);
266 // ----------------------------
268 REALLY_INLINE /*static*/ void AtomListHelper::wbData(const void* container, LISTDATA** address, LISTDATA* data)
270 MMgc::GC* const gc = data->gc();
271 if (gc->IsPointerToGCPage(container))
273 WB(gc, gc->FindBeginningFast(container), address, data);
275 else
277 *address = data;
281 REALLY_INLINE /*static*/ AtomListHelper::TYPE AtomListHelper::load(LISTDATA* data, uint32_t index)
283 AvmAssert(data != NULL);
284 return data->entries[index];
287 REALLY_INLINE /*static*/ void AtomListHelper::store(LISTDATA* data, uint32_t index, TYPE value)
289 AvmAssert(data != NULL);
290 AvmCore::atomWriteBarrier(data->gc(), data, &data->entries[index], value);
293 REALLY_INLINE /*static*/ void AtomListHelper::storeInEmpty(LISTDATA* data, uint32_t index, TYPE value)
295 AvmAssert(data != NULL);
296 // newly-allocated space clears to 0; clearRange() clears to nullObjectAtom.
297 // Both are "empty" as far as AtomList is concerned.
298 AvmAssert(data->entries[index] == 0 || data->entries[index] == nullObjectAtom);
299 AvmCore::atomWriteBarrier_ctor(data->gc(), data, &data->entries[index], value);
302 REALLY_INLINE /*static*/ void AtomListHelper::clearRange(LISTDATA* data, uint32_t start, uint32_t count)
304 AvmAssert(count > 0);
305 AvmCore::decrementAtomRegion_null(&data->entries[start], count);
308 REALLY_INLINE /*static*/ void AtomListHelper::moveRange(LISTDATA* data, uint32_t srcStart, uint32_t dstStart, uint32_t count)
310 AvmAssert(data != NULL);
311 data->gc()->movePointersWithinBlock((void**)data,
312 uint32_t((char*)(&data->entries[dstStart]) - (char*)data),
313 uint32_t((char*)(&data->entries[srcStart]) - (char*)data),
314 count,
315 /*zeroEmptied*/ true);
318 REALLY_INLINE /*static*/ void AtomListHelper::gcTrace(MMgc::GC* gc, LISTDATA** loc)
320 gc->TraceLocation(loc);
323 // ----------------------------
325 REALLY_INLINE /*static*/ void WeakRefListHelper::wbData(const void* container, LISTDATA** address, LISTDATA* data)
327 MMgc::GC* const gc = data->gc();
328 if (gc->IsPointerToGCPage(container))
330 WB(gc, gc->FindBeginningFast(container), address, data);
332 else
334 *address = data;
338 REALLY_INLINE /*static*/ WeakRefListHelper::TYPE WeakRefListHelper::load(LISTDATA* data, uint32_t index)
340 AvmAssert(data != NULL);
341 MMgc::GCWeakRef* weak = data->entries[index];
342 return weak ? (TYPE)weak->get() : NULL;
345 REALLY_INLINE /*static*/ void WeakRefListHelper::store(LISTDATA* data, uint32_t index, TYPE value)
347 AvmAssert(data != NULL);
348 MMgc::GCWeakRef* weak = value ? value->GetWeakRef() : NULL;
349 WB(data->gc(), data, &data->entries[index], weak);
352 REALLY_INLINE /*static*/ void WeakRefListHelper::storeInEmpty(LISTDATA* data, uint32_t index, TYPE value)
354 AvmAssert(data != NULL);
355 AvmAssert(data->entries[index] == 0);
356 store(data, index, value);
359 REALLY_INLINE /*static*/ void WeakRefListHelper::clearRange(LISTDATA* data, uint32_t start, uint32_t count)
361 AvmAssert(count > 0);
362 VMPI_memset(&data->entries[start], 0, count*sizeof(STORAGE));
365 REALLY_INLINE /*static*/ void WeakRefListHelper::moveRange(LISTDATA* data, uint32_t srcStart, uint32_t dstStart, uint32_t count)
367 AvmAssert(data != NULL);
368 data->gc()->movePointersWithinBlock((void**)data,
369 uint32_t((char*)(&data->entries[dstStart]) - (char*)data),
370 uint32_t((char*)(&data->entries[srcStart]) - (char*)data),
371 count,
372 /*zeroEmptied*/ true);
375 REALLY_INLINE /*static*/ void WeakRefListHelper::gcTrace(MMgc::GC* gc, LISTDATA** loc)
377 gc->TraceLocation(loc);
380 // ----------------------------
382 template<class T, class ListHelper>
383 REALLY_INLINE bool ListImpl<T,ListHelper>::isEmpty() const
385 return m_data->len == 0;
388 template<class T, class ListHelper>
389 REALLY_INLINE uint32_t ListImpl<T,ListHelper>::length() const
391 return m_data->len;
394 template<class T, class ListHelper>
395 REALLY_INLINE uint32_t ListImpl<T,ListHelper>::capacity() const
397 return uint32_t((ListHelper::LISTDATA::getSize(m_data) - offsetof(typename ListHelper::LISTDATA, entries)) /
398 sizeof(typename ListHelper::STORAGE));
401 template<class T, class ListHelper>
402 REALLY_INLINE T ListImpl<T,ListHelper>::get(uint32_t index) const
404 AvmAssert(index < m_data->len);
405 return ListHelper::load(m_data, index);
408 template<class T, class ListHelper>
409 REALLY_INLINE void ListImpl<T,ListHelper>::replace(uint32_t index, T value)
411 AvmAssert(index < m_data->len);
412 ListHelper::store(m_data, index, value);
415 template<class T, class ListHelper>
416 REALLY_INLINE void ListImpl<T,ListHelper>::set(uint32_t index, T value)
418 // Yes, this is worth inlining, according to performance testing.
419 if (index >= m_data->len)
421 ensureCapacityExtra(index, 1);
422 m_data->len = index+1;
424 ListHelper::store(m_data, index, value);
427 template<class T, class ListHelper>
428 REALLY_INLINE T ListImpl<T,ListHelper>::first() const
430 AvmAssert(m_data->len > 0);
431 return ListHelper::load(m_data, 0);
434 template<class T, class ListHelper>
435 REALLY_INLINE T ListImpl<T,ListHelper>::last() const
437 AvmAssert(m_data->len > 0);
438 return ListHelper::load(m_data, m_data->len-1);
441 template<class T, class ListHelper>
442 REALLY_INLINE T ListImpl<T,ListHelper>::removeFirst()
444 AvmAssert(!isEmpty());
445 return removeAt(0);
448 template<class T, class ListHelper>
449 REALLY_INLINE T ListImpl<T,ListHelper>::operator[](uint32_t index) const
451 AvmAssert(index < m_data->len);
452 return ListHelper::load(m_data, index);
455 template<class T, class ListHelper>
456 REALLY_INLINE void ListImpl<T,ListHelper>::ensureCapacityExtra(uint32_t cap, uint32_t extra)
458 MMGC_STATIC_ASSERT(0xFFFFFFFF > kListMaxLength);
459 uint32_t const ncap = (cap > 0xFFFFFFFF - extra) ? // if true, cap + extra will overflow a uint32_t...
460 0xFFFFFFFF : // ...in that case, choose a size that will definitely fail in ensureCapacityImpl.
461 (cap + extra);
463 if (ncap > capacity())
465 ensureCapacityImpl(ncap);
469 template<class T, class ListHelper>
470 REALLY_INLINE void ListImpl<T,ListHelper>::ensureCapacity(uint32_t cap)
472 AvmAssert(m_data != NULL);
473 if (cap > capacity())
475 ensureCapacityImpl(cap);
479 template<class T, class ListHelper>
480 REALLY_INLINE uint64_t ListImpl<T,ListHelper>::bytesUsed() const
482 AvmAssert(m_data != NULL);
483 return ListHelper::LISTDATA::getSize(m_data);
486 template<class T, class ListHelper>
487 REALLY_INLINE /*static*/ typename ListHelper::LISTDATA* ListImpl<T,ListHelper>::allocData(MMgc::GC* gc, uint32_t cap)
489 AvmAssert(cap <= kListMaxLength);
490 typename ListHelper::LISTDATA* newData = ListHelper::LISTDATA::create(gc, cap);
491 newData->len = 0;
492 newData->set_gc(gc);
493 return newData;
496 template<class T, class ListHelper>
497 REALLY_INLINE void ListImpl<T,ListHelper>::skipDestructor()
499 // Note that we explicitly do not attempt to free the data here;
500 // this method should only be called in situations where we
501 // know that MMGC has already been torn down, thus an attempt
502 // to free the data would be unsafe.
503 m_data = NULL;
506 // ----------------------------
509 template<class T>
510 REALLY_INLINE GCList<T>::GCList(MMgc::GC* gc, uint32_t capacity, const TYPE* args)
511 : m_list(gc, capacity, (MMgc::GCObject* const*)args)
513 MMGC_STATIC_ASSERT((TypeSniffer<T>::isGCObject::value == true ||
514 TypeSniffer<T>::isGCFinalizedObject::value == true ||
515 TypeSniffer<T>::isGCTraceableObject::value == true) &&
516 TypeSniffer<T>::isRCObject::value == false);
517 MMGC_STATIC_ASSERT(TypeSniffer<T>::isNonPointer::value == true);
520 template<class T>
521 REALLY_INLINE bool GCList<T>::isEmpty() const
523 return m_list.isEmpty();
526 template<class T>
527 REALLY_INLINE uint32_t GCList<T>::length() const
529 return m_list.length();
532 template<class T>
533 REALLY_INLINE uint32_t GCList<T>::capacity() const
535 return m_list.capacity();
538 template<class T>
539 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::get(uint32_t index) const
541 return reinterpret_cast<TYPE>(m_list.get(index));
544 template<class T>
545 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::first() const
547 return reinterpret_cast<TYPE>(m_list.first());
550 template<class T>
551 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::last() const
553 return reinterpret_cast<TYPE>(m_list.last());
556 template<class T>
557 REALLY_INLINE void GCList<T>::replace(uint32_t index, TYPE value)
559 m_list.replace(index, reinterpret_cast<MMgc::GCObject*>(value));
562 template<class T>
563 REALLY_INLINE void GCList<T>::set(uint32_t index, TYPE value)
565 m_list.set(index, reinterpret_cast<MMgc::GCObject*>(value));
568 template<class T>
569 REALLY_INLINE void GCList<T>::add(TYPE value)
571 m_list.add(reinterpret_cast<MMgc::GCObject*>(value));
574 template<class T>
575 REALLY_INLINE void GCList<T>::add(const GCList<T>& that)
577 m_list.add(*(const LIST*)&that);
580 template<class T>
581 REALLY_INLINE void GCList<T>::insert(uint32_t index, TYPE value, uint32_t count)
583 m_list.insert(index, reinterpret_cast<MMgc::GCObject*>(value), count);
586 template<class T>
587 REALLY_INLINE void GCList<T>::insert(uint32_t index, const TYPE* args, uint32_t argc)
589 m_list.insert(index, args, argc);
592 template<class T>
593 REALLY_INLINE void GCList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const TYPE* args)
595 m_list.splice(insertPoint, insertCount, deleteCount, args);
598 template<class T>
599 REALLY_INLINE void GCList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const GCList<T>& args, uint32_t argsOffset)
601 m_list.splice(insertPoint, insertCount, deleteCount, args, argsOffset);
604 template<class T>
605 REALLY_INLINE void GCList<T>::reverse()
607 m_list.reverse();
610 template<class T>
611 REALLY_INLINE void GCList<T>::clear()
613 m_list.clear();
616 template<class T>
617 REALLY_INLINE int32_t GCList<T>::indexOf(TYPE value) const
619 return m_list.indexOf(reinterpret_cast<MMgc::GCObject*>(value));
622 template<class T>
623 REALLY_INLINE int32_t GCList<T>::lastIndexOf(TYPE value) const
625 return m_list.lastIndexOf(reinterpret_cast<MMgc::GCObject*>(value));
628 template<class T>
629 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::removeAt(uint32_t index)
631 return reinterpret_cast<TYPE>(m_list.removeAt(index));
634 template<class T>
635 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::removeFirst()
637 return reinterpret_cast<TYPE>(m_list.removeFirst());
640 template<class T>
641 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::removeLast()
643 return reinterpret_cast<TYPE>(m_list.removeLast());
646 template<class T>
647 REALLY_INLINE typename GCList<T>::TYPE GCList<T>::operator[](uint32_t index) const
649 return reinterpret_cast<TYPE>(m_list[index]);
652 template<class T>
653 REALLY_INLINE void GCList<T>::ensureCapacity(uint32_t cap)
655 m_list.ensureCapacity(cap);
658 template<class T>
659 REALLY_INLINE uint64_t GCList<T>::bytesUsed() const
661 return m_list.bytesUsed();
664 template<class T>
665 REALLY_INLINE void GCList<T>::skipDestructor()
667 m_list.skipDestructor();
670 template<class T>
671 REALLY_INLINE void GCList<T>::gcTrace(MMgc::GC* gc)
673 m_list.gcTrace(gc);
676 // ----------------------------
678 template<class T>
679 REALLY_INLINE RCList<T>::RCList(MMgc::GC* gc, uint32_t capacity, const TYPE* args)
680 : m_list(gc, capacity, (MMgc::RCObject* const*)args)
682 MMGC_STATIC_ASSERT(TypeSniffer<T>::isRCObject::value == true);
683 MMGC_STATIC_ASSERT(TypeSniffer<T>::isNonPointer::value == true);
686 template<class T>
687 REALLY_INLINE bool RCList<T>::isEmpty() const
689 return m_list.isEmpty();
692 template<class T>
693 REALLY_INLINE uint32_t RCList<T>::length() const
695 return m_list.length();
698 template<class T>
699 REALLY_INLINE uint32_t RCList<T>::capacity() const
701 return m_list.capacity();
704 template<class T>
705 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::get(uint32_t index) const
707 return reinterpret_cast<TYPE>(m_list.get(index));
710 template<class T>
711 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::first() const
713 return reinterpret_cast<TYPE>(m_list.first());
716 template<class T>
717 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::last() const
719 return reinterpret_cast<TYPE>(m_list.last());
722 template<class T>
723 REALLY_INLINE void RCList<T>::replace(uint32_t index, TYPE value)
725 m_list.replace(index, value);
728 template<class T>
729 REALLY_INLINE void RCList<T>::set(uint32_t index, TYPE value)
731 m_list.set(index, value);
734 template<class T>
735 REALLY_INLINE void RCList<T>::add(TYPE value)
737 m_list.add(value);
740 template<class T>
741 REALLY_INLINE void RCList<T>::add(const RCList<T>& that)
743 m_list.add(*(const LIST*)&that);
746 template<class T>
747 REALLY_INLINE void RCList<T>::insert(uint32_t index, TYPE value, uint32_t count)
749 m_list.insert(index, value, count);
752 template<class T>
753 REALLY_INLINE void RCList<T>::insert(uint32_t index, const TYPE* args, uint32_t argc)
755 m_list.insert(index, args, argc);
758 template<class T>
759 REALLY_INLINE void RCList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const TYPE* args)
761 m_list.splice(insertPoint, insertCount, deleteCount, args);
764 template<class T>
765 REALLY_INLINE void RCList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const RCList<T>& args, uint32_t argsOffset)
767 m_list.splice(insertPoint, insertCount, deleteCount, args, argsOffset);
770 template<class T>
771 REALLY_INLINE void RCList<T>::reverse()
773 m_list.reverse();
776 template<class T>
777 REALLY_INLINE void RCList<T>::clear()
779 m_list.clear();
782 template<class T>
783 REALLY_INLINE int32_t RCList<T>::indexOf(TYPE value) const
785 return m_list.indexOf(value);
788 template<class T>
789 REALLY_INLINE int32_t RCList<T>::lastIndexOf(TYPE value) const
791 return m_list.lastIndexOf(value);
794 template<class T>
795 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::removeAt(uint32_t index)
797 return reinterpret_cast<TYPE>(m_list.removeAt(index));
800 template<class T>
801 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::removeFirst()
803 return reinterpret_cast<TYPE>(m_list.removeFirst());
806 template<class T>
807 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::removeLast()
809 return reinterpret_cast<TYPE>(m_list.removeLast());
812 template<class T>
813 REALLY_INLINE typename RCList<T>::TYPE RCList<T>::operator[](uint32_t index) const
815 return reinterpret_cast<TYPE>(m_list[index]);
818 template<class T>
819 REALLY_INLINE void RCList<T>::ensureCapacity(uint32_t cap)
821 m_list.ensureCapacity(cap);
824 template<class T>
825 REALLY_INLINE uint64_t RCList<T>::bytesUsed() const
827 return m_list.bytesUsed();
830 template<class T>
831 REALLY_INLINE void RCList<T>::skipDestructor()
833 m_list.skipDestructor();
836 template<class T>
837 REALLY_INLINE void RCList<T>::gcTrace(MMgc::GC* gc)
839 m_list.gcTrace(gc);
843 // ----------------------------
845 template<class T>
846 REALLY_INLINE UnmanagedPointerList<T>::UnmanagedPointerList(MMgc::GC* gc, uint32_t capacity, const T* args)
847 : m_list(gc, capacity, (const UnmanagedPointer*)args)
849 // We must not be a GC/RCObject.
850 MMGC_STATIC_ASSERT(TypeSniffer<T>::isGCObject::value == false &&
851 TypeSniffer<T>::isGCFinalizedObject::value == false &&
852 TypeSniffer<T>::isRCObject::value == false &&
853 TypeSniffer<T>::isGCTraceableObject::value == false);
855 // BUT we MUST be a pointer type.
856 MMGC_STATIC_ASSERT(TypeSniffer<T>::isNonPointer::value == false);
859 template<class T>
860 REALLY_INLINE bool UnmanagedPointerList<T>::isEmpty() const
862 return m_list.isEmpty();
865 template<class T>
866 REALLY_INLINE uint32_t UnmanagedPointerList<T>::length() const
868 return m_list.length();
871 template<class T>
872 REALLY_INLINE uint32_t UnmanagedPointerList<T>::capacity() const
874 return m_list.capacity();
877 template<class T>
878 REALLY_INLINE T UnmanagedPointerList<T>::get(uint32_t index) const
880 return (T)m_list.get(index);
883 template<class T>
884 REALLY_INLINE T UnmanagedPointerList<T>::first() const
886 return (T)m_list.first();
889 template<class T>
890 REALLY_INLINE T UnmanagedPointerList<T>::last() const
892 return (T)m_list.last();
895 template<class T>
896 REALLY_INLINE void UnmanagedPointerList<T>::replace(uint32_t index, T value)
898 m_list.replace(index, (UnmanagedPointer)value);
901 template<class T>
902 REALLY_INLINE void UnmanagedPointerList<T>::set(uint32_t index, T value)
904 m_list.set(index, (UnmanagedPointer)value);
907 template<class T>
908 REALLY_INLINE void UnmanagedPointerList<T>::add(T value)
910 m_list.add((UnmanagedPointer)value);
913 template<class T>
914 REALLY_INLINE void UnmanagedPointerList<T>::add(const UnmanagedPointerList<T>& that)
916 m_list.add(*(const LIST*)&that);
919 template<class T>
920 REALLY_INLINE void UnmanagedPointerList<T>::insert(uint32_t index, T value, uint32_t count)
922 m_list.insert(index, (UnmanagedPointer)value, count);
925 template<class T>
926 REALLY_INLINE void UnmanagedPointerList<T>::insert(uint32_t index, const T* args, uint32_t argc)
928 m_list.insert(index, args, argc);
931 template<class T>
932 REALLY_INLINE void UnmanagedPointerList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const T* args)
934 m_list.splice(insertPoint, insertCount, deleteCount, args);
937 template<class T>
938 REALLY_INLINE void UnmanagedPointerList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const UnmanagedPointerList<T>& args, uint32_t argsOffset)
940 m_list.splice(insertPoint, insertCount, deleteCount, args, argsOffset);
943 template<class T>
944 REALLY_INLINE void UnmanagedPointerList<T>::reverse()
946 m_list.reverse();
949 template<class T>
950 REALLY_INLINE void UnmanagedPointerList<T>::clear()
952 m_list.clear();
955 template<class T>
956 REALLY_INLINE int32_t UnmanagedPointerList<T>::indexOf(T value) const
958 return m_list.indexOf((UnmanagedPointer)value);
961 template<class T>
962 REALLY_INLINE int32_t UnmanagedPointerList<T>::lastIndexOf(T value) const
964 return m_list.lastIndexOf((UnmanagedPointer)value);
967 template<class T>
968 REALLY_INLINE T UnmanagedPointerList<T>::removeAt(uint32_t index)
970 return (T)m_list.removeAt(index);
973 template<class T>
974 REALLY_INLINE T UnmanagedPointerList<T>::removeFirst()
976 return (T)m_list.removeFirst();
979 template<class T>
980 REALLY_INLINE T UnmanagedPointerList<T>::removeLast()
982 return (T)m_list.removeLast();
985 template<class T>
986 REALLY_INLINE T UnmanagedPointerList<T>::operator[](uint32_t index) const
988 return (T)m_list[index];
991 template<class T>
992 REALLY_INLINE void UnmanagedPointerList<T>::ensureCapacity(uint32_t cap)
994 m_list.ensureCapacity(cap);
997 template<class T>
998 REALLY_INLINE uint64_t UnmanagedPointerList<T>::bytesUsed() const
1000 return m_list.bytesUsed();
1003 template<class T>
1004 REALLY_INLINE void UnmanagedPointerList<T>::skipDestructor()
1006 m_list.skipDestructor();
1009 template<class T>
1010 REALLY_INLINE void UnmanagedPointerList<T>::gcTrace(MMgc::GC* gc)
1012 m_list.gcTrace(gc);
1015 // ----------------------------
1017 template<class T>
1018 REALLY_INLINE WeakRefList<T>::WeakRefList(MMgc::GC* gc, uint32_t capacity, const TYPE* args)
1019 : m_list(gc, capacity, (MMgc::GCObject* const*)args)
1021 MMGC_STATIC_ASSERT(TypeSniffer<T>::isGCObject::value ||
1022 TypeSniffer<T>::isGCFinalizedObject::value ||
1023 TypeSniffer<T>::isRCObject::value ||
1024 TypeSniffer<T>::isGCTraceableObject::value);
1025 MMGC_STATIC_ASSERT(TypeSniffer<T>::isNonPointer::value == true);
1028 template<class T>
1029 REALLY_INLINE bool WeakRefList<T>::isEmpty() const
1031 return m_list.isEmpty();
1034 template<class T>
1035 REALLY_INLINE uint32_t WeakRefList<T>::length() const
1037 return m_list.length();
1040 template<class T>
1041 REALLY_INLINE uint32_t WeakRefList<T>::capacity() const
1043 return m_list.capacity();
1046 template<class T>
1047 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::get(uint32_t index) const
1049 return reinterpret_cast<TYPE>(m_list.get(index));
1052 template<class T>
1053 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::first() const
1055 return reinterpret_cast<TYPE>(m_list.first());
1058 template<class T>
1059 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::last() const
1061 return reinterpret_cast<TYPE>(m_list.last());
1064 template<class T>
1065 REALLY_INLINE void WeakRefList<T>::replace(uint32_t index, TYPE value)
1067 m_list.replace(index, to_gc(value));
1070 template<class T>
1071 REALLY_INLINE void WeakRefList<T>::set(uint32_t index, TYPE value)
1073 m_list.set(index, reinterpret_cast<MMgc::GCObject*>(value));
1076 template<class T>
1077 REALLY_INLINE void WeakRefList<T>::add(TYPE value)
1079 m_list.add(reinterpret_cast<MMgc::GCObject*>(value));
1082 template<class T>
1083 REALLY_INLINE void WeakRefList<T>::add(const WeakRefList<T>& that)
1085 m_list.add(*(const LIST*)&that);
1088 template<class T>
1089 REALLY_INLINE void WeakRefList<T>::insert(uint32_t index, TYPE value, uint32_t count)
1091 m_list.insert(index, reinterpret_cast<MMgc::GCObject*>(value), count);
1094 template<class T>
1095 REALLY_INLINE void WeakRefList<T>::insert(uint32_t index, const TYPE* args, uint32_t argc)
1097 m_list.insert(index, args, argc);
1100 template<class T>
1101 REALLY_INLINE void WeakRefList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const TYPE* args)
1103 m_list.splice(insertPoint, insertCount, deleteCount, args);
1106 template<class T>
1107 REALLY_INLINE void WeakRefList<T>::splice(uint32_t insertPoint, uint32_t insertCount, uint32_t deleteCount, const WeakRefList<T>& args, uint32_t argsOffset)
1109 m_list.splice(insertPoint, insertCount, deleteCount, args, argsOffset);
1112 template<class T>
1113 REALLY_INLINE void WeakRefList<T>::reverse()
1115 m_list.reverse();
1118 template<class T>
1119 REALLY_INLINE void WeakRefList<T>::clear()
1121 m_list.clear();
1124 template<class T>
1125 REALLY_INLINE int32_t WeakRefList<T>::indexOf(TYPE value) const
1127 return m_list.indexOf(reinterpret_cast<MMgc::GCObject*>(value));
1130 template<class T>
1131 REALLY_INLINE int32_t WeakRefList<T>::lastIndexOf(TYPE value) const
1133 return m_list.lastIndexOf(reinterpret_cast<MMgc::GCObject*>(value));
1136 template<class T>
1137 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::removeAt(uint32_t index)
1139 return reinterpret_cast<TYPE>(m_list.removeAt(index));
1142 template<class T>
1143 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::removeFirst()
1145 return reinterpret_cast<TYPE>(m_list.removeFirst());
1148 template<class T>
1149 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::removeLast()
1151 return reinterpret_cast<TYPE>(m_list.removeLast());
1154 template<class T>
1155 REALLY_INLINE typename WeakRefList<T>::TYPE WeakRefList<T>::operator[](uint32_t index) const
1157 return reinterpret_cast<TYPE>(m_list[index]);
1160 template<class T>
1161 REALLY_INLINE void WeakRefList<T>::ensureCapacity(uint32_t cap)
1163 m_list.ensureCapacity(cap);
1166 template<class T>
1167 REALLY_INLINE uint64_t WeakRefList<T>::bytesUsed() const
1169 return m_list.bytesUsed();
1172 template<class T>
1173 REALLY_INLINE void WeakRefList<T>::skipDestructor()
1175 m_list.skipDestructor();
1178 template<class T>
1179 REALLY_INLINE uint32_t WeakRefList<T>::removeCollectedItems()
1181 return m_list.removeNullItems();
1184 template<class T>
1185 REALLY_INLINE void WeakRefList<T>::gcTrace(MMgc::GC* gc)
1187 m_list.gcTrace(gc);
1190 // ----------------------------
1192 template<class T>
1193 REALLY_INLINE DataList<T>::DataList(MMgc::GC* gc, uint32_t capacity, const T* args)
1194 : ListImpl< T, DataListHelper<T> >(gc, capacity, args)
1196 // We must not be a pointer type.
1197 MMGC_STATIC_ASSERT(TypeSniffer<T>::isNonPointer::value == true);
1199 // If you make a NonGCObject list that holds GC/RCObjects, you are almost
1200 // certainly making a mistake. (Redundant to the above check, but left in
1201 // for emphasis.)
1202 MMGC_STATIC_ASSERT(TypeSniffer<T>::isGCObject::value == false &&
1203 TypeSniffer<T>::isGCFinalizedObject::value == false &&
1204 TypeSniffer<T>::isRCObject::value == false &&
1205 TypeSniffer<T>::isGCTraceableObject::value == false);
1208 // ----------------------------
1210 template<class T>
1211 REALLY_INLINE DataListAccessor<T>::DataListAccessor(DataList<T>* v) : m_list(v)
1215 template<class T>
1216 REALLY_INLINE T* DataListAccessor<T>::addr()
1218 return (m_list != NULL) ? m_list->m_data->entries : (T*)NULL;
1221 template<class T>
1222 REALLY_INLINE uint32_t DataListAccessor<T>::length()
1224 return (m_list != NULL) ? m_list->length() : 0;
1227 // ----------------------------
1229 template<class T>
1230 REALLY_INLINE HeapList<T>::HeapList(MMgc::GC* gc, uint32_t capacity, const typename T::TYPE* args)
1231 : list(gc, capacity, args)
1236 #endif /* __avmplus_List_inlines__ */