Index: issm/trunk/src/c/DataSet/Vertices.cpp
===================================================================
--- issm/trunk/src/c/DataSet/Vertices.cpp	(revision 4211)
+++ issm/trunk/src/c/DataSet/Vertices.cpp	(revision 4219)
@@ -42,3 +42,139 @@
 /*}}}*/
 
-/*Object management*/
+/*Numerics management*/
+/*FUNCTION Vertices::CreatePartitioningVector{{{1*/
+void  Vertices::CreatePartitioningVector(Vec* ppartition,int numberofobjects){
+
+	int i;
+
+	/*output: */
+	Vec partition=NULL;
+
+	/*Create partition vector: */
+	partition=NewVec(numberofobjects);
+
+	/*Go through all objects, and ask each object to plug its doflist in 
+	 * partition: */
+
+	for(i=0;i<this->Size();i++){
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->CreatePartition(partition);
+	}
+
+	/*Assemble the petsc vector: */
+	VecAssemblyBegin(partition);
+	VecAssemblyEnd(partition);
+
+	/*Assign output pointers: */
+	*ppartition=partition;
+}
+/*}}}*/
+/*FUNCTION Vertices::DistributeDofs{{{1*/
+void  Vertices::DistributeDofs(int numberofobjects,int numberofdofsperobject){
+
+	extern int num_procs;
+	extern int my_rank;
+
+	int  i;
+	
+	int  dofcount=0;
+	int* alldofcount=NULL;
+	int* truedofs=NULL;
+	int* alltruedofs=NULL;
+
+	/*Go through objects, and distribute dofs locally, from 0 to numberofdofsperobject: */
+	for (i=0;i<this->Size();i++){
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->DistributeDofs(&dofcount);
+	}
+
+	/*Ok, now every object has distributed dofs, but locally, and with a dof count starting from 
+	 *0. This means the dofs between all the cpus are not synchronized! We need to synchronize all 
+	 *dof on all cpus, and use those to update the dofs of every object: */
+
+	alldofcount=(int*)xmalloc(num_procs*sizeof(int));
+	MPI_Gather(&dofcount,1,MPI_INT,alldofcount,1,MPI_INT,0,MPI_COMM_WORLD);
+	MPI_Bcast(alldofcount,num_procs,MPI_INT,0,MPI_COMM_WORLD);
+
+	/*Ok, now every cpu should start its own dof count at the end of the dofcount 
+	 * from cpu-1. : */
+	dofcount=0;
+	if(my_rank==0){
+		dofcount=0;
+	}
+	else{
+		for(i=0;i<my_rank;i++){
+			dofcount+=alldofcount[i];
+		}
+	}
+
+
+	/*Ok, now every cpu knows where his dofs should start. Update the dof count: */
+	for (i=0;i<this->Size();i++){
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->OffsetDofs(dofcount);
+	}
+
+	/*Finally, remember that cpus may have skipped some objects, because they were clones. For every 
+	 * object that is not a clone, tell them to show their dofs, so that later on, they can get picked 
+	 * up by their clones: */
+	truedofs=(int*)xcalloc(numberofobjects*numberofdofsperobject,sizeof(int));
+	alltruedofs=(int*)xcalloc(numberofobjects*numberofdofsperobject,sizeof(int));
+
+	for (i=0;i<this->Size();i++){
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->ShowTrueDofs(truedofs);
+	}
+	
+	MPI_Allreduce ( (void*)truedofs,(void*)alltruedofs,numberofobjects*numberofdofsperobject,MPI_INT,MPI_MAX,MPI_COMM_WORLD);
+
+	/*Ok, now every cpu knows the true dofs of everyone else that is not a clone. Let the clones recover those true dofs: */
+	for (i=0;i<this->Size();i++){
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->UpdateCloneDofs(alltruedofs);
+	}
+
+	/* Free ressources: */
+	xfree((void**)&alldofcount);
+	xfree((void**)&truedofs);
+	xfree((void**)&alltruedofs);
+
+}
+/*}}}*/
+/*FUNCTION Vertices::FlagClones{{{1*/
+void  Vertices::FlagClones(int numberofobjects){
+
+	int i;
+	extern int num_procs;
+
+	int* ranks=NULL;
+	int* minranks=NULL;
+
+	/*Allocate ranks: */
+	ranks=(int*)xmalloc(numberofobjects*sizeof(int));
+	minranks=(int*)xmalloc(numberofobjects*sizeof(int));
+
+	for(i=0;i<numberofobjects;i++)ranks[i]=num_procs; //no cpu can have rank num_procs. This is the maximum limit.
+
+	/*Now go through all our objects and ask them to report to who they belong (which rank): */
+	Ranks(ranks);
+
+	/*We need to take the minimum rank for each vertex, and every cpu needs to get that result. That way, 
+	 * when we start building the dof list for all vertexs, a cpu can check whether its vertex already has been 
+	 * dealt with by another cpu. We take the minimum because we are going to manage dof assignment in increasing 
+	 * order of cpu rank. This is also why we initialized this array to num_procs.*/
+	MPI_Allreduce ( (void*)ranks,(void*)minranks,numberofobjects,MPI_INT,MPI_MIN,MPI_COMM_WORLD);
+
+	/*Now go through all objects, and use minranks to flag which objects are cloned: */
+	for(i=0;i<this->Size();i++){
+		/*For this object, decide whether it is a clone: */
+		Vertex* vertex=(Vertex*)this->GetObjectByOffset(i);
+		vertex->SetClone(minranks);
+	}
+
+	/*Free ressources: */
+	xfree((void**)&ranks); 
+	xfree((void**)&minranks);
+
+}
+/*}}}*/
