Index: /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.cpp
===================================================================
--- /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.cpp	(revision 2548)
+++ /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.cpp	(revision 2549)
@@ -2,4 +2,11 @@
  * \brief  "c" core code for interpolating values from a structured grid.
  */ 
+
+#ifdef HAVE_CONFIG_H
+	#include "config.h"
+#else
+#error "Cannot compile with HAVE_CONFIG_H symbol! run configure first!"
+#endif
+
 
 #include "./InterpFromGridToMeshx.h"
@@ -9,5 +16,4 @@
 #define __FUNCT__ "InterpFromGridToMeshx"
 
-int findindices(int* pm,int* pn,double* x,int x_rows, double* y,int y_rows, double xgrid,double ygrid);
 
 int InterpFromGridToMeshx( Vec* pdata_mesh,double* x_in, int x_rows, double* y_in, int y_rows, double* data, int M, int N, double* x_mesh, double* y_mesh, int nods,double default_value) {
@@ -20,10 +26,14 @@
 	double* x=NULL;
 	double* y=NULL;
-	int i,m,n;
-	double x_grid,y_grid;
-	double xi,eta;
-	double G1,G2,G3,G4,data_value;
-	double area_1,area_2,area_3;
-	double area;
+	double  x_grid,y_grid;
+	int     i;
+
+	/*threading: */
+	InterpFromGridToMeshxThreadStruct gate;
+	int num=1;
+
+	#ifdef _MULTITHREADING_
+	num=_NUMTHREADS_;
+	#endif
 
 	/*Some checks on arguments: */
@@ -58,110 +68,21 @@
 	}
 
-	/*Linear (triangle) interpolation: */
-	for ( i=MPI_Lowerrow(nods); i<MPI_Upperrow(nods); i++) {
+	/*initialize thread parameters: */
+	gate.x_mesh=x_mesh;
+	gate.y_mesh=y_mesh;
+	gate.x_rows=x_rows;
+	gate.y_rows=y_rows;
+	gate.x=x;
+	gate.y=y;
+	gate.nods=nods;
+	gate.data_mesh=data_mesh;
+	gate.data=data;
+	gate.M=M;
+	gate.N=N;
 
-		x_grid=*(x_mesh+i);
-		y_grid=*(y_mesh+i);
-
-		/*Find indices m and n into y and x, for which  y(m)<=y_grids<=y(m+1) and x(n)<=x_grid<=x(n+1)*/
-		if(findindices(&n,&m,x,x_rows, y,y_rows, x_grid,y_grid)){
-			
-			/*Get area*/
-			area=(x[n+1]-x[n])*(y[m+1]-y[m]);
-
-			/*is it the upper right triangle?*/
-			/*2'     3'
-			 *+-----+
-			 *1\    |
-			 *| \   |
-			 *|  \  |
-			 *|   \ |
-			 *|    \|
-			 *2----3+1' */
-			if ((x_grid-x[n])/(x[n+1]-x[n])<(y_grid-y[m])/(y[m+1]-y[m])){
-
-				/*Then find values of data at each summit*/
-				G1=*(data+m*N+n);
-				G2=*(data+(m+1)*N+n+1);
-				G3=*(data+(m+1)*N+n);
-
-				/*Get first area coordinate*/
-				area_1=((y[m+1]-y_grid)*(x[n+1]-x[n]))/area;
-				/*Get second area coordinate*/
-				area_2=((x_grid-x[n])*(y[m+1]-y[m]))/area;
-				/*Get third area coordinate = 1-area1-area2*/
-				area_3=1-area_1-area_2;
-
-				/*interpolate*/
-				data_value=area_1*G1+area_2*G2+area_3*G3;
-			}
-			else {
-
-				/*Then find values of data at each summit*/
-				G1=*(data+(m+1)*N+n+1);
-				G2=*(data+m*N+n);
-				G3=*(data+m*N+n+1);
-
-				/*Get first area coordinate*/
-				area_1=((y_grid-y[m])*(x[n+1]-x[n]))/area;
-				/*Get second area coordinate*/
-				area_2=((x[n+1]-x_grid)*(y[m+1]-y[m]))/area;
-				/*Get third area coordinate = 1-area1-area2*/
-				area_3=1-area_1-area_2;
-
-				/*interpolate*/
-				data_value=area_1*G1+area_2*G2+area_3*G3;
-			}
-
-			/*Treat NANs*/
-			if (isnan(data_value)){
-				data_value=default_value;
-			}
-		}
-		else{
-			data_value=default_value;
-		}
-		VecSetValue(data_mesh,i,data_value,INSERT_VALUES);
-	}
+	/*launch the thread manager with InterpFromGridToMeshxt as a core: */
+	LaunchThread(InterpFromGridToMeshxt,(void*)&gate,num);
 
 	/*Assign output pointers:*/
 	*pdata_mesh=data_mesh;
 }
-
-int findindices(int* pm,int* pn,double* x,int x_rows, double* y,int y_rows, double xgrid,double ygrid){
-
-	int foundx=0;
-	int foundy=0;
-	int i;
-	int m=-1;
-	int n=-1;
-
-	for (i=0;i<x_rows-1;i++){
-		if ( (*(x+i)<=xgrid) && (xgrid<*(x+i+1)) ){
-			m=i;
-			foundx= 1;
-			break;
-		}
-	}
-	if(*(x+x_rows-1)==xgrid){
-		m=x_rows-2;
-		foundx=1;
-	}
-	
-	for (i=0;i<y_rows-1;i++){
-		if ( (*(y+i)<=ygrid) && (ygrid<*(y+i+1)) ){
-			n=i;
-			foundy= 1;
-			break;
-		}
-	}
-	if(*(y+y_rows-1)==ygrid){
-		m=y_rows-2;
-		foundy=1;
-	}
-
-	/*Assign output pointers:*/
-	*pm=m;
-	*pn=n;
-	return foundx*foundy;
-}
Index: /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.h
===================================================================
--- /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.h	(revision 2548)
+++ /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshx.h	(revision 2549)
@@ -8,5 +8,30 @@
 #include "../toolkits/toolkits.h"
 
+
+
+/*threading: */
+typedef struct{
+
+	double* x_mesh;
+	double* y_mesh;
+	int     x_rows;
+	int     y_rows;
+	double* x;
+	double* y;
+	int     nods;
+	double  default_value;
+	Vec     data_mesh;
+	double* data;
+	int     M;
+	int     N;
+
+} InterpFromGridToMeshxThreadStruct;
+
+int findindices(int* pm,int* pn,double* x,int x_rows, double* y,int y_rows, double xgrid,double ygrid);
+
 int InterpFromGridToMeshx( Vec* pdata_mesh,double* x, int x_rows, double* y, int y_rows, double* data, int M, int N, double* x_mesh, double* y_mesh, int nods, double default_value);
+
+void* InterpFromGridToMeshxt(void* vInterpFromGridToMeshxThreadStruct);
+
 
 #endif /* _INTERPFROMGRIDTOMESHX_H */
Index: /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshxt.cpp
===================================================================
--- /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshxt.cpp	(revision 2549)
+++ /issm/trunk/src/c/InterpFromGridToMeshx/InterpFromGridToMeshxt.cpp	(revision 2549)
@@ -0,0 +1,174 @@
+/*!\file:  InterpFromGridToMeshxt.cpp
+ * \brief  thread core for InterpFromGridToMeshxt code
+ */ 
+
+#include "./InterpFromGridToMeshx.h"
+#include "../shared/shared.h"
+
+#undef __FUNCT__ 
+#define __FUNCT__ "InterpFromGridToMeshxt"
+
+void* InterpFromGridToMeshxt(void* vpthread_handle){
+
+	/*gate variables :*/
+	InterpFromGridToMeshxThreadStruct* gate=NULL;
+	pthread_handle* handle=NULL;
+	int     my_thread;
+	int     num_threads;
+	
+	Vec     data_mesh=NULL;
+	double* x_mesh=NULL;
+	double* y_mesh=NULL;
+	int     x_rows,y_rows;
+	double* x=NULL;
+	double* y=NULL;
+	int     nods;
+	double  default_value;
+	double* data=NULL;
+	int     M,N;
+
+
+	/*intermediary: */
+	int     i0;
+	int     i1;
+	int     i,m,n;
+	double  x_grid;
+	double  y_grid;
+	double  area;
+	double G1,G2,G3,G4,data_value;
+	double area_1,area_2,area_3;
+	double xi,eta;
+
+
+	/*recover handle and gate: */
+	handle=(pthread_handle*)vpthread_handle;
+	gate=(InterpFromGridToMeshxThreadStruct*)handle->gate;
+	my_thread=handle->id;
+	num_threads=handle->num;
+	
+	/*recover parameters :*/
+	x_mesh=gate->x_mesh;
+	y_mesh=gate->y_mesh;
+	x_rows=gate->x_rows;
+	y_rows=gate->y_rows;
+	x=gate->x;
+	y=gate->y;
+	nods=gate->nods;
+	data_mesh=gate->data_mesh;
+	data=gate->data;
+	default_value=gate->default_value;
+	M=gate->M;
+	N=gate->N;
+
+	/*partition loop across threads: */
+	PartitionRange(&i0,&i1,nods,num_threads,my_thread);
+
+	printf("%i %i %i %i\n",i0,i1,my_thread,num_threads);
+
+	/*Linear (triangle) interpolation: */
+	for ( i=i0; i<i1; i++) {
+
+		x_grid=*(x_mesh+i);
+		y_grid=*(y_mesh+i);
+
+		/*Find indices m and n into y and x, for which  y(m)<=y_grids<=y(m+1) and x(n)<=x_grid<=x(n+1)*/
+		if(findindices(&n,&m,x,x_rows, y,y_rows, x_grid,y_grid)){
+			
+			/*Get area*/
+			area=(x[n+1]-x[n])*(y[m+1]-y[m]);
+
+			/*is it the upper right triangle?*/
+			/*2'     3'
+			 *+-----+
+			 *1\    |
+			 *| \   |
+			 *|  \  |
+			 *|   \ |
+			 *|    \|
+			 *2----3+1' */
+			if ((x_grid-x[n])/(x[n+1]-x[n])<(y_grid-y[m])/(y[m+1]-y[m])){
+
+				/*Then find values of data at each summit*/
+				G1=*(data+m*N+n);
+				G2=*(data+(m+1)*N+n+1);
+				G3=*(data+(m+1)*N+n);
+
+				/*Get first area coordinate*/
+				area_1=((y[m+1]-y_grid)*(x[n+1]-x[n]))/area;
+				/*Get second area coordinate*/
+				area_2=((x_grid-x[n])*(y[m+1]-y[m]))/area;
+				/*Get third area coordinate = 1-area1-area2*/
+				area_3=1-area_1-area_2;
+
+				/*interpolate*/
+				data_value=area_1*G1+area_2*G2+area_3*G3;
+			}
+			else {
+
+				/*Then find values of data at each summit*/
+				G1=*(data+(m+1)*N+n+1);
+				G2=*(data+m*N+n);
+				G3=*(data+m*N+n+1);
+
+				/*Get first area coordinate*/
+				area_1=((y_grid-y[m])*(x[n+1]-x[n]))/area;
+				/*Get second area coordinate*/
+				area_2=((x[n+1]-x_grid)*(y[m+1]-y[m]))/area;
+				/*Get third area coordinate = 1-area1-area2*/
+				area_3=1-area_1-area_2;
+
+				/*interpolate*/
+				data_value=area_1*G1+area_2*G2+area_3*G3;
+			}
+
+			/*Treat NANs*/
+			if (isnan(data_value)){
+				data_value=default_value;
+			}
+		}
+		else{
+			data_value=default_value;
+		}
+		VecSetValue(data_mesh,i,data_value,INSERT_VALUES);
+	}
+
+}
+
+
+int findindices(int* pm,int* pn,double* x,int x_rows, double* y,int y_rows, double xgrid,double ygrid){
+
+	int foundx=0;
+	int foundy=0;
+	int i;
+	int m=-1;
+	int n=-1;
+
+	for (i=0;i<x_rows-1;i++){
+		if ( (*(x+i)<=xgrid) && (xgrid<*(x+i+1)) ){
+			m=i;
+			foundx= 1;
+			break;
+		}
+	}
+	if(*(x+x_rows-1)==xgrid){
+		m=x_rows-2;
+		foundx=1;
+	}
+	
+	for (i=0;i<y_rows-1;i++){
+		if ( (*(y+i)<=ygrid) && (ygrid<*(y+i+1)) ){
+			n=i;
+			foundy= 1;
+			break;
+		}
+	}
+	if(*(y+y_rows-1)==ygrid){
+		m=y_rows-2;
+		foundy=1;
+	}
+
+	/*Assign output pointers:*/
+	*pm=m;
+	*pn=n;
+	return foundx*foundy;
+}
Index: /issm/trunk/src/c/InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dxt.cpp
===================================================================
--- /issm/trunk/src/c/InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dxt.cpp	(revision 2548)
+++ /issm/trunk/src/c/InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dxt.cpp	(revision 2549)
@@ -45,5 +45,4 @@
 	double area_1,area_2,area_3;
 	double data_value;
-	int    step;
 
 	/*recover handle and gate: */
@@ -72,10 +71,5 @@
 
 	/*distribute elements across threads :*/
-	step=(int)floor((double)nels_data/(double)num_threads);
-	for(i=0;i<(my_thread+1);i++){
-		i0=i*step;
-		if(i==(num_threads-1))i1=nels_data;
-		else i1=i0+step;
-	}
+	PartitionRange(&i0,&i1,nels_data,num_threads,my_thread);
 	
 	for (i=i0;i<i1;i++){
Index: /issm/trunk/src/c/Makefile.am
===================================================================
--- /issm/trunk/src/c/Makefile.am	(revision 2548)
+++ /issm/trunk/src/c/Makefile.am	(revision 2549)
@@ -89,4 +89,5 @@
 					./shared/Threads/issm_threads.h\
 					./shared/Threads/LaunchThread.cpp\
+					./shared/Threads/PartitionRange.cpp\
 					./shared/Matlab/matlabshared.h\
 					./shared/Matlab/PrintfFunction.cpp\
@@ -249,4 +250,5 @@
 					./InterpFromGridToMeshx/InterpFromGridToMeshx.cpp\
 					./InterpFromGridToMeshx/InterpFromGridToMeshx.h\
+					./InterpFromGridToMeshx/InterpFromGridToMeshxt.cpp\
 					./InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dx.cpp\
 					./InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dxt.cpp\
@@ -386,4 +388,5 @@
 					./shared/Threads/issm_threads.h\
 					./shared/Threads/LaunchThread.cpp\
+					./shared/Threads/PartitionRange.cpp\
 					./shared/Alloc/alloc.h\
 					./shared/Alloc/alloc.cpp\
@@ -545,4 +548,5 @@
 					./InterpFromGridToMeshx/InterpFromGridToMeshx.cpp\
 					./InterpFromGridToMeshx/InterpFromGridToMeshx.h\
+					./InterpFromGridToMeshx/InterpFromGridToMeshxt.cpp\
 					./InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dx.cpp\
 					./InterpFromMeshToMesh2dx/InterpFromMeshToMesh2dxt.cpp\
Index: /issm/trunk/src/c/shared/Threads/PartitionRange.cpp
===================================================================
--- /issm/trunk/src/c/shared/Threads/PartitionRange.cpp	(revision 2549)
+++ /issm/trunk/src/c/shared/Threads/PartitionRange.cpp	(revision 2549)
@@ -0,0 +1,37 @@
+/*!\file:  PartitionRange.cpp
+ * \brief: return i0,i1, range of local thread.
+ */ 
+
+#ifdef HAVE_CONFIG_H
+	#include "config.h"
+#else
+#error "Cannot compile with HAVE_CONFIG_H symbol! run configure first!"
+#endif
+
+#include <math.h>
+
+#undef __FUNCT__ 
+#define __FUNCT__ "PartitionRange"
+
+void PartitionRange(int* pi0,int* pi1, int num_el,int num_threads,int my_thread){
+
+	/*output: */
+	int i0,i1;
+	
+	int step;
+	int i;
+
+
+	/*distribute elements across threads :*/
+	step=(int)floor((double)num_el/(double)num_threads);
+	for(i=0;i<(my_thread+1);i++){
+		i0=i*step;
+		if(i==(num_threads-1))i1=num_el;
+		else i1=i0+step;
+	}
+
+
+	/*Assign output pointers:*/
+	*pi0=i0;
+	*pi1=i1;
+}
Index: /issm/trunk/src/c/shared/Threads/issm_threads.h
===================================================================
--- /issm/trunk/src/c/shared/Threads/issm_threads.h	(revision 2548)
+++ /issm/trunk/src/c/shared/Threads/issm_threads.h	(revision 2549)
@@ -18,4 +18,5 @@
  * or just serially if not requested: */
 void LaunchThread(void* function(void*), void* gate,int num_threads);
+void PartitionRange(int* pi0,int* pi1, int num_el,int num_threads,int my_thread);
 
 #endif //ifndef _ISSM_THREADS_H_
