/*!\file:  Matrix.h
 * \brief wrapper to matrix objects. The goal is to control which API (PETSc,Scalpack, Plapack?) 
 * implements our underlying matrix format.
 */ 

#ifndef _MATRIX_H_
#define _MATRIX_H_

/*Headers:*/
/*{{{1*/
#ifdef HAVE_CONFIG_H
	#include <config.h>
#else
#error "Cannot compile with HAVE_CONFIG_H symbol! run configure first!"
#endif
#include "../../toolkits/toolkits.h"
#include "../../EnumDefinitions/EnumDefinitions.h"

#ifdef _HAVE_ADOLC_
#include "adolc.h"
#endif

class Vector;

/*}}}*/

class Matrix{

	public:
	
		#ifdef _HAVE_PETSC_
		Mat matrix; 
		#else
		SeqMat* matrix; 
		#endif
		#ifdef _HAVE_ADOLC_
		adouble* amatrix;
		#endif

		/*Matrix constructors, destructors {{{1*/
		Matrix();
		Matrix(int M,int N);
		Matrix(int M,int N,double sparsity);
		Matrix(double* serial_mat,int M,int N,double sparsity);
		Matrix(int M,int N,int connectivity,int numberofdofspernode);
		~Matrix();
		/*}}}*/
		/*Matrix specific routines {{{1*/
		void Echo(void);
		void Assemble(void);
		double Norm(NormMode norm_type);
		void GetSize(int* pM,int* pN);
		void GetLocalSize(int* pM,int* pN);
		void MatMult(Vector* X,Vector* AX);
		Matrix* Duplicate(void);
		double* ToSerial(void);
		void SetValues(int m,int* idxm,int n,int* idxn,double* values,InsMode mode);
		void Convert(MatrixType type);
		/*}}}*/

};

#endif //#ifndef _MATRIX_H_
