Tpetra parallel linear algebra  Version of the Day
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Tpetra_FECrsMatrix_def.hpp
1 // @HEADER
2 // *****************************************************************************
3 // Tpetra: Templated Linear Algebra Services Package
4 //
5 // Copyright 2008 NTESS and the Tpetra contributors.
6 // SPDX-License-Identifier: BSD-3-Clause
7 // *****************************************************************************
8 // @HEADER
9 
10 #ifndef TPETRA_FECRSMATRIX_DEF_HPP
11 #define TPETRA_FECRSMATRIX_DEF_HPP
12 #include <sstream>
13 #include "Tpetra_CrsMatrix.hpp"
14 
15 namespace Tpetra {
16 
17 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
19 FECrsMatrix(const Teuchos::RCP<const fe_crs_graph_type>& graph,
20  const Teuchos::RCP<Teuchos::ParameterList>& params) :
21  // We want the OWNED_PLUS_SHARED graph here
22  // NOTE: The casts below are terrible, but necesssary
23  crs_matrix_type( graph->inactiveCrsGraph_.is_null() ? Teuchos::rcp_const_cast<crs_graph_type>(Teuchos::rcp_dynamic_cast<const crs_graph_type>(graph)) : graph->inactiveCrsGraph_,params),
24  feGraph_(graph)
25 
26 {
27  const char tfecfFuncName[] = "FECrsMatrix(RCP<const FECrsGraph>[, RCP<ParameterList>]): ";
28 
29  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC
30  (graph.is_null (), std::runtime_error, "Input graph is null.");
31  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC
32  (!graph->isFillComplete (), std::runtime_error, "Input graph is not "
33  "fill complete. You must call fillComplete on the graph before using "
34  "it to construct a FECrsMatrix. Note that calling resumeFill on the "
35  "graph makes it not fill complete, even if you had previously called "
36  "fillComplete. In that case, you must call fillComplete on the graph "
37  "again.");
38  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC
39  ( *graph->activeCrsGraph_!= FE::ACTIVE_OWNED,std::runtime_error,
40  "Input graph must be in FE::ACTIVE_OWNED mode when this constructor is called.");
41 
42  bool start_owned = false;
43  if (! params.is_null ()) {
44  if (params->isParameter ("start owned")) {
45  start_owned = params->get<bool>("start owned", start_owned);
46  }
47  }
48  if(start_owned) {
49  activeCrsMatrix_ = Teuchos::rcp(new FE::WhichActive(FE::ACTIVE_OWNED));
50  } else {
51  activeCrsMatrix_ = Teuchos::rcp(new FE::WhichActive(FE::ACTIVE_OWNED_PLUS_SHARED));
52  }
53 
54  // Make an "inactive" matrix, if we need to
55  if(!graph->inactiveCrsGraph_.is_null() ) {
56  // We are *requiring* memory aliasing here, so we'll grab the first chunk of the Owned+Shared matrix's values array to make the
57  // guy for the Owned matrix.
58  inactiveCrsMatrix_ = Teuchos::rcp(new crs_matrix_type(*this,graph));
59  }
60 
61  fillState_ = Teuchos::rcp(new FE::FillState(FE::FillState::closed));
62 }
63 
64 
65 
66 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
68  if(!inactiveCrsMatrix_.is_null() && *activeCrsMatrix_ == FE::ACTIVE_OWNED_PLUS_SHARED) {
69  // Do a self-export in "restricted mode"
70  this->doExport(*this,*feGraph_->ownedRowsImporter_,CM,true);
71  inactiveCrsMatrix_->fillComplete();
72  }
73  crs_matrix_type::fillComplete();
74 }//end doOverlapToLocal
75 
76 
77 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
79  // This should be a no-op for all of our purposes
80 }//end doLocalToOverlap
81 
82 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
84  if(*activeCrsMatrix_ == FE::ACTIVE_OWNED_PLUS_SHARED)
85  *activeCrsMatrix_ = FE::ACTIVE_OWNED;
86  else
87  *activeCrsMatrix_ = FE::ACTIVE_OWNED_PLUS_SHARED;
88 
89  if(inactiveCrsMatrix_.is_null()) return;
90 
91  this->swap(*inactiveCrsMatrix_);
92 
93 }//end switchActiveCrsMatrix
94 
95 
96 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
98  if(*activeCrsMatrix_ == FE::ACTIVE_OWNED_PLUS_SHARED) {
99  doOwnedPlusSharedToOwned(Tpetra::ADD);
100  switchActiveCrsMatrix();
101  }
102  else
103  throw std::runtime_error("FECrsMatrix: Local CrsMatrix already active. Cannot endFill()");
104 }
105 
106 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
107 void FECrsMatrix<Scalar, LocalOrdinal, GlobalOrdinal, Node>::beginFill() {
108  // Note: This does not throw an error since the on construction, the FECRS is in overlap mode. Ergo, calling beginFill(),
109  // like one should expect to do in a rational universe, should not cause an error.
110  if(*activeCrsMatrix_ == FE::ACTIVE_OWNED) {
111  this->resumeFill();
112  switchActiveCrsMatrix();
113  }
114  this->resumeFill();
115 }
116 
117 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
119  const char tfecfFuncName[] = "FECrsMatrix::beginAssembly: ";
120  if (*fillState_ != FE::FillState::closed)
121  {
122  std::ostringstream errmsg;
123  errmsg << "Cannot begin assembly, matrix is not in a closed state "
124  << "but is currently open for "
125  << (*fillState_ == FE::FillState::open ? "assembly" : "modification");
126  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
127  }
128  *fillState_ = FE::FillState::open;
129  this->beginFill();
130 }
131 
132 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
134  const char tfecfFuncName[] = "FECrsMatrix::endAssembly: ";
135  if (*fillState_ != FE::FillState::open)
136  {
137  std::ostringstream errmsg;
138  errmsg << "Cannot end assembly, matrix is not open for assembly "
139  << "but is currently "
140  << (*fillState_ == FE::FillState::closed ? "closed" : "open for modification");
141  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
142  }
143  *fillState_ = FE::FillState::closed;
144  this->endFill();
145 }
146 
147 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
149  const char tfecfFuncName[] = "FECrsMatrix::beginModify: ";
150  if (*fillState_ != FE::FillState::closed)
151  {
152  std::ostringstream errmsg;
153  errmsg << "Cannot begin modifying, matrix is not in a closed state "
154  << "but is currently open for "
155  << (*fillState_ == FE::FillState::open ? "assembly" : "modification");
156  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
157  }
158  *fillState_ = FE::FillState::modify;
159  this->resumeFill();
160 }
161 
162 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
164  const char tfecfFuncName[] = "FECrsMatrix::endModify: ";
165  if (*fillState_ != FE::FillState::modify)
166  {
167  std::ostringstream errmsg;
168  errmsg << "Cannot end modifying, matrix is not open to modify but is currently "
169  << (*fillState_ == FE::FillState::open ? "open for assembly" : "closed");
170  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
171  }
172  *fillState_ = FE::FillState::closed;
173  this->fillComplete();
174 }
175 
176 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
177 LocalOrdinal
179  impl_scalar_type rowVals[],
180  const crs_graph_type& graph,
181  const RowInfo& rowInfo,
182  const GlobalOrdinal inds[],
183  const impl_scalar_type newVals[],
184  const LocalOrdinal numElts)
185 {
186  const char tfecfFuncName[] = "FECrsMatrix::replaceGlobalValues: ";
187  if (*fillState_ != FE::FillState::open)
188  {
189  std::ostringstream errmsg;
190  errmsg << "Cannot replace global values, matrix is not open for assembly "
191  << "but is currently "
192  << (*fillState_ == FE::FillState::modify ? "open for modification" : "closed");
193  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
194  }
195  return crs_matrix_type::replaceGlobalValuesImpl(rowVals, graph, rowInfo, inds, newVals, numElts);
196 }
197 
198 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
199 LocalOrdinal
201  impl_scalar_type rowVals[],
202  const crs_graph_type& graph,
203  const RowInfo& rowInfo,
204  const LocalOrdinal inds[],
205  const impl_scalar_type newVals[],
206  const LocalOrdinal numElts)
207 {
208  const char tfecfFuncName[] = "FECrsMatrix::replaceLocalValues: ";
209  if (*fillState_ != FE::FillState::open && *fillState_ != FE::FillState::modify)
210  {
211  std::ostringstream errmsg;
212  errmsg << "Cannot replace local values, matrix is not open to fill/modify. "
213  << "The matrix is currently closed";
214  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
215  }
216  return crs_matrix_type::replaceLocalValuesImpl(rowVals, graph, rowInfo, inds, newVals, numElts);
217 }
218 
219 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
220 LocalOrdinal
221 FECrsMatrix<Scalar, LocalOrdinal, GlobalOrdinal, Node>::sumIntoGlobalValuesImpl(
222  impl_scalar_type rowVals[],
223  const crs_graph_type& graph,
224  const RowInfo& rowInfo,
225  const GlobalOrdinal inds[],
226  const impl_scalar_type newVals[],
227  const LocalOrdinal numElts,
228  const bool atomic)
229 {
230  const char tfecfFuncName[] = "FECrsMatrix::sumIntoGlobalValues: ";
231  if (*fillState_ != FE::FillState::open)
232  {
233  std::ostringstream errmsg;
234  errmsg << "Cannot sum in to global values, matrix is not open for assembly. "
235  << "The matrix is currently "
236  << (*fillState_ == FE::FillState::modify ? "open for modification" : "closed");
237  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
238  }
239  return crs_matrix_type::sumIntoGlobalValuesImpl(
240  rowVals, graph, rowInfo, inds, newVals, numElts, atomic
241  );
242 }
243 
244 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
245 LocalOrdinal
246 FECrsMatrix<Scalar, LocalOrdinal, GlobalOrdinal, Node>::sumIntoLocalValuesImpl(
247  impl_scalar_type rowVals[],
248  const crs_graph_type& graph,
249  const RowInfo& rowInfo,
250  const LocalOrdinal inds[],
251  const impl_scalar_type newVals[],
252  const LocalOrdinal numElts,
253  const bool atomic)
254 {
255  const char tfecfFuncName[] = "FECrsMatrix::sumIntoLocalValues: ";
256  if (*fillState_ != FE::FillState::open)
257  {
258  std::ostringstream errmsg;
259  errmsg << "Cannot sum in to local values, matrix is not open for assembly. "
260  << "The matrix is currently "
261  << (*fillState_ == FE::FillState::modify ? "open for modification" : "closed");
262  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
263  }
264  return crs_matrix_type::sumIntoLocalValuesImpl(
265  rowVals, graph, rowInfo, inds, newVals, numElts, atomic
266  );
267 }
268 
269 template<class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
270 void
271 FECrsMatrix<Scalar, LocalOrdinal, GlobalOrdinal, Node>::insertGlobalValuesImpl(
272  crs_graph_type& graph,
273  RowInfo& rowInfo,
274  const GlobalOrdinal gblColInds[],
275  const impl_scalar_type vals[],
276  const size_t numInputEnt)
277 {
278  const char tfecfFuncName[] = "FECrsMatrix::insertGlobalValues: ";
279  if (*fillState_ != FE::FillState::open)
280  {
281  std::ostringstream errmsg;
282  errmsg << "Cannot insert global values, matrix is not open for assembly. "
283  << "The matrix is currently "
284  << (*fillState_ == FE::FillState::modify ? "open for modification" : "closed");
285  TEUCHOS_TEST_FOR_EXCEPTION_CLASS_FUNC(true, std::logic_error, errmsg.str());
286  }
287  return crs_matrix_type::insertGlobalValuesImpl(graph, rowInfo, gblColInds, vals, numInputEnt);
288 }
289 
290 } // end namespace Tpetra
291 
292 
293 //
294 // Explicit instantiation macro
295 //
296 // Must be expanded from within the Tpetra namespace!
297 //
298 #define TPETRA_FECRSMATRIX_INSTANT(SCALAR,LO,GO,NODE) \
299  template class FECrsMatrix<SCALAR, LO, GO, NODE>;
300 
301 
302 
303 #endif // TPETRA_FECRSMATRIX_DEF
Sparse matrix that presents a row-oriented interface that lets users read or modify entries...
Sparse matrix that presents a row-oriented interface that lets users read or modify entries...
CrsMatrix< Scalar, LocalOrdinal, GlobalOrdinal, Node > crs_matrix_type
Parent CrsMatrix type using the same scalars.
LocalOrdinal replaceGlobalValuesImpl(impl_scalar_type rowVals[], const crs_graph_type &graph, const RowInfo &rowInfo, const GlobalOrdinal inds[], const impl_scalar_type newVals[], const LocalOrdinal numElts)
Overloads of modification methods.
Allocation information for a locally owned row in a CrsGraph or CrsMatrix.
void doOwnedToOwnedPlusShared(const CombineMode CM=Tpetra::ADD)
Migrate data from the owned to the owned+shared matrix Precondition: Must be FE_ACTIVE_OWNED mode...
void switchActiveCrsMatrix()
Switches which CrsGraph is active (without migrating data)
CombineMode
Rule for combining data in an Import or Export.
void beginAssembly()
Activates the owned+shared mode for assembly.
Sum new values.
void endModify()
Closes modification phase.
void doOwnedPlusSharedToOwned(const CombineMode CM=Tpetra::ADD)
Migrate data from the owned+shared to the owned matrix Since this is non-unique -&gt; unique...
FECrsMatrix(const Teuchos::RCP< const fe_crs_graph_type > &graph, const Teuchos::RCP< Teuchos::ParameterList > &params=Teuchos::null)
Constructor specifying one or two previously constructed graphs.
void endAssembly()
Migrates data to the owned mode.
A distributed graph accessed by rows (adjacency lists) and stored sparsely.
typename row_matrix_type::impl_scalar_type impl_scalar_type
The type used internally in place of Scalar.
void beginModify()
Activates the owned mode for modifying local values.