cid#1607171 Data race condition
[LibreOffice.git] / reportdesign / source / core / api / Groups.cxx
bloba6d9b0633e1517960e6ced25e2e5b04329212507
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
19 #include <Groups.hxx>
20 #include <Group.hxx>
21 #include <ReportDefinition.hxx>
22 #include <com/sun/star/lang/NoSupportException.hpp>
23 #include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
24 #include <o3tl/safeint.hxx>
25 #include <core_resource.hxx>
26 #include <strings.hrc>
27 #include <utility>
29 namespace reportdesign
32 using namespace com::sun::star;
34 OGroups::OGroups(const rtl::Reference< OReportDefinition >& _xParent,uno::Reference< uno::XComponentContext > context)
35 :GroupsBase(m_aMutex)
36 ,m_aContainerListeners(m_aMutex)
37 ,m_xContext(std::move(context))
38 ,m_xParent(_xParent)
42 // TODO: VirtualFunctionFinder: This is virtual function!
44 OGroups::~OGroups()
48 void SAL_CALL OGroups::dispose()
50 cppu::WeakComponentImplHelperBase::dispose();
53 // TODO: VirtualFunctionFinder: This is virtual function!
55 void SAL_CALL OGroups::disposing()
57 for(auto& rGroup : m_aGroups)
58 rGroup->dispose();
59 m_aGroups.clear();
60 lang::EventObject aDisposeEvent( getXWeak() );
61 m_aContainerListeners.disposeAndClear( aDisposeEvent );
62 m_xContext.clear();
65 // XGroups
66 uno::Reference< report::XReportDefinition > SAL_CALL OGroups::getReportDefinition()
68 return m_xParent.get();
71 uno::Reference< report::XGroup > SAL_CALL OGroups::createGroup( )
73 return new OGroup(this,m_xContext);
76 // XIndexContainer
77 void SAL_CALL OGroups::insertByIndex( ::sal_Int32 Index, const uno::Any& aElement )
80 ::osl::MutexGuard aGuard(m_aMutex);
81 bool bAdd = (Index == static_cast<sal_Int32>(m_aGroups.size()));
82 if ( !bAdd )
83 checkIndex(Index);
84 uno::Reference< report::XGroup > xGroup(aElement,uno::UNO_QUERY);
85 if ( !xGroup.is() )
86 throw lang::IllegalArgumentException(RptResId(RID_STR_ARGUMENT_IS_NULL),*this,2);
88 if ( bAdd )
89 m_aGroups.push_back(xGroup);
90 else
92 TGroups::iterator aPos = m_aGroups.begin();
93 ::std::advance(aPos,Index);
94 m_aGroups.insert(aPos, xGroup);
97 // notify our container listeners
98 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::Any(Index), aElement, uno::Any());
99 m_aContainerListeners.notifyEach(&container::XContainerListener::elementInserted,aEvent);
103 void SAL_CALL OGroups::removeByIndex( ::sal_Int32 Index )
105 uno::Reference< report::XGroup > xGroup;
107 ::osl::MutexGuard aGuard(m_aMutex);
108 checkIndex(Index);
109 TGroups::iterator aPos = m_aGroups.begin();
110 ::std::advance(aPos,Index);
111 xGroup = *aPos;
112 m_aGroups.erase(aPos);
114 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::Any(Index), uno::Any(xGroup), uno::Any());
115 m_aContainerListeners.notifyEach(&container::XContainerListener::elementRemoved,aEvent);
118 // XIndexReplace
119 void SAL_CALL OGroups::replaceByIndex( ::sal_Int32 Index, const uno::Any& Element )
121 uno::Any aOldElement;
123 ::osl::MutexGuard aGuard(m_aMutex);
124 checkIndex(Index);
125 uno::Reference< report::XGroup > xGroup(Element,uno::UNO_QUERY);
126 if ( !xGroup.is() )
127 throw lang::IllegalArgumentException(RptResId(RID_STR_ARGUMENT_IS_NULL),*this,2);
128 TGroups::iterator aPos = m_aGroups.begin();
129 ::std::advance(aPos,Index);
130 aOldElement <<= *aPos;
131 *aPos = std::move(xGroup);
134 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::Any(Index), Element, aOldElement);
135 m_aContainerListeners.notifyEach(&container::XContainerListener::elementReplaced,aEvent);
138 // XIndexAccess
139 ::sal_Int32 SAL_CALL OGroups::getCount( )
141 ::osl::MutexGuard aGuard(m_aMutex);
142 return m_aGroups.size();
145 uno::Any SAL_CALL OGroups::getByIndex( ::sal_Int32 Index )
147 ::osl::MutexGuard aGuard(m_aMutex);
148 checkIndex(Index);
149 TGroups::const_iterator aPos = m_aGroups.begin();
150 ::std::advance(aPos,Index);
151 return uno::Any(*aPos);
154 // XElementAccess
155 uno::Type SAL_CALL OGroups::getElementType( )
157 return cppu::UnoType<report::XGroup>::get();
160 sal_Bool SAL_CALL OGroups::hasElements( )
162 ::osl::MutexGuard aGuard(m_aMutex);
163 return !m_aGroups.empty();
166 // XChild
167 uno::Reference< uno::XInterface > SAL_CALL OGroups::getParent( )
169 return m_xParent;
172 void SAL_CALL OGroups::setParent( const uno::Reference< uno::XInterface >& /*Parent*/ )
174 throw lang::NoSupportException();
177 // XContainer
178 void SAL_CALL OGroups::addContainerListener( const uno::Reference< container::XContainerListener >& xListener )
180 m_aContainerListeners.addInterface(xListener);
183 void SAL_CALL OGroups::removeContainerListener( const uno::Reference< container::XContainerListener >& xListener )
185 m_aContainerListeners.removeInterface(xListener);
188 void OGroups::checkIndex(sal_Int32 _nIndex)
190 if ( _nIndex < 0 || m_aGroups.size() <= o3tl::make_unsigned(_nIndex) )
191 throw lang::IndexOutOfBoundsException();
197 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */