1/*
2 * Copyright 2002 Marcus Overhagen. All Rights Reserved.
3 * This file may be used under the terms of the MIT License.
4 */
5
6
7/*!	This works like a cache for time source objects, to make sure
8	each team only has one object representation for each time source.
9*/
10
11
12#include "TimeSourceObjectManager.h"
13
14#include <stdio.h>
15
16#include <Autolock.h>
17#include <MediaRoster.h>
18
19#include <MediaDebug.h>
20#include <MediaMisc.h>
21
22#include "TimeSourceObject.h"
23
24
25namespace BPrivate {
26namespace media {
27
28
29TimeSourceObjectManager* gTimeSourceObjectManager;
30	// initialized by BMediaRoster.
31
32
33TimeSourceObjectManager::TimeSourceObjectManager()
34	:
35	BLocker("time source object manager")
36{
37}
38
39
40TimeSourceObjectManager::~TimeSourceObjectManager()
41{
42	CALLED();
43
44	// force unloading all currently loaded time sources
45	NodeMap::iterator iterator = fMap.begin();
46	for (; iterator != fMap.end(); iterator++) {
47		BTimeSource* timeSource = iterator->second;
48
49		PRINT(1, "Forcing release of TimeSource id %ld...\n", timeSource->ID());
50		int32 debugCount = 0;
51		while (timeSource->Release() != NULL)
52			debugCount++;
53
54		PRINT(1, "Forcing release of TimeSource done, released %d times\n",
55			debugCount);
56	}
57}
58
59
60/*!	BMediaRoster::MakeTimeSourceFor does use this function to request
61	a time source object. If it is already in memory, it will be
62	Acquired(), if not, a new TimeSourceObject will be created.
63*/
64BTimeSource*
65TimeSourceObjectManager::GetTimeSource(const media_node& node)
66{
67	CALLED();
68	BAutolock _(this);
69
70	PRINT(1, "TimeSourceObjectManager::GetTimeSource, node id %ld\n",
71		node.node);
72
73	NodeMap::iterator found = fMap.find(node.node);
74	if (found != fMap.end())
75		return dynamic_cast<BTimeSource*>(found->second->Acquire());
76
77	// time sources are not accounted in node reference counting
78	BTimeSource* timeSource = new(std::nothrow) TimeSourceObject(node);
79	if (timeSource == NULL)
80		return NULL;
81
82	fMap.insert(std::make_pair(node.node, timeSource));
83	return timeSource;
84}
85
86
87/*!	This function is called during deletion of the time source object.
88*/
89void
90TimeSourceObjectManager::ObjectDeleted(BTimeSource* timeSource)
91{
92	CALLED();
93	BAutolock _(this);
94
95	PRINT(1, "TimeSourceObjectManager::ObjectDeleted, node id %ld\n",
96		timeSource->ID());
97
98	fMap.erase(timeSource->ID());
99
100	status_t status = BMediaRoster::Roster()->ReleaseNode(timeSource->Node());
101	if (status != B_OK) {
102		ERROR("TimeSourceObjectManager::ObjectDeleted, ReleaseNode failed\n");
103	}
104}
105
106
107}	// namespace media
108}	// namespace BPrivate
109