1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: SdGlobalResourceContainer.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sd.hxx"
34 #include "tools/SdGlobalResourceContainer.hxx"
39 using namespace ::com::sun::star
;
40 using namespace ::com::sun::star::uno
;
46 //===== SdGlobalResourceContainer::Implementation =============================
48 class SdGlobalResourceContainer::Implementation
51 friend class SdGlobalResourceContainer
;
52 static SdGlobalResourceContainer
* mpInstance
;
56 /** All instances of SdGlobalResource in this vector are owned by the
57 container and will be destroyed when the container is destroyed.
59 typedef ::std::vector
<SdGlobalResource
*> ResourceList
;
60 ResourceList maResources
;
62 typedef ::std::vector
<boost::shared_ptr
<SdGlobalResource
> > SharedResourceList
;
63 SharedResourceList maSharedResources
;
65 typedef ::std::vector
<Reference
<XInterface
> > XInterfaceResourceList
;
66 XInterfaceResourceList maXInterfaceResources
;
73 SdGlobalResourceContainer
& SdGlobalResourceContainer::Instance (void)
75 DBG_ASSERT(Implementation::mpInstance
!=NULL
,
76 "SdGlobalResourceContainer::Instance(): instance has been deleted");
77 // Maybe we should throw an exception when the instance has been deleted.
78 return *Implementation::mpInstance
;
81 SdGlobalResourceContainer
*
82 SdGlobalResourceContainer::Implementation::mpInstance
= NULL
;
87 //===== SdGlobalResourceContainer =============================================
89 void SdGlobalResourceContainer::AddResource (
90 ::std::auto_ptr
<SdGlobalResource
> pResource
)
92 ::osl::MutexGuard
aGuard (mpImpl
->maMutex
);
94 Implementation::ResourceList::iterator iResource
;
95 iResource
= ::std::find (
96 mpImpl
->maResources
.begin(),
97 mpImpl
->maResources
.end(),
99 if (iResource
== mpImpl
->maResources
.end())
100 mpImpl
->maResources
.push_back(pResource
.get());
103 // Because the given resource is an auto_ptr it is highly unlikely
104 // that we come here. But who knows?
106 "SdGlobalResourceContainer:AddResource(): Resource added twice.");
108 // We can not put the auto_ptr into the vector so we release the
109 // auto_ptr and document that we take ownership explicitly.
116 void SdGlobalResourceContainer::AddResource (
117 ::boost::shared_ptr
<SdGlobalResource
> pResource
)
119 ::osl::MutexGuard
aGuard (mpImpl
->maMutex
);
121 Implementation::SharedResourceList::iterator iResource
;
122 iResource
= ::std::find (
123 mpImpl
->maSharedResources
.begin(),
124 mpImpl
->maSharedResources
.end(),
126 if (iResource
== mpImpl
->maSharedResources
.end())
127 mpImpl
->maSharedResources
.push_back(pResource
);
131 "SdGlobalResourceContainer:AddResource(): Resource added twice.");
138 void SdGlobalResourceContainer::AddResource (const Reference
<XInterface
>& rxResource
)
140 ::osl::MutexGuard
aGuard (mpImpl
->maMutex
);
142 Implementation::XInterfaceResourceList::iterator iResource
;
143 iResource
= ::std::find (
144 mpImpl
->maXInterfaceResources
.begin(),
145 mpImpl
->maXInterfaceResources
.end(),
147 if (iResource
== mpImpl
->maXInterfaceResources
.end())
148 mpImpl
->maXInterfaceResources
.push_back(rxResource
);
152 "SdGlobalResourceContainer:AddResource(): Resource added twice.");
159 ::std::auto_ptr
<SdGlobalResource
> SdGlobalResourceContainer::ReleaseResource (
160 SdGlobalResource
* pResource
)
162 ::std::auto_ptr
<SdGlobalResource
> pResult (NULL
);
164 ::osl::MutexGuard
aGuard (mpImpl
->maMutex
);
166 Implementation::ResourceList::iterator iResource
;
167 iResource
= ::std::find (
168 mpImpl
->maResources
.begin(),
169 mpImpl
->maResources
.end(),
171 if (iResource
!= mpImpl
->maResources
.end())
173 pResult
.reset (*iResource
);
174 mpImpl
->maResources
.erase(iResource
);
183 SdGlobalResourceContainer::SdGlobalResourceContainer (void)
184 : mpImpl (new SdGlobalResourceContainer::Implementation())
186 Implementation::mpInstance
= this;
192 SdGlobalResourceContainer::~SdGlobalResourceContainer (void)
194 ::osl::MutexGuard
aGuard (mpImpl
->maMutex
);
196 // Release the resources in reversed order of their addition to the
197 // container. This is because a resource A added before resource B
198 // may have been created due to a request of B. Thus B depends on A and
199 // should be destroyed first.
200 Implementation::ResourceList::reverse_iterator iResource
;
201 for (iResource
= mpImpl
->maResources
.rbegin();
202 iResource
!= mpImpl
->maResources
.rend();
208 // The SharedResourceList has not to be released manually. We just
209 // assert resources that are still held by someone other than us.
210 Implementation::SharedResourceList::reverse_iterator iSharedResource
;
211 for (iSharedResource
= mpImpl
->maSharedResources
.rbegin();
212 iSharedResource
!= mpImpl
->maSharedResources
.rend();
215 if ( ! iSharedResource
->unique())
217 SdGlobalResource
* pResource
= iSharedResource
->get();
218 OSL_TRACE(" %p %d", pResource
, iSharedResource
->use_count());
219 DBG_ASSERT(iSharedResource
->unique(),
220 "SdGlobalResource still held in ~SdGlobalResourceContainer");
224 Implementation::XInterfaceResourceList::reverse_iterator iXInterfaceResource
;
225 for (iXInterfaceResource
= mpImpl
->maXInterfaceResources
.rbegin();
226 iXInterfaceResource
!= mpImpl
->maXInterfaceResources
.rend();
227 ++iXInterfaceResource
)
229 Reference
<lang::XComponent
> xComponent (*iXInterfaceResource
, UNO_QUERY
);
230 *iXInterfaceResource
= NULL
;
232 xComponent
->dispose();
235 DBG_ASSERT(Implementation::mpInstance
== this,
236 "~SdGlobalResourceContainer(): more than one instance of singleton");
237 Implementation::mpInstance
= NULL
;
243 } // end of namespace sd