Amesos2 - Direct Sparse Solver Interfaces  Version of the Day
Amesos2_MultiVecAdapter_def.hpp
1 // @HEADER
2 //
3 // ***********************************************************************
4 //
5 // Amesos2: Templated Direct Sparse Solver Package
6 // Copyright 2011 Sandia Corporation
7 //
8 // Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
9 // the U.S. Government retains certain rights in this software.
10 //
11 // Redistribution and use in source and binary forms, with or without
12 // modification, are permitted provided that the following conditions are
13 // met:
14 //
15 // 1. Redistributions of source code must retain the above copyright
16 // notice, this list of conditions and the following disclaimer.
17 //
18 // 2. Redistributions in binary form must reproduce the above copyright
19 // notice, this list of conditions and the following disclaimer in the
20 // documentation and/or other materials provided with the distribution.
21 //
22 // 3. Neither the name of the Corporation nor the names of the
23 // contributors may be used to endorse or promote products derived from
24 // this software without specific prior written permission.
25 //
26 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
27 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
30 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
31 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
32 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
33 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
34 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
35 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
36 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 //
38 // Questions? Contact Michael A. Heroux (maherou@sandia.gov)
39 //
40 // ***********************************************************************
41 //
42 // @HEADER
43 
44 
45 #ifndef AMESOS2_MULTIVECADAPTER_DEF_HPP
46 #define AMESOS2_MULTIVECADAPTER_DEF_HPP
47 
49 // EpetraMultiVecAdapter_def.hpp not included because the specialization is not a template
51 
52 #include "Amesos2_Util.hpp" // for getDistributionMap
53 
54 namespace Amesos2{
55 
56  namespace Util {
57 
59  // Pointer-getting utilities //
61 
62  template <typename MV, typename V>
63  typename vector_pointer_helper<MV, V>::ptr_return_type *
64  vector_pointer_helper<MV, V>::get_pointer_to_vector ( const Teuchos::Ptr< MV > &mv ) {
65  return mv->getMVPointer_impl();
66  }
67 
68  template <typename MV, typename V>
69  typename vector_pointer_helper<MV, V>::ptr_return_type *
70  vector_pointer_helper<MV, V>::get_pointer_to_vector ( Teuchos::Ptr< MV > &mv ) {
71  return mv->getMVPointer_impl();
72  }
73 
74  template <typename MV, typename V>
75  typename vector_pointer_helper<MV, V>::ptr_return_type *
76  vector_pointer_helper<MV, V>::get_pointer_to_vector ( const Teuchos::Ptr< const MV > &mv ) {
77  return mv->getMVPointer_impl();
78  }
79 
80  template <typename MV, typename V>
81  typename vector_pointer_helper<MV, V>::ptr_return_type *
82  vector_pointer_helper<MV, V>::get_pointer_to_vector ( Teuchos::Ptr< const MV > &mv ) {
83  return mv->getMVPointer_impl();
84  }
85 
86 
88  // Copy-getting utilities //
90 
91  /*
92  * If the multivector scalar type and the desired scalar tpye are
93  * the same, then we can do a simple straight copy.
94  */
95  template <typename MV>
96  void same_type_get_copy<MV>::apply(const Teuchos::Ptr<const MV> mv,
97  const Teuchos::ArrayView<typename MV::scalar_t>& v,
98  const size_t ldx,
99  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
100  EDistribution distribution )
101  {
102  mv->get1dCopy (v, ldx, distribution_map, distribution);
103  }
104 
105  /*
106  * In the case where the scalar type of the multi-vector and the
107  * corresponding S type are different, then we need to first get a
108  * copy of the scalar values, then convert each one into the S
109  * type before inserting into the vals array.
110  */
111  template <typename MV, typename S>
112  void diff_type_get_copy<MV,S>::
113  apply (const Teuchos::Ptr<const MV> mv,
114  const Teuchos::ArrayView<S>& v,
115  const size_t ldx,
116  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
117  EDistribution distribution )
118  {
119  typedef typename MV::scalar_t mv_scalar_t;
120  typedef typename Teuchos::Array<mv_scalar_t>::size_type size_type;
121 
122  TEUCHOS_TEST_FOR_EXCEPTION(
123  mv.getRawPtr () == NULL, std::invalid_argument,
124  "Amesos2::diff_type_get_copy::apply: mv is null.");
125  TEUCHOS_TEST_FOR_EXCEPTION(
126  distribution_map.getRawPtr () == NULL, std::invalid_argument,
127  "Amesos2::diff_type_get_copy::apply: distribution_map is null.");
128 
129  const size_type vals_length = v.size ();
130  Teuchos::Array<mv_scalar_t> vals_tmp (vals_length);
131 
132  mv->get1dCopy (vals_tmp (), ldx, distribution_map, distribution);
133  for (size_type i = 0; i < vals_length; ++i) {
134  v[i] = Teuchos::as<S> (vals_tmp[i]);
135  }
136  }
137 
144  template <class MV, typename S>
146  do_get (const Teuchos::Ptr<const MV>& mv,
147  const Teuchos::ArrayView<S>& vals,
148  const size_t ldx,
149  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
150  EDistribution distribution)
151  {
152  // Dispatch to the copy function appropriate for the type
153  if_then_else<is_same<typename MV::scalar_t,S>::value,
154  same_type_get_copy<MV>,
155  diff_type_get_copy<MV,S> >::type::apply (mv, vals, ldx, distribution_map, distribution);
156  }
157 
158  template <class MV, typename S>
160  do_get (const Teuchos::Ptr<const MV>& mv,
161  const Teuchos::ArrayView<S>& vals,
162  const size_t ldx,
163  EDistribution distribution,
164  typename MV::global_ordinal_t indexBase)
165  {
166  typedef typename MV::local_ordinal_t lo_t;
167  typedef typename MV::global_ordinal_t go_t;
168  typedef typename MV::global_size_t gs_t;
169  typedef typename MV::node_t node_t;
170 
171  TEUCHOS_TEST_FOR_EXCEPTION(
172  mv.getRawPtr () == NULL, std::invalid_argument,
173  "Amesos2::get_1d_copy_helper::do_get(5 args): mv is null.");
174 
175  Teuchos::RCP<const Tpetra::Map<lo_t,go_t,node_t> > map
176  = Amesos2::Util::getDistributionMap<lo_t,go_t,gs_t,node_t> (distribution,
177  mv->getGlobalLength (),
178  mv->getComm (),
179  indexBase,
180  mv->getMap());
181 
182  do_get (mv, vals, ldx, Teuchos::ptrInArg (*map), distribution);
183  }
184 
185  template <class MV, typename S>
186  void get_1d_copy_helper<MV,S>::do_get(const Teuchos::Ptr<const MV>& mv,
187  const Teuchos::ArrayView<S>& vals,
188  const size_t ldx)
189  {
190  typedef Tpetra::Map<typename MV::local_ordinal_t,
191  typename MV::global_ordinal_t,
192  typename MV::node_t> map_type;
193  TEUCHOS_TEST_FOR_EXCEPTION(
194  mv.getRawPtr () == NULL, std::invalid_argument,
195  "Amesos2::get_1d_copy_helper::do_get(3 args): mv is null.");
196 
197  Teuchos::RCP<const map_type> map = mv->getMap ();
198  TEUCHOS_TEST_FOR_EXCEPTION(
199  map.is_null (), std::invalid_argument,
200  "Amesos2::get_1d_copy_helper::do_get(3 args): mv->getMap() is null.");
201 
202 
203  do_get (mv, vals, ldx, Teuchos::ptrInArg (*map), ROOTED); // ROOTED the default here for now
204  }
205 
206  template <class MV, typename KV>
207  void get_1d_copy_helper_kokkos_view<MV,KV>::
208  do_get (const Teuchos::Ptr<const MV>& mv,
209  KV& kokkos_vals,
210  const size_t ldx,
211  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
212  EDistribution distribution)
213  {
214  mv->get1dCopy_kokkos_view(kokkos_vals, ldx, distribution_map, distribution);
215  }
216 
217  template <class MV, typename KV>
218  void get_1d_copy_helper_kokkos_view<MV,KV>::
219  do_get (const Teuchos::Ptr<const MV>& mv,
220  KV& kokkos_vals,
221  const size_t ldx,
222  EDistribution distribution,
223  typename MV::global_ordinal_t indexBase)
224  {
225  typedef typename MV::local_ordinal_t lo_t;
226  typedef typename MV::global_ordinal_t go_t;
227  typedef typename MV::global_size_t gs_t;
228  typedef typename MV::node_t node_t;
229 
230  TEUCHOS_TEST_FOR_EXCEPTION(
231  mv.getRawPtr () == NULL, std::invalid_argument,
232  "Amesos2::get_1d_copy_helper_kokkos_view::do_get(5 args): mv is null.");
233 
234  Teuchos::RCP<const Tpetra::Map<lo_t,go_t,node_t> > map
235  = Amesos2::Util::getDistributionMap<lo_t,go_t,gs_t,node_t> (distribution,
236  mv->getGlobalLength (),
237  mv->getComm (),
238  indexBase,
239  mv->getMap());
240 
241  do_get (mv, kokkos_vals, ldx, Teuchos::ptrInArg (*map), distribution);
242  }
243 
244  template <class MV, typename KV>
245  void get_1d_copy_helper_kokkos_view<MV,KV>::do_get(const Teuchos::Ptr<const MV>& mv,
246  KV& kokkos_vals,
247  const size_t ldx)
248  {
249  typedef Tpetra::Map<typename MV::local_ordinal_t,
250  typename MV::global_ordinal_t,
251  typename MV::node_t> map_type;
252  TEUCHOS_TEST_FOR_EXCEPTION(
253  mv.getRawPtr () == NULL, std::invalid_argument,
254  "Amesos2::get_1d_copy_helper::do_get(3 args): mv is null.");
255 
256  Teuchos::RCP<const map_type> map = mv->getMap ();
257  TEUCHOS_TEST_FOR_EXCEPTION(
258  map.is_null (), std::invalid_argument,
259  "Amesos2::get_1d_copy_helper_kokkos_view::do_get(3 args): mv->getMap() is null.");
260 
261  do_get (mv, kokkos_vals, ldx, Teuchos::ptrInArg (*map), ROOTED); // ROOTED the default here for now
262  }
263 
264 
266  // Copy-puting utilities //
268 
269  template <typename MV>
270  void same_type_data_put<MV>::apply(const Teuchos::Ptr<MV>& mv,
271  const Teuchos::ArrayView<typename MV::scalar_t>& data,
272  const size_t ldx,
273  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
274  EDistribution distribution )
275  {
276  mv->put1dData (data, ldx, distribution_map, distribution);
277  }
278 
279  /*
280  * In the case where the scalar type of the multi-vector and the
281  * corresponding S type are different, then we need to first get a
282  * copy of the scalar values, then convert each one into the S
283  * type before inserting into the vals array.
284  */
285  template <typename MV, typename S>
286  void diff_type_data_put<MV,S>::apply(const Teuchos::Ptr<MV>& mv,
287  const Teuchos::ArrayView<S>& data,
288  const size_t ldx,
289  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
290  EDistribution distribution )
291  {
292  typedef typename MV::scalar_t mv_scalar_t;
293  typedef typename Teuchos::Array<mv_scalar_t>::size_type size_type;
294 
295  TEUCHOS_TEST_FOR_EXCEPTION(
296  mv.getRawPtr () == NULL, std::invalid_argument,
297  "Amesos2::diff_type_data_put(4 args): mv is null.");
298 
299  const size_type vals_length = data.size ();
300  Teuchos::Array<mv_scalar_t> data_tmp (vals_length);
301 
302  for (size_type i = 0; i < vals_length; ++i) {
303  data_tmp[i] = Teuchos::as<mv_scalar_t> (data[i]);
304  }
305 
306  mv->put1dData (data_tmp (), ldx, distribution_map, distribution);
307  }
308 
309 
316  template <class MV, typename S>
317  void put_1d_data_helper<MV,S>::do_put(const Teuchos::Ptr<MV>& mv,
318  const Teuchos::ArrayView<S>& data,
319  const size_t ldx,
320  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
321  EDistribution distribution )
322  {
323  // Dispatch to the copy function appropriate for the type
324  if_then_else<is_same<typename MV::scalar_t,S>::value,
325  same_type_data_put<MV>,
326  diff_type_data_put<MV,S> >::type::apply(mv, data, ldx, distribution_map, distribution);
327  }
328 
329  template <class MV, typename S>
330  void put_1d_data_helper<MV,S>::do_put(const Teuchos::Ptr<MV>& mv,
331  const Teuchos::ArrayView<S>& data,
332  const size_t ldx,
333  EDistribution distribution, typename MV::global_ordinal_t indexBase)
334  {
335  typedef typename MV::local_ordinal_t lo_t;
336  typedef typename MV::global_ordinal_t go_t;
337  typedef typename MV::global_size_t gs_t;
338  typedef typename MV::node_t node_t;
339 
340  const Teuchos::RCP<const Tpetra::Map<lo_t,go_t,node_t> > map
341  = Amesos2::Util::getDistributionMap<lo_t,go_t,gs_t,node_t>(distribution,
342  mv->getGlobalLength(),
343  mv->getComm(),
344  indexBase,
345  mv->getMap());
346 
347  do_put(mv, data, ldx, Teuchos::ptrInArg(*map), distribution);
348  }
349 
350  template <class MV, typename S>
351  void put_1d_data_helper<MV,S>::do_put (const Teuchos::Ptr<MV>& mv,
352  const Teuchos::ArrayView<S>& data,
353  const size_t ldx)
354  {
355  const Teuchos::RCP<const Tpetra::Map<typename MV::local_ordinal_t,
356  typename MV::global_ordinal_t,
357  typename MV::node_t> > map
358  = mv->getMap();
359  do_put (mv, data, ldx, Teuchos::ptrInArg (*map), ROOTED); // Default as ROOTED for now
360  }
361 
362  template <class MV, typename KV>
363  void put_1d_data_helper_kokkos_view<MV,KV>::do_put(const Teuchos::Ptr<MV>& mv,
364  KV& kokkos_data,
365  const size_t ldx,
366  Teuchos::Ptr<const Tpetra::Map<typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t> > distribution_map,
367  EDistribution distribution )
368  {
369  mv->put1dData_kokkos_view(kokkos_data, ldx, distribution_map, distribution);
370  }
371 
372  template <class MV, typename KV>
373  void put_1d_data_helper_kokkos_view<MV,KV>::do_put(const Teuchos::Ptr<MV>& mv,
374  KV& kokkos_data,
375  const size_t ldx,
376  EDistribution distribution, typename MV::global_ordinal_t indexBase)
377  {
378  typedef typename MV::local_ordinal_t lo_t;
379  typedef typename MV::global_ordinal_t go_t;
380  typedef typename MV::global_size_t gs_t;
381  typedef typename MV::node_t node_t;
382 
383  const Teuchos::RCP<const Tpetra::Map<lo_t,go_t,node_t> > map
384  = Amesos2::Util::getDistributionMap<lo_t,go_t,gs_t,node_t>(distribution,
385  mv->getGlobalLength(),
386  mv->getComm(),
387  indexBase,
388  mv->getMap());
389 
390  do_put(mv, kokkos_data, ldx, Teuchos::ptrInArg(*map), distribution);
391  }
392 
393  template <class MV, typename KV>
394  void put_1d_data_helper_kokkos_view<MV,KV>::do_put (const Teuchos::Ptr<MV>& mv,
395  KV& kokkos_data,
396  const size_t ldx)
397  {
398  const Teuchos::RCP<const Tpetra::Map<typename MV::local_ordinal_t,
399  typename MV::global_ordinal_t,
400  typename MV::node_t> > map
401  = mv->getMap();
402  do_put (mv, kokkos_data, ldx, Teuchos::ptrInArg (*map), ROOTED); // Default as ROOTED for now
403  }
404 
405  } // end namespace Util
406 
407 } // end namespace Amesos2
408 
409 #endif // AMESOS2_EPETRAMULTIVECADAPTER_DEF
Utility functions for Amesos2.
Amesos2::MultiVecAdapter specialization for the Kokkos::View class.
static void do_get(const Teuchos::Ptr< const MV > &mv, const Teuchos::ArrayView< S > &vals, const size_t ldx, Teuchos::Ptr< const Tpetra::Map< typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t > > distribution_map, EDistribution distribution=ROOTED)
Helper class for getting 1-D copies of multivectors.
Definition: Amesos2_MultiVecAdapter_def.hpp:146
Amesos2::MultiVecAdapter specialization for the Tpetra::MultiVector class.
static void do_put(const Teuchos::Ptr< MV > &mv, const Teuchos::ArrayView< S > &data, const size_t ldx, Teuchos::Ptr< const Tpetra::Map< typename MV::local_ordinal_t, typename MV::global_ordinal_t, typename MV::node_t > > distribution_map, EDistribution distribution=ROOTED)
Helper class for putting 1-D data arrays into multivectors.
Definition: Amesos2_MultiVecAdapter_def.hpp:317
EDistribution
Definition: Amesos2_TypeDecl.hpp:123