1 /******************************************************************************
2  * Copyright 1998-2019 Lawrence Livermore National Security, LLC and other
3  * HYPRE Project Developers. See the top-level COPYRIGHT file for details.
4  *
5  * SPDX-License-Identifier: (Apache-2.0 OR MIT)
6  ******************************************************************************/
7 
8 #include <math.h>
9 #include <stdlib.h>
10 
11 #include "multivector.h"
12 #include "_hypre_utilities.h"
13 
14 /* abstract multivector */
15 struct mv_MultiVector
16 {
17   void*	data;      /* the pointer to the actual multivector */
18   HYPRE_Int	ownsData;
19 
20   mv_InterfaceInterpreter* interpreter; /* a structure that defines
21 					      multivector operations */
22 } ;
23 
24 void *
mv_MultiVectorGetData(mv_MultiVectorPtr x)25 mv_MultiVectorGetData (mv_MultiVectorPtr x)
26 {
27   hypre_assert (x!=NULL);
28   return x->data;
29 }
30 
31 mv_MultiVectorPtr
mv_MultiVectorWrap(mv_InterfaceInterpreter * ii,void * data,HYPRE_Int ownsData)32 mv_MultiVectorWrap( mv_InterfaceInterpreter* ii, void * data, HYPRE_Int ownsData )
33 {
34   mv_MultiVectorPtr x;
35 
36   x = hypre_TAlloc(struct mv_MultiVector, 1, HYPRE_MEMORY_HOST);
37   hypre_assert( x != NULL );
38 
39   x->interpreter = ii;
40   x->data = data;
41   x->ownsData = ownsData;
42 
43   return x;
44 }
45 
46 mv_MultiVectorPtr
mv_MultiVectorCreateFromSampleVector(void * ii_,HYPRE_Int n,void * sample)47 mv_MultiVectorCreateFromSampleVector( void* ii_, HYPRE_Int n, void* sample ) {
48 
49   mv_MultiVectorPtr x;
50   mv_InterfaceInterpreter* ii = (mv_InterfaceInterpreter*)ii_;
51 
52   x = hypre_TAlloc(struct mv_MultiVector, 1, HYPRE_MEMORY_HOST);
53   hypre_assert( x != NULL );
54 
55   x->interpreter = ii;
56   x->data = (ii->CreateMultiVector)( ii, n, sample );
57   x->ownsData = 1;
58 
59   return x;
60 }
61 
62 mv_MultiVectorPtr
mv_MultiVectorCreateCopy(mv_MultiVectorPtr x,HYPRE_Int copyValues)63 mv_MultiVectorCreateCopy( mv_MultiVectorPtr x, HYPRE_Int copyValues ) {
64 
65   mv_MultiVectorPtr y;
66   void* data;
67   mv_InterfaceInterpreter* ii;
68 
69   hypre_assert( x != NULL );
70   ii = x->interpreter;
71 
72   y = hypre_TAlloc(struct mv_MultiVector, 1, HYPRE_MEMORY_HOST);
73   hypre_assert( y != NULL );
74 
75   data = (ii->CopyCreateMultiVector)( x->data, copyValues );
76 
77   y->interpreter = ii;
78   y->data = data;
79   y->ownsData = 1;
80 
81   return y;
82 }
83 
84 void
mv_MultiVectorDestroy(mv_MultiVectorPtr v)85 mv_MultiVectorDestroy( mv_MultiVectorPtr v) {
86 
87   if ( v == NULL )
88     return;
89 
90   if ( v->ownsData )
91     (v->interpreter->DestroyMultiVector)( v->data );
92   hypre_TFree( v ,HYPRE_MEMORY_HOST);
93 }
94 
95 void
mv_MultiVectorSetMask(mv_MultiVectorPtr v,HYPRE_Int * mask)96 mv_MultiVectorSetMask( mv_MultiVectorPtr v, HYPRE_Int* mask ) {
97 
98   hypre_assert( v != NULL );
99   (v->interpreter->SetMask)( v->data, mask );
100 }
101 
102 HYPRE_Int
mv_MultiVectorWidth(mv_MultiVectorPtr v)103 mv_MultiVectorWidth( mv_MultiVectorPtr v ) {
104 
105   if ( v == NULL )
106     return 0;
107 
108   return (v->interpreter->Width)( v->data );
109 }
110 
111 HYPRE_Int
mv_MultiVectorHeight(mv_MultiVectorPtr v)112 mv_MultiVectorHeight( mv_MultiVectorPtr v ) {
113 
114   if ( v == NULL )
115     return 0;
116 
117   return (v->interpreter->Height)(v->data);
118 }
119 
120 void
mv_MultiVectorClear(mv_MultiVectorPtr v)121 mv_MultiVectorClear( mv_MultiVectorPtr v ) {
122 
123   hypre_assert( v != NULL );
124   (v->interpreter->ClearMultiVector)( v->data );
125 }
126 
127 void
mv_MultiVectorSetRandom(mv_MultiVectorPtr v,HYPRE_Int seed)128 mv_MultiVectorSetRandom( mv_MultiVectorPtr v, HYPRE_Int seed ) {
129 
130   hypre_assert( v != NULL );
131   (v->interpreter->SetRandomVectors)( v->data, seed );
132 }
133 
134 void
mv_MultiVectorCopy(mv_MultiVectorPtr src,mv_MultiVectorPtr dest)135 mv_MultiVectorCopy( mv_MultiVectorPtr src, mv_MultiVectorPtr dest ) {
136 
137   hypre_assert( src != NULL && dest != NULL );
138   (src->interpreter->CopyMultiVector)( src->data, dest->data );
139 }
140 
141 void
mv_MultiVectorAxpy(HYPRE_Complex a,mv_MultiVectorPtr x,mv_MultiVectorPtr y)142 mv_MultiVectorAxpy( HYPRE_Complex a, mv_MultiVectorPtr x, mv_MultiVectorPtr y ) {
143 
144   hypre_assert( x != NULL && y != NULL );
145   (x->interpreter->MultiAxpy)( a, x->data, y->data );
146 }
147 
148 void
mv_MultiVectorByMultiVector(mv_MultiVectorPtr x,mv_MultiVectorPtr y,HYPRE_Int xyGHeight,HYPRE_Int xyHeight,HYPRE_Int xyWidth,HYPRE_Real * xy)149 mv_MultiVectorByMultiVector( mv_MultiVectorPtr x, mv_MultiVectorPtr y,
150 				     HYPRE_Int xyGHeight, HYPRE_Int xyHeight,
151 				     HYPRE_Int xyWidth, HYPRE_Real* xy ) {
152 /* xy = x'*y */
153 
154   hypre_assert( x != NULL && y != NULL );
155   (x->interpreter->MultiInnerProd)
156     ( x->data, y->data, xyGHeight, xyHeight, xyWidth, xy );
157 }
158 
159 void
mv_MultiVectorByMultiVectorDiag(mv_MultiVectorPtr x,mv_MultiVectorPtr y,HYPRE_Int * mask,HYPRE_Int n,HYPRE_Real * d)160 mv_MultiVectorByMultiVectorDiag( mv_MultiVectorPtr x, mv_MultiVectorPtr y,
161 					 HYPRE_Int* mask, HYPRE_Int n, HYPRE_Real* d ) {
162 /* d = diag(x'*y) */
163 
164   hypre_assert( x != NULL && y != NULL );
165   (x->interpreter->MultiInnerProdDiag)( x->data, y->data, mask, n, d );
166 }
167 
168 void
mv_MultiVectorByMatrix(mv_MultiVectorPtr x,HYPRE_Int rGHeight,HYPRE_Int rHeight,HYPRE_Int rWidth,HYPRE_Complex * rVal,mv_MultiVectorPtr y)169 mv_MultiVectorByMatrix( mv_MultiVectorPtr x,
170 			   HYPRE_Int rGHeight, HYPRE_Int rHeight,
171 			   HYPRE_Int rWidth, HYPRE_Complex* rVal,
172 			   mv_MultiVectorPtr y ) {
173 
174   /* y = x*r */
175 
176   hypre_assert( x != NULL && y != NULL );
177   (x->interpreter->MultiVecMat)
178     ( x->data, rGHeight, rHeight, rWidth, rVal, y->data );
179 }
180 
181 void
mv_MultiVectorXapy(mv_MultiVectorPtr x,HYPRE_Int rGHeight,HYPRE_Int rHeight,HYPRE_Int rWidth,HYPRE_Complex * rVal,mv_MultiVectorPtr y)182 mv_MultiVectorXapy( mv_MultiVectorPtr x,
183 		       HYPRE_Int rGHeight, HYPRE_Int rHeight,
184 		       HYPRE_Int rWidth, HYPRE_Complex* rVal,
185 		       mv_MultiVectorPtr y ) {
186 
187   /* y = y + x*a */
188 
189   hypre_assert( x != NULL && y != NULL );
190   (x->interpreter->MultiXapy)
191     ( x->data, rGHeight, rHeight, rWidth, rVal, y->data );
192 }
193 
194 void
mv_MultiVectorByDiagonal(mv_MultiVectorPtr x,HYPRE_Int * mask,HYPRE_Int n,HYPRE_Complex * d,mv_MultiVectorPtr y)195 mv_MultiVectorByDiagonal( mv_MultiVectorPtr x,
196 			     HYPRE_Int* mask, HYPRE_Int n, HYPRE_Complex* d,
197 			     mv_MultiVectorPtr y ) {
198 
199   /* y = x*d */
200 
201   hypre_assert( x != NULL && y != NULL );
202   (x->interpreter->MultiVecMatDiag)( x->data, mask, n, d, y->data );
203 }
204 
205 void
mv_MultiVectorEval(void (* f)(void *,void *,void *),void * par,mv_MultiVectorPtr x,mv_MultiVectorPtr y)206 mv_MultiVectorEval( void (*f)( void*, void*, void* ), void* par,
207 		       mv_MultiVectorPtr x, mv_MultiVectorPtr y ) {
208 
209   /* y = f(x) computed vector-wise */
210 
211   hypre_assert( x != NULL && y != NULL );
212   (x->interpreter->Eval)( f, par, x->data, y->data );
213 }
214 
215 
216