Commit 296f8b6c authored by berenger-bramas's avatar berenger-bramas

Had clean the Blas version

+
The blas fonction (only one yet) used is in a global file
+
A simple test to compare Targets and Sources model (Tsm)
and no-Tsm has been added to the Tests directory.
It simply checks that all cells have the same values (and it's right)
But it does not test the L2P and P2P.

git-svn-id: svn+ssh://scm.gforge.inria.fr/svn/scalfmm/scalfmm/trunk@42 2616d619-271b-44dc-8df4-d4a8f33a7222
parent 62a881df
This diff is collapsed.
......@@ -17,10 +17,11 @@
* It is needed by the Fmb Kernels.
*/
class FExtendFmbCell {
protected:
public:
// FMB_Info_P is declared in FAbstractFmbKernels
static const int MultipoleSize = int(((FMB_Info_P)+1) * ((FMB_Info_P)+2) * 0.5); //< The size of the multipole
protected:
FComplexe multipole_exp[MultipoleSize]; //< For multipole extenssion
FComplexe local_exp[MultipoleSize]; //< For local extenssion
......
......@@ -3,6 +3,7 @@
// /!\ Please, you must read the license at the bottom of this page
#include "../Utils/FGlobal.hpp"
#include "../Utils/FBlas.hpp"
#include "../Components/FAbstractKernels.hpp"
#include "../Containers/FTreeCoordinate.hpp"
......@@ -14,36 +15,6 @@
#include "../Utils/FTrace.hpp"
#include <iostream>
#include <cblas.h>
template <typename T>
void cblas_gemv(const enum CBLAS_ORDER order ,
const enum CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
T t;
t.you_cannot_use_this_function_with_this_type();
}
template <>
void cblas_gemv<double>(const enum CBLAS_ORDER order ,
const enum CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
cblas_zgemv(order,TransA,M,N,alpha,A,lda,X,incX,beta,Y,incY);
}
template <>
void cblas_gemv<float>(const enum CBLAS_ORDER order ,
const enum CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
cblas_cgemv(order,TransA,M,N,alpha,A,lda,X,incX,beta,Y,incY);
}
/**
......@@ -321,11 +292,12 @@ protected:
cosSin[idxl].setReal( FMath::Sin(angle + FMath::FPiDiv2) );
cosSin[idxl].setImag( FMath::Sin(angle) );
//printf("%d=%.15e/%.15e (angle %.15e=%d * %.15e + %.15e // (%.15e))\n",idxl,cosSin[idxl].getReal(),cosSin[idxl].getImag(),
// angle,idxl,inSphere.phi,this->PiArrayInner[idxlMod4],angleinter);
/*printf("%d=%.15e/%.15e (angle %.15e=%d * %.15e + %.15e // (%.15e))\n",
idxl,cosSin[idxl].getReal(),cosSin[idxl].getImag(),
angle,idxl,inSphere.phi,this->PiArrayInner[idxlMod4],angleinter);*/
//printf("sin(%.15e) = %.15e\n",
// angle + FMath::FPiDiv2,FMath::Sin(angle + FMath::FPiDiv2));
/*printf("sin(%.15e) = %.15e\n",
angle + FMath::FPiDiv2,FMath::Sin(angle + FMath::FPiDiv2));*/
}
// p_associated_Legendre_function_Array
......
#ifndef FBLAS_HPP
#define FBLAS_HPP
#include <cblas.h>
//#include <mkl.h>
///////////////////////////////////////////////////////
// GEMV
///////////////////////////////////////////////////////
template <typename T>
void cblas_gemv(const CBLAS_ORDER order ,
const CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
T t;
t.you_cannot_use_this_function_with_this_type();
}
template <>
void cblas_gemv<double>(const CBLAS_ORDER order ,
const CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
cblas_zgemv(order,TransA,M,N,alpha,A,lda,X,incX,beta,Y,incY);
}
template <>
void cblas_gemv<float>(const CBLAS_ORDER order ,
const CBLAS_TRANSPOSE TransA , const int M , const int N ,
const void *alpha , const void *A , const int lda ,
const void *X , const int incX , const void *beta ,
void *Y , const int incY){
cblas_cgemv(order,TransA,M,N,alpha,A,lda,X,incX,beta,Y,incY);
}
#endif //FBLAS_HPP
......@@ -10,6 +10,9 @@
* Please read the license
*
* Propose basic complexe class.
* Do not modify the attributes of this class.
* It can be passed to blas fonction and has to be
* 2 x real size only.
*/
class FComplexe {
FReal real; //< Real
......
......@@ -12,6 +12,7 @@ endif()
#add blass
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -lcblas")
#ADD_DEFINITIONS(-Wl,--start-group $(MKLROOT)/lib/ia32/libmkl_intel.a $(MKLROOT)/lib/ia32/libmkl_sequential.a $(MKLROOT)/lib/ia32/libmkl_core.a -Wl,--end-group -lpthread)
#test
# ADD_DEFINITIONS(-fexpensive-optimizations -funroll-loops -frerun-cse-after-loop -frerun-loop-opt)
......
......@@ -29,9 +29,10 @@
#include "../Sources/Files/FFMALoader.hpp"
// With openmp : g++ testFmbBlasAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp ../Sources/Utils/FTrace.cpp -lgomp -fopenmp -lblas -O2 -o testFmbBlasAlgorithm.exe
// With openmp : g++ testFmbBlasAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp ../Sources/Utils/FTrace.cpp -lgomp -fopenmp -lcblas -O2 -o testFmbBlasAlgorithm.exe
// icpc -openmp -openmp-lib=compat testFmbAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp -O2 -o testFmbAlgorithm.exe
// g++ testFmbBlasAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp ../Sources/Utils/FTrace.cpp -lgomp -fopenmp -lmkl_ia32 -O2 -o testFmbBlasAlgorithm.exe
/** This program show an example of use of
* the fmm basic algo
* it also check that eachh particules is little or longer
......@@ -116,9 +117,9 @@ int main(int argc, char ** argv){
counter.tic();
//FFmbKernelsBlas FFmbKernelsPotentialForces
FFmbKernelsPotentialForces<FmbParticule, FmbCell, NbLevels> kernels(loader.getBoxWidth());
FFmbKernelsBlas<FmbParticule, FmbCell, NbLevels> kernels(loader.getBoxWidth());
//FFMMAlgorithm FFMMAlgorithmThreaded FFMMAlgorithmArray FFMMAlgorithmTask
FFmmAlgorithm<FFmbKernelsPotentialForces, FmbParticule, FmbCell, FSimpleLeaf, NbLevels, SizeSubLevels> algo(&tree,&kernels);
FFmmAlgorithm<FFmbKernelsBlas, FmbParticule, FmbCell, FSimpleLeaf, NbLevels, SizeSubLevels> algo(&tree,&kernels);
algo.execute();
counter.tac();
......
// /!\ Please, you must read the license at the bottom of this page
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include "../Sources/Utils/FTic.hpp"
#include "../Sources/Containers/FOctree.hpp"
#include "../Sources/Containers/FList.hpp"
#include "../Sources/Components/FFmaParticule.hpp"
#include "../Sources/Extenssions/FExtendForces.hpp"
#include "../Sources/Extenssions/FExtendPotential.hpp"
#include "../Sources/Extenssions/FExtendParticuleType.hpp"
#include "../Sources/Extenssions/FExtendCellType.hpp"
#include "../Sources/Components/FBasicCell.hpp"
#include "../Sources/Fmb/FExtendFmbCell.hpp"
#include "../Sources/Core/FFmmAlgorithm.hpp"
#include "../Sources/Core/FFmmAlgorithmTsm.hpp"
#include "../Sources/Core/FFmmAlgorithmArray.hpp"
#include "../Sources/Core/FFmmAlgorithmArrayTsm.hpp"
#include "../Sources/Components/FSimpleLeaf.hpp"
#include "../Sources/Components/FTypedLeaf.hpp"
#include "../Sources/Fmb/FFmbKernelsPotentialForces.hpp"
#include "../Sources/Fmb/FFmbKernelsForces.hpp"
#include "../Sources/Fmb/FFmbKernelsPotential.hpp"
// With openmp : g++ testFmbTsmAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp ../Sources/Utils/FTrace.cpp -lgomp -fopenmp -O2 -o testFmbTsmAlgorithm.exe
// icpc -openmp -openmp-lib=compat testFmbTsmAlgorithm.cpp ../Sources/Utils/FAssertable.cpp ../Sources/Utils/FDebug.cpp -O2 -o testFmbTsmAlgorithm.exe
/** This program show an example of use of
* the fmm basic algo
* it also check that eachh particules is little or longer
* related that each other
*/
/** Fmb class has to extend {FExtendForces,FExtendPotential,FExtendPhysicalValue}
* Because we use fma loader it needs {FFmaParticule}
*/
class FmbParticule : public FFmaParticule, public FExtendForces, public FExtendPotential {
public:
};
class FmbParticuleTyped : public FmbParticule, public FExtendParticuleType {
public:
};
/** Custom cell
*
*/
class FmbCell : public FBasicCell, public FExtendFmbCell {
public:
};
class FmbCellTyped : public FmbCell, public FExtendCellType {
public:
};
// Simply create particules and try the kernels
int main(int argc, char ** argv){
///////////////////////What we do/////////////////////////////
std::cout << ">> This executable has to be used to test Fmb on a Tsm system.\n";
std::cout << ">> It compares the results between Tms and no Tms (except P2P & L2P).\n";
//////////////////////////////////////////////////////////////
const int NbLevels = 9;//10;
const int SizeSubLevels = 3;//3
FTic counter;
const long NbPart = 200000;//2000000
const double BoxWidth = 1.0;
const F3DPosition CenterOfBox(0.5,0.5,0.5);
// -----------------------------------------------------
std::cout << "Creating " << NbPart << " particules ..." << std::endl;
counter.tic();
FmbParticule* particules = new FmbParticule[NbPart];
FmbParticuleTyped* particulesTyped = new FmbParticuleTyped[NbPart*2];
for(int idxPart = 0 ; idxPart < NbPart ; ++idxPart){
const double x = FReal(rand())/RAND_MAX;
const double y = FReal(rand())/RAND_MAX;
const double z = FReal(rand())/RAND_MAX;
// Particule for standart model
particules[idxPart].setPosition(x,y,z);
particules[idxPart].setPhysicalValue(1);
// Create a clone for typed (Tsm) version
particulesTyped[idxPart*2].setPosition(x,y,z);
particulesTyped[idxPart*2+1].setPosition(x,y,z);
particulesTyped[idxPart*2].setPhysicalValue(1);
particulesTyped[idxPart*2+1].setPhysicalValue(1);
particulesTyped[idxPart*2].setAsSource();
particulesTyped[idxPart*2+1].setAsTarget();
}
counter.tac();
std::cout << "Done " << "(" << counter.elapsed() << "s)." << std::endl;
// -----------------------------------------------------
FOctree<FmbParticule, FmbCell, FSimpleLeaf, NbLevels, SizeSubLevels> tree(BoxWidth,CenterOfBox);
FOctree<FmbParticuleTyped, FmbCellTyped, FTypedLeaf, NbLevels, SizeSubLevels> treeTyped(BoxWidth,CenterOfBox);
std::cout << "Inserting particules ..." << std::endl;
counter.tic();
for(long idxPart = 0 ; idxPart < NbPart ; ++idxPart){
tree.insert(&particules[idxPart]);
treeTyped.insert(&particulesTyped[idxPart*2]);
treeTyped.insert(&particulesTyped[idxPart*2+1]);
}
counter.tac();
std::cout << "Done " << "(" << counter.elapsed() << "s)." << std::endl;
// -----------------------------------------------------
std::cout << "Working on particules ..." << std::endl;
counter.tic();
//FFmbKernelsPotentialForces FFmbKernelsForces FFmbKernelsPotential
FFmbKernelsPotentialForces<FmbParticule, FmbCell, NbLevels> kernels(BoxWidth);
FFmbKernelsPotentialForces<FmbParticuleTyped, FmbCellTyped, NbLevels> kernelsTyped(BoxWidth);
//FFmmAlgorithm FFmmAlgorithmArray
FFmmAlgorithmArray<FFmbKernelsPotentialForces, FmbParticule, FmbCell, FSimpleLeaf, NbLevels, SizeSubLevels> algo(&tree,&kernels);
FFmmAlgorithmArrayTsm<FFmbKernelsPotentialForces, FmbParticuleTyped, FmbCellTyped, FTypedLeaf, NbLevels, SizeSubLevels> algoTyped(&treeTyped,&kernelsTyped);
algo.execute();
algoTyped.execute();
counter.tac();
std::cout << "Done " << "(" << counter.elapsed() << "s)." << std::endl;
// -----------------------------------------------------
// Here we compare the cells of the trees that must contains the same values
std::cout << "Start checking ..." << std::endl;
{
FOctree<FmbParticule, FmbCell, FSimpleLeaf, NbLevels, SizeSubLevels>::Iterator octreeIterator(&tree);
octreeIterator.gotoBottomLeft();
FOctree<FmbParticuleTyped, FmbCellTyped, FTypedLeaf, NbLevels, SizeSubLevels>::Iterator octreeIteratorTyped(&treeTyped);
octreeIteratorTyped.gotoBottomLeft();
for(int idxLevel = NbLevels - 1 ; idxLevel > 1 ; --idxLevel ){
std::cout << "\t test level " << idxLevel << "\n";
do{
bool poleDiff = false;
bool localDiff = false;
for(int idxValues = 0 ; idxValues < FExtendFmbCell::MultipoleSize && !(poleDiff && localDiff); ++idxValues){
const FComplexe pole = octreeIterator.getCurrentCell()->getMultipole()[idxValues];
const FComplexe poleTyped = octreeIteratorTyped.getCurrentCell()->getMultipole()[idxValues];
if(!FMath::LookEqual(pole.getImag(),poleTyped.getImag()) || !FMath::LookEqual(pole.getReal(),poleTyped.getReal())){
poleDiff = true;
printf("Pole diff imag( %.15e , %.15e ) real( %.15e , %.15e)\n",
pole.getImag(),poleTyped.getImag(),pole.getReal(),poleTyped.getReal());
}
const FComplexe local = octreeIterator.getCurrentCell()->getLocal()[idxValues];
const FComplexe localTyped = octreeIteratorTyped.getCurrentCell()->getLocal()[idxValues];
if(!FMath::LookEqual(local.getImag(),localTyped.getImag()) || !FMath::LookEqual(local.getReal(),localTyped.getReal())){
localDiff = true;
printf("Pole diff imag( %.15e , %.15e ) real( %.15e , %.15e)\n",
local.getImag(),localTyped.getImag(),local.getReal(),localTyped.getReal());
}
}
if(poleDiff){
std::cout << "Multipole error at level " << idxLevel << "\n";
}
if(localDiff){
std::cout << "Locale error at level " << idxLevel << "\n";
}
} while(octreeIterator.moveRight() && octreeIteratorTyped.moveRight());
octreeIterator.moveUp();
octreeIterator.gotoLeft();
octreeIteratorTyped.moveUp();
octreeIteratorTyped.gotoLeft();
}
}
std::cout << "Done ..." << std::endl;
delete [] particules;
delete [] particulesTyped;
return 0;
}
// [--LICENSE--]
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment