diff --git a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/CMakeLists.txt b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/CMakeLists.txt
index e9f2ac5f984c550ddade2aee5420874700aed676..5b3e95266908469a9dbc158b06b95717764ce0e4 100644
--- a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/CMakeLists.txt
+++ b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/CMakeLists.txt
@@ -23,7 +23,8 @@ atlas_depends_on_subdirs( PUBLIC
                           MuonSpectrometer/MuonDigitContainer
                           MuonSpectrometer/MuonIdHelpers
                           MuonSpectrometer/MuonRDO
-                          MuonSpectrometer/MuonReconstruction/MuonRecEvent/MuonPrepRawData )
+                          MuonSpectrometer/MuonReconstruction/MuonRecEvent/MuonPrepRawData 
+			  MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization )
 
 # External dependencies:
 find_package( tdaq-common COMPONENTS eformat_write DataWriter )
@@ -33,7 +34,7 @@ atlas_add_component( MuonMM_CnvTools
                      src/*.cxx
                      src/components/*.cxx
                      INCLUDE_DIRS ${TDAQ-COMMON_INCLUDE_DIRS}
-                     LINK_LIBRARIES ${TDAQ-COMMON_LIBRARIES} ByteStreamData ByteStreamData_test GaudiKernel AthenaBaseComps SGTools StoreGateLib SGtests AtlasDetDescr Identifier ByteStreamCnvSvcBaseLib MuonContainerManager MuonReadoutGeometry MuonDigitContainer MuonIdHelpersLib MuonRDO MuonPrepRawData )
+                     LINK_LIBRARIES ${TDAQ-COMMON_LIBRARIES} ByteStreamData ByteStreamData_test GaudiKernel AthenaBaseComps SGTools StoreGateLib SGtests AtlasDetDescr Identifier ByteStreamCnvSvcBaseLib MuonContainerManager MuonReadoutGeometry MuonDigitContainer MuonIdHelpersLib MuonRDO MuonPrepRawData MMClusterization )
 
 # Install files from the package:
 atlas_install_headers( MuonMM_CnvTools )
diff --git a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.cxx b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.cxx
index 1342d58a4546f7ebd7d31faf580814cdad5ecf7f..6ad1d56ea08157074f050d211aa56c3876753f06 100644
--- a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.cxx
+++ b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.cxx
@@ -27,6 +27,8 @@
 #include "ByteStreamCnvSvcBase/IROBDataProviderSvc.h"
 #include "MuonCnvToolInterfaces/IMuonRawDataProviderTool.h"
 
+#include "MMClusterization/IMMClusterBuilderTool.h"
+
 using namespace MuonGM;
 using namespace Trk;
 using namespace Muon;
@@ -40,7 +42,8 @@ Muon::MmRdoToPrepDataTool::MmRdoToPrepDataTool(const std::string& t,
   m_mmIdHelper(0),
   m_idHelperTool("Muon::MuonIdHelperTool/MuonIdHelperTool"),
   m_fullEventDone(false),
-  m_mmPrepDataContainer(0) 
+  m_mmPrepDataContainer(0),
+  m_clusterBuilderTool("SimpleMMClusterBuilderTool/SimpleMMClusterBuilderTool",this)
 {
   declareInterface<Muon::IMuonRdoToPrepDataTool>(this);
 
@@ -51,6 +54,7 @@ Muon::MmRdoToPrepDataTool::MmRdoToPrepDataTool(const std::string& t,
 		  "Muon::MMPrepDataContainer to record");
   
   declareProperty("MergePrds", m_merge = true);
+  declareProperty("ClusterBuilderTool",m_clusterBuilderTool);
 }
 
 
@@ -141,7 +145,6 @@ StatusCode Muon::MmRdoToPrepDataTool::processCollection(const MM_RawDataCollecti
   }
 
   std::vector<MMPrepData> MMprds;
-  std::vector<int> MMflag;
   // convert the RDO collection to a PRD collection
   MM_RawDataCollection::const_iterator it = rdoColl->begin();
   for ( ; it != rdoColl->end() ; ++it ) {
@@ -218,114 +221,19 @@ StatusCode Muon::MmRdoToPrepDataTool::processCollection(const MM_RawDataCollecti
       prdColl->push_back(new MMPrepData(prdId,hash,localPos,rdoList,cov,detEl,time,charge));
     } else {
        MMprds.push_back(MMPrepData(prdId,hash,localPos,rdoList,cov,detEl,time,charge));
-       MMflag.push_back(0);
     } 
   }
 
   if(merge) {
-     for (unsigned int i=0; i<MMprds.size(); ++i){
-         // skip the merged prds
-         if(MMflag[i]==1) continue;
- 
-         bool merge = false;
-         unsigned int jmerge = -1;
-         Identifier id_prd = MMprds[i].identify();
-         int strip = m_mmIdHelper->channel(id_prd);
-         int gasGap  = m_mmIdHelper->gasGap(id_prd);
-         int layer   = m_mmIdHelper->multilayer(id_prd);
-         ATH_MSG_VERBOSE("  MMprds " <<  MMprds.size() <<" index "<< i << " strip " << strip << " gasGap " << gasGap << " layer " << layer << " z " << MMprds[i].globalPosition().z() );
-         for (unsigned int j=i+1; j<MMprds.size(); ++j){
-           Identifier id_prdN = MMprds[j].identify();
-           int stripN = m_mmIdHelper->channel(id_prdN);
-           int gasGapN  = m_mmIdHelper->gasGap(id_prdN);
-           int layerN   = m_mmIdHelper->multilayer(id_prdN);
-           if( gasGapN==gasGap && layerN==layer ) {
-             ATH_MSG_VERBOSE(" next MMprds strip same gasGap and layer index " << j << " strip " << stripN << " gasGap " << gasGapN << " layer " << layerN );
-             if(abs(strip-stripN)<2) {
-               merge = true;
-               jmerge = j;
-               break;
-             }
-           }
-         }
- 
-         if(!merge) {
-           ATH_MSG_VERBOSE(" add isolated MMprds strip " << strip << " gasGap " << gasGap << " layer " << layer );
-           std::vector<Identifier> rdoList;
-           rdoList.push_back(id_prd);
-           double covX = MMprds[i].localCovariance()(Trk::locX,Trk::locX);
-           Amg::MatrixX* covN = new Amg::MatrixX(1,1);
-           covN->setIdentity();
-           (*covN)(0,0) = covX;
-           MMPrepData* prdN = new MMPrepData(id_prd, hash, MMprds[i].localPosition(), rdoList, covN, MMprds[i].detectorElement());
-           prdN->setHashAndIndex(prdColl->identifyHash(), prdColl->size());
-           prdColl->push_back(prdN);
-         } else {
-           unsigned int nmerge = 0;
-           std::vector<Identifier> rdoList;
-           std::vector<unsigned int> mergeIndices;
-           std::vector<int> mergeStrips;
-           rdoList.push_back(id_prd);
-           MMflag[i] = 1;
-           mergeIndices.push_back(i);
-           mergeStrips.push_back(strip);
-           unsigned int nmergeStrips = 1;
-           unsigned int nmergeStripsMax = 25;
-           for (unsigned int k=0; k < nmergeStripsMax; ++k) {
-             for (unsigned int j=jmerge; j<MMprds.size(); ++j){
-               if(MMflag[j] == 1) continue;
-               Identifier id_prdN = MMprds[j].identify();
-               int stripN = m_mmIdHelper->channel(id_prdN);
-               if( abs(mergeStrips[k]-stripN) <= 1 ) {
-                 int gasGapN  = m_mmIdHelper->gasGap(id_prdN);
-                 int layerN   = m_mmIdHelper->multilayer(id_prdN);
-                 if( gasGapN==gasGap && layerN==layer ) {
-                   if(mergeStrips[k]==stripN) {
-                     MMflag[j] = 1;
-                     continue;
-                   }
-                   nmerge++;
-                   rdoList.push_back(id_prdN);
-                   MMflag[j] = 1;
-                   mergeIndices.push_back(j);
-                   mergeStrips.push_back(stripN);
-                   nmergeStrips++;
-                 }
-               }
-             }
-             if(k>=nmergeStrips) break;
-           }
-           ATH_MSG_VERBOSE(" add merged MMprds nmerge " << nmerge << " strip " << strip << " gasGap " << gasGap << " layer " << layer );
- 
-           // start off from strip in the middle
-           int stripSum = 0;
-           for (unsigned int k =0; k<mergeStrips.size(); ++k) {
-             stripSum += mergeStrips[k];
-           }
-           stripSum = stripSum/mergeStrips.size();
- 
-           unsigned int j = jmerge;
-           for (unsigned int k =0; k<mergeStrips.size(); ++k) {
-             if(mergeStrips[k]==stripSum) j = mergeIndices[k];
-             ATH_MSG_VERBOSE(" merged strip nr " << k <<  " strip " << mergeStrips[k] << " index " << mergeIndices[k]);
-           }
-           ATH_MSG_VERBOSE(" Look for strip nr " << stripSum << " found at index " << j);
- 
-           double covX = MMprds[j].localCovariance()(Trk::locX, Trk::locX);
-           Amg::MatrixX* covN = new Amg::MatrixX(1,1);
-           covN->setIdentity();
-           (*covN)(0,0) = 6.*(nmerge + 1.)*covX;
-           if(nmerge<=1) (*covN)(0,0) = covX;
-           ATH_MSG_VERBOSE(" make merged prepData at strip " << m_mmIdHelper->channel(MMprds[j].identify()) << " nmerge " << nmerge << " sqrt covX " << sqrt((*covN)(0,0)));
-
-           MMPrepData* prdN = new MMPrepData(MMprds[j].identify(), hash, MMprds[j].localPosition(), rdoList, covN, MMprds[j].detectorElement());
-           prdN->setHashAndIndex(prdColl->identifyHash(), prdColl->size());
-           prdColl->push_back(prdN);
-         }
-       } // end loop MMprds[i]
-     // clear vector and delete elements
-     MMflag.clear();
-     MMprds.clear();
+    std::vector<MMPrepData> clusters;
+
+    m_clusterBuilderTool->getClusters(MMprds,clusters);
+    for (unsigned int i = 0 ; i<clusters.size() ; ++i ) {
+      MMPrepData* prdN = &(clusters.at(i));
+      prdN->setHashAndIndex(prdColl->identifyHash(), prdColl->size());
+      prdColl->push_back(prdN);
+    } 
+
   }
 
 
diff --git a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.h b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.h
index 90a3d5666dac2129734a88298154d9d5a98eafee..b0b1448ae2afa9948cbb3ae943235a2b13bdcb1f 100644
--- a/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.h
+++ b/MuonSpectrometer/MuonCnv/MuonMM_CnvTools/src/MmRdoToPrepDataTool.h
@@ -39,6 +39,7 @@ namespace Muon
 
   class IMuonRawDataProviderTool;
   class MuonIdHelperTool;
+  class IMMClusterBuilderTool;
 
   class MmRdoToPrepDataTool : virtual public IMuonRdoToPrepDataTool, virtual public AthAlgTool
   {
@@ -94,6 +95,9 @@ namespace Muon
 
     std::string m_outputCollectionLocation;            
     bool m_merge; 
+
+    ToolHandle<IMMClusterBuilderTool> m_clusterBuilderTool;
+
   }; 
 } // end of namespace
 
diff --git a/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.cxx b/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.cxx
index 0f09c5ff3cd58df75e7bf4e10dc9a930fcfd9995..5fecfed05fbd9cb54b47038ece3a6dda71687a9e 100644
--- a/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.cxx
+++ b/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.cxx
@@ -3,6 +3,8 @@
 */
 #include "SimpleMMClusterBuilderTool.h"
 #include "MuonPrepRawData/MMPrepData.h"
+#include "MuonReadoutGeometry/MuonDetectorManager.h"
+#include "MuonIdHelpers/MmIdHelper.h"
 
 using namespace Muon;
 
@@ -10,9 +12,11 @@ Muon::SimpleMMClusterBuilderTool::SimpleMMClusterBuilderTool(const std::string&
 							     const std::string& n,
 							     const IInterface*  p )
   :  
-  AthAlgTool(t,n,p)
+  AthAlgTool(t,n,p),
+  m_muonMgr(NULL),
+  m_mmIdHelper(NULL)
 {
-
+  declareInterface<IMMClusterBuilderTool>(this);
 
 }
 
@@ -25,6 +29,25 @@ Muon::SimpleMMClusterBuilderTool::~SimpleMMClusterBuilderTool()
 StatusCode Muon::SimpleMMClusterBuilderTool::initialize()
 {
 
+  ATH_MSG_INFO("AAAAAAAAAAAAAAAAAAAAAAAA in the simplemmclusterbuildertool");
+
+
+  /// get the detector descriptor manager
+  StoreGateSvc* detStore=0;
+  StatusCode sc = serviceLocator()->service("DetectorStore", detStore);
+  if (sc.isSuccess()) {
+    sc = detStore->retrieve( m_muonMgr );
+    if (sc.isFailure()) {
+      ATH_MSG_FATAL(" Cannot retrieve MuonReadoutGeometry ");
+      return sc;
+    }
+  } else {
+    ATH_MSG_ERROR("DetectorStore not found ");
+    return sc;
+  }
+  
+  m_mmIdHelper = m_muonMgr->mmIdHelper();
+  
   return StatusCode::SUCCESS;
 }
 
@@ -35,14 +58,119 @@ StatusCode Muon::SimpleMMClusterBuilderTool::finalize()
   return StatusCode::SUCCESS;
 }
 
-StatusCode Muon::SimpleMMClusterBuilderTool::getClusters(std::vector<Muon::MMPrepData>& stripsVect, 
+StatusCode Muon::SimpleMMClusterBuilderTool::getClusters(std::vector<Muon::MMPrepData>& MMprds, 
 							 std::vector<Muon::MMPrepData>& clustersVect)
 
 {
 
-  ATH_MSG_DEBUG("Size of the input vector: " << stripsVect.size()); 
-  ATH_MSG_DEBUG("Size of the output vector: " << clustersVect.size()); 
+  ATH_MSG_INFO("BBBBBBBBBBBBBBBBB getCLusters in the simplemmclusterbuildertool");
 
 
+  ATH_MSG_DEBUG("Size of the input vector: " << MMprds.size()); 
+  ATH_MSG_DEBUG("Size of the output vector: " << clustersVect.size()); 
+  std::vector<int> MMflag;
+  IdentifierHash hash;
+
+  if ( MMprds.size() > 0 ) {
+    hash = MMprds.at(0).collectionHash();
+  }
+  else {
+    ATH_MSG_DEBUG("Empty PRD collection: no clusterization" );
+    return StatusCode::SUCCESS;
+  }
+
+  for (unsigned int i=0; i<MMprds.size(); ++i){
+    MMflag.push_back(0);
+  }
+
+  for (unsigned int i=0; i<MMprds.size(); ++i){
+    // skip the merged prds
+    if(MMflag[i]==1) continue;
+    
+    unsigned int jmerge = -1;
+    Identifier id_prd = MMprds[i].identify();
+    int strip = m_mmIdHelper->channel(id_prd);
+    int gasGap  = m_mmIdHelper->gasGap(id_prd);
+    int layer   = m_mmIdHelper->multilayer(id_prd);
+    ATH_MSG_VERBOSE("  MMprds " <<  MMprds.size() <<" index "<< i << " strip " << strip << " gasGap " << gasGap << " layer " << layer << " z " << MMprds[i].globalPosition().z() );
+    for (unsigned int j=i+1; j<MMprds.size(); ++j){
+      Identifier id_prdN = MMprds[j].identify();
+      int stripN = m_mmIdHelper->channel(id_prdN);
+      int gasGapN  = m_mmIdHelper->gasGap(id_prdN);
+      int layerN   = m_mmIdHelper->multilayer(id_prdN);
+      if( gasGapN==gasGap && layerN==layer ) {
+	ATH_MSG_VERBOSE(" next MMprds strip same gasGap and layer index " << j << " strip " << stripN << " gasGap " << gasGapN << " layer " << layerN );
+	if(abs(strip-stripN)<2) {
+	  jmerge = j;
+	  break;
+	}
+      }
+    }
+ 
+    unsigned int nmerge = 0;
+    std::vector<Identifier> rdoList;
+    std::vector<unsigned int> mergeIndices;
+    std::vector<int> mergeStrips;
+    rdoList.push_back(id_prd);
+    MMflag[i] = 1;
+    mergeIndices.push_back(i);
+    mergeStrips.push_back(strip);
+    unsigned int nmergeStrips = 1;
+    unsigned int nmergeStripsMax = 25;
+    for (unsigned int k=0; k < nmergeStripsMax; ++k) {
+      for (unsigned int j=jmerge; j<MMprds.size(); ++j){
+	if(MMflag[j] == 1) continue;
+	Identifier id_prdN = MMprds[j].identify();
+	int stripN = m_mmIdHelper->channel(id_prdN);
+	if( abs(mergeStrips[k]-stripN) <= 1 ) {
+	  int gasGapN  = m_mmIdHelper->gasGap(id_prdN);
+	  int layerN   = m_mmIdHelper->multilayer(id_prdN);
+	  if( gasGapN==gasGap && layerN==layer ) {
+	    if(mergeStrips[k]==stripN) {
+	      MMflag[j] = 1;
+	      continue;
+	    }
+	    nmerge++;
+	    rdoList.push_back(id_prdN);
+	    MMflag[j] = 1;
+	    mergeIndices.push_back(j);
+	    mergeStrips.push_back(stripN);
+	    nmergeStrips++;
+	  }
+	}
+      }
+      if(k>=nmergeStrips) break;
+    }
+    ATH_MSG_VERBOSE(" add merged MMprds nmerge " << nmerge << " strip " << strip << " gasGap " << gasGap << " layer " << layer );
+    
+    // start off from strip in the middle
+    int stripSum = 0;
+    for (unsigned int k =0; k<mergeStrips.size(); ++k) {
+      stripSum += mergeStrips[k];
+    }
+    stripSum = stripSum/mergeStrips.size();
+    
+    unsigned int j = jmerge;
+    for (unsigned int k =0; k<mergeStrips.size(); ++k) {
+      if(mergeStrips[k]==stripSum) j = mergeIndices[k];
+      ATH_MSG_VERBOSE(" merged strip nr " << k <<  " strip " << mergeStrips[k] << " index " << mergeIndices[k]);
+    }
+    ATH_MSG_VERBOSE(" Look for strip nr " << stripSum << " found at index " << j);
+    
+    double covX = MMprds[j].localCovariance()(Trk::locX, Trk::locX);
+    Amg::MatrixX* covN = new Amg::MatrixX(1,1);
+    covN->setIdentity();
+    (*covN)(0,0) = 6.*(nmerge + 1.)*covX;
+    if(nmerge<=1) (*covN)(0,0) = covX;
+    ATH_MSG_VERBOSE(" make merged prepData at strip " << m_mmIdHelper->channel(MMprds[j].identify()) << " nmerge " << nmerge << " sqrt covX " << sqrt((*covN)(0,0)));
+    
+    MMPrepData* prdN = new MMPrepData(MMprds[j].identify(), hash, MMprds[j].localPosition(), rdoList, covN, MMprds[j].detectorElement());
+    clustersVect.push_back(*prdN);
+  } // end loop MMprds[i]
+  //clear vector and delete elements
+  MMflag.clear();
+  MMprds.clear();
+ 
+
   return StatusCode::SUCCESS;
 }
diff --git a/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.h b/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.h
index 38176c7e78ca48998a7b14f3afdce0cf7ff12ba8..5e5581e672febd5326e6aca5cc301a7cd2596bea 100644
--- a/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.h
+++ b/MuonSpectrometer/MuonReconstruction/MuonDataPrep/MMClusterization/src/SimpleMMClusterBuilderTool.h
@@ -8,20 +8,25 @@
 #include "MMClusterization/IMMClusterBuilderTool.h"
 #include "MuonPrepRawData/MMPrepData.h"
 #include "AthenaBaseComps/AthAlgTool.h"
+
+class MmIdHelper;
+namespace MuonGM
+{
+  class MuonDetectorManager;
+}
+
 //
 // Simple clusterization tool for MicroMegas
 //
 namespace Muon
 {
   
-  class IMMClusterBuilderTool;
-
   class SimpleMMClusterBuilderTool : virtual public IMMClusterBuilderTool, public AthAlgTool {
 
   public:
     /** Default constructor */
     SimpleMMClusterBuilderTool(const std::string&, const std::string&, const IInterface*);
-    
+     
     /** Default destructor */
     virtual ~SimpleMMClusterBuilderTool();
 
@@ -35,9 +40,11 @@ namespace Muon
 			   std::vector<Muon::MMPrepData>& clustersVect);
 
   private: 
-  
-
 
+    /// Muon Detector Descriptor
+    const MuonGM::MuonDetectorManager* m_muonMgr;
+    const MmIdHelper* m_mmIdHelper;
+    
 };