Actual source code: evector.c
4: /*
5: Makes a PETSc vector look like a ESI
6: */
8: #include esi/petsc/vector.h
10: esi::petsc::Vector<double,int>::Vector( ::esi::IndexSpace<int> *inmap)
11: {
12: ::esi::ErrorCode ierr;
13: int n,N;
14: MPI_Comm *icomm;
16: inmap->getRunTimeModel("MPI",reinterpret_cast<void *&>(icomm));if (ierr) return;
18: inmap->getLocalSize(n);if (ierr) return;
19: inmap->getGlobalSize(N);if (ierr) return;
20: VecCreate(*icomm,&this->vec);if (ierr) return;
21: VecSetSizes(this->vec,n,N);if (ierr) return;
22: PetscObjectSetOptionsPrefix((PetscObject)this->vec,"esi");if (ierr) return;
23: VecSetFromOptions(this->vec);if (ierr) return;
24: this->pobject = (PetscObject)this->vec;
25: this->map = (::esi::IndexSpace<int> *)inmap;
26: this->map->addReference();
27: PetscObjectGetComm((PetscObject)this->vec,&this->comm);if (ierr) return;
28: }
30: esi::petsc::Vector<double,int>::Vector( Vec pvec)
31: {
32: ::esi::ErrorCode ierr;
33: int n,N;
34:
35: this->vec = pvec;
36: this->pobject = (PetscObject)this->vec;
37: PetscObjectReference((PetscObject)pvec);if (ierr) return;
38: PetscObjectGetComm((PetscObject)this->vec,&this->comm);if (ierr) return;
40: VecGetSize(pvec,&N);if (ierr) return;
41: VecGetLocalSize(pvec,&n);if (ierr) return;
42: this->map = new esi::petsc::IndexSpace<int>(this->comm,n,N);
43: }
45: esi::petsc::Vector<double,int>::~Vector()
46: {
48: this->map->deleteReference();if (ierr) return;
49: VecDestroy(this->vec);if (ierr) return;
50: }
52: /* ---------------esi::Object methods ------------------------------------------------------------ */
54: ::esi::ErrorCode esi::petsc::Vector<double,int>::getInterface(const char* name, void *& iface)
55: {
56: PetscTruth flg;
57: if (PetscStrcmp(name,"esi::Object",&flg),flg){
58: iface = (void *) (::esi::Object *) this;
59: } else if (PetscStrcmp(name,"esi::Vector",&flg),flg){
60: iface = (void *) (::esi::Vector<double,int> *) this;
61: } else if (PetscStrcmp(name,"esi::petsc::Vector",&flg),flg){
62: iface = (void *) (::esi::petsc::Vector<double,int> *) this;
63: } else if (PetscStrcmp(name,"esi::VectorReplaceAccess",&flg),flg){
64: iface = (void *) (::esi::VectorReplaceAccess<double,int> *) this;
65: } else if (PetscStrcmp(name,"Vec",&flg),flg){
66: iface = (void *) this->vec;
67: } else {
68: iface = 0;
69: }
70: return 0;
71: }
74: ::esi::ErrorCode esi::petsc::Vector<double,int>::getInterfacesSupported(::esi::Argv * list)
75: {
76: list->appendArg("esi::Object");
77: list->appendArg("esi::Vector");
78: list->appendArg("esi::VectorReplaceAccess");
79: list->appendArg("esi::petsc::Vector");
80: list->appendArg("Vec");
81: return 0;
82: }
84: /*
85: Note: this returns the map used in creating the vector;
86: it is not the same as the PETSc map contained inside the PETSc vector
87: */
88: ::esi::ErrorCode esi::petsc::Vector<double,int>::getIndexSpace( ::esi::IndexSpace<int>*& outmap)
89: {
90: outmap = this->map;
91: return 0;
92: }
94: ::esi::ErrorCode esi::petsc::Vector<double,int>::getGlobalSize( int & dim)
95: {
96: return VecGetSize(this->vec,&dim);
97: }
99: ::esi::ErrorCode esi::petsc::Vector<double,int>::getLocalSize( int & dim)
100: {
101: return VecGetLocalSize(this->vec,&dim);
102: }
104: ::esi::ErrorCode esi::petsc::Vector<double,int>::clone( ::esi::Vector<double,int>*& outvector)
105: {
106: int ierr;
107: ::esi::IndexSpace<int> *lmap;
108: ::esi::IndexSpace<int> *amap;
110: this->getIndexSpace(lmap);
111: lmap->getInterface("esi::IndexSpace",reinterpret_cast<void *&>(amap));
112: outvector = (::esi::Vector<double,int> *) new esi::petsc::Vector<double,int>(amap);
113: return 0;
114: }
116: /*
117: Currently only works if both vectors are PETSc
118: */
119: ::esi::ErrorCode esi::petsc::Vector<double,int>::copy( ::esi::Vector<double,int> &yy)
120: {
121: esi::petsc::Vector<double,int> *y = 0;
122: int ierr;
124: yy.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
125: if (!y) return 1;
127: return VecCopy(y->vec,this->vec);
128: }
130: ::esi::ErrorCode esi::petsc::Vector<double,int>::put( double scalar)
131: {
132: return VecSet(&scalar,this->vec);
133: }
135: ::esi::ErrorCode esi::petsc::Vector<double,int>::scale( double scalar)
136: {
137: return VecScale(&scalar,this->vec);
138: }
140: /*
141: Currently only works if both vectors are PETSc
142: */
143: ::esi::ErrorCode esi::petsc::Vector<double,int>::scaleDiagonal( ::esi::Vector<double,int> &yy)
144: {
145: ::esi::ErrorCode ierr;
146: esi::petsc::Vector<double,int> *y;
147:
148: yy.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
149: if (!y) return 1;
151: return VecPointwiseMult(y->vec,this->vec,this->vec);
152: }
154: ::esi::ErrorCode esi::petsc::Vector<double,int>::norm1(double &scalar)
155: {
156: return VecNorm(this->vec,NORM_1,&scalar);
157: }
159: ::esi::ErrorCode esi::petsc::Vector<double,int>::norm2(double &scalar)
160: {
161: return VecNorm(this->vec,NORM_2,&scalar);
162: }
164: ::esi::ErrorCode esi::petsc::Vector<double,int>::norm2squared(double &scalar)
165: {
166: int VecNorm(this->vec,NORM_2,&scalar);
167: scalar *= scalar;
168: return 0;
169: }
171: ::esi::ErrorCode esi::petsc::Vector<double,int>::normInfinity(double &scalar)
172: {
173: return VecNorm(this->vec,NORM_INFINITY,&scalar);
174: }
176: /*
177: Currently only works if both vectors are PETSc
178: */
179: ::esi::ErrorCode esi::petsc::Vector<double,int>::dot( ::esi::Vector<double,int> &yy,double &product)
180: {
183: esi::petsc::Vector<double,int> *y; yy.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
184: if (!y) return 1;
185: return VecDot(this->vec,y->vec,&product);
186: }
188: /*
189: Currently only works if both vectors are PETSc
190: */
191: ::esi::ErrorCode esi::petsc::Vector<double,int>::axpy( ::esi::Vector<double,int> &yy,double scalar)
192: {
195: esi::petsc::Vector<double,int> *y; yy.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
196: if (!y) return 1;
197: return VecAXPY(&scalar,y->vec,this->vec);
198: }
200: ::esi::ErrorCode esi::petsc::Vector<double,int>::axpby(double dy1, ::esi::Vector<double,int> &yy1,double y2, ::esi::Vector<double,int> &yy2)
201: {
204: esi::petsc::Vector<double,int> *y; yy1.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
205: if (!y) return 1;
206: esi::petsc::Vector<double,int> *w; yy2.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(w));
207: if (!w) return 1;
208: VecCopy(y->vec,this->vec);
209: VecScale(&dy1,this->vec);
210: VecAXPY(&y2,w->vec,this->vec);
211: return(0);
212: }
214: /*
215: Currently only works if both vectors are PETSc
216: */
217: ::esi::ErrorCode esi::petsc::Vector<double,int>::aypx(double scalar, ::esi::Vector<double,int> &yy)
218: {
220:
221: esi::petsc::Vector<double,int> *y; yy.getInterface("esi::petsc::Vector",reinterpret_cast<void *&>(y));
222: if (!y) return 1;
223: return VecAYPX(&scalar,y->vec,this->vec);
224: }
226: ::esi::ErrorCode esi::petsc::Vector<double,int>::getCoefPtrReadLock(double *&pointer)
227: {
228: return VecGetArray(this->vec,&pointer);
229: }
231: ::esi::ErrorCode esi::petsc::Vector<double,int>::getCoefPtrReadWriteLock(double *&pointer)
232: {
233: return VecGetArray(this->vec,&pointer);
234: }
236: ::esi::ErrorCode esi::petsc::Vector<double,int>::releaseCoefPtrLock(double *&pointer)
237: {
238: return VecRestoreArray(this->vec,&pointer);
239: }
241: ::esi::ErrorCode esi::petsc::Vector<double,int>::setArrayPointer(double *pointer,int length)
242: {
243: return VecPlaceArray(this->vec,pointer);
244: }
246: // --------------------------------------------------------------------------------------------------------
247: namespace esi{namespace petsc{
248: template<class Scalar,class Ordinal> class VectorFactory : public virtual ::esi::VectorFactory<Scalar,Ordinal>
249: {
250: public:
252: // constructor
253: VectorFactory(void){};
254:
255: // Destructor.
256: virtual ~VectorFactory(void){};
258: // Interface for gov::cca::Component
259: #if defined(PETSC_HAVE_CCA)
260: virtual void setServices(gov::cca::Services *svc)
261: {
262: svc->addProvidesPort(this,svc->createPortInfo("getVector", "esi::VectorFactory", 0));
263: };
264: #endif
266: // Construct a Vector
267: virtual ::esi::ErrorCode getVector(::esi::IndexSpace<Ordinal>&map,::esi::Vector<Scalar,Ordinal>*&v)
268: {
269: v = new esi::petsc::Vector<Scalar,Ordinal>(&map);
270: return 0;
271: };
272: };
273: }}
275: ::esi::petsc::VectorFactory<double,int> VFInstForIntel64CompilerBug;
277: EXTERN_C_BEGIN
278: #if defined(PETSC_HAVE_CCA)
279: gov::cca::Component *create_esi_petsc_vectorfactory(void)
280: {
281: return dynamic_cast<gov::cca::Component *>(new esi::petsc::VectorFactory<double,int>);
282: }
283: #else
284: ::esi::VectorFactory<double,int> *create_esi_petsc_vectorfactory(void)
285: {
286: return dynamic_cast< ::esi::VectorFactory<double,int> *>(new esi::petsc::VectorFactory<double,int>);
287: }
288: #endif
289: EXTERN_C_END
291: // --------------------------------------------------------------------------------------------------------
292: #if defined(PETSC_HAVE_TRILINOS)
293: #define PETRA_MPI /* used by Ptera to indicate MPI code */
294: #include "Petra_ESI_Vector.h"
296: template<class Scalar,class Ordinal> class Petra_ESI_VectorFactory : public virtual ::esi::VectorFactory<Scalar,Ordinal>
297: {
298: public:
300: // constructor
301: Petra_ESI_VectorFactory(void) {};
302:
303: // Destructor.
304: virtual ~Petra_ESI_VectorFactory(void) {};
306: // Interface for gov::cca::Component
307: #if defined(PETSC_HAVE_CCA)
308: virtual void setServices(gov::cca::Services *svc)
309: {
310: svc->addProvidesPort(this,svc->createPortInfo("getVector", "esi::VectorFactory", 0));
311: };
312: #endif
314: // Construct a Vector
315: virtual ::esi::ErrorCode getVector(::esi::IndexSpace<Ordinal>&lmap,::esi::Vector<Scalar,Ordinal>*&v)
316: {
317: Petra_ESI_IndexSpace<Ordinal> *map;
318: int lmap.getInterface("Petra_ESI_IndexSpace",reinterpret_cast<void *&>(map));
319: if (!map) SETERRQ(1,"Requires Petra_ESI_IndexSpace");
320: v = new Petra_ESI_Vector<Scalar,Ordinal>(*map);
321: // map->addReference(); /* Petra has bug and does not increase reference count */
322: if (!v) SETERRQ(1,"Unable to create new Petra_ESI_Vector");
323: return 0;
324: };
325: };
327: EXTERN_C_BEGIN
328: #if defined(PETSC_HAVE_CCA)
329: gov::cca::Component *create_petra_esi_vectorfactory(void)
330: {
331: return dynamic_cast<gov::cca::Component *>(new Petra_ESI_VectorFactory<double,int>);
332: }
333: #else
334: ::esi::VectorFactory<double,int> *create_petra_esi_vectorfactory(void)
335: {
336: return dynamic_cast< ::esi::VectorFactory<double,int> *>(new Petra_ESI_VectorFactory<double,int>);
337: }
338: #endif
339: EXTERN_C_END
340: #endif
342: // --------------------------------------------------------------------------------------------------------
344: // CCAFFEINE expects each .so file to have a getComponentList function.
345: // See dccafe/cxx/dc/framework/ComponentFactory.h for details.
346: EXTERN_C_BEGIN
347: char **getComponentList() {
348: static char *list[7];
349: list[0] = "create_esi_petsc_vectorfactory esi::petsc::Vector";
350: list[1] = "create_petra_esi_vectorfactory Petra_ESI_Vector";
351: list[2] = "create_esi_petsc_indexspacefactory esi::petsc::IndexSpace";
352: list[3] = "create_petra_esi_indexspacefactory Petra_ESI_IndexSpace";
353: list[4] = "create_esi_petsc_operatorfactory esi::petsc::Operator";
354: list[5] = "create_petra_esi_operatorfactory Petra_ESI_CRS_Matrix";
355: list[6] = 0;
356: return list;
357: }
358: EXTERN_C_END