| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140 | /* * StarPU * Copyright (C) INRIA 2008-2009 (see AUTHORS file) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by * the Free Software Foundation; either version 2.1 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Lesser General Public License in COPYING.LGPL for more details. */#include <starpu_mpi.h>#include <stdlib.h>#define NITER	2048#define BIGSIZE	64#define SIZE	64int main(int argc, char **argv){	MPI_Init(NULL, NULL);	int rank, size;	MPI_Comm_rank(MPI_COMM_WORLD, &rank);	MPI_Comm_size(MPI_COMM_WORLD, &size);	if (size < 2)	{		if (rank == 0)			fprintf(stderr, "We need at least processes.\n");		MPI_Finalize();		return 0;	}	/* We only use 2 nodes for that test */	if (rank >= 2)	{		MPI_Finalize();		return 0;	}			starpu_init(NULL);	starpu_mpi_initialize();	/* Node 0 will allocate a big block and only register an inner part of	 * it as the block data, Node 1 will allocate a block of small size and	 * register it directly. Node 0 and 1 will then exchange the content of	 * their blocks. */	float *block;	starpu_data_handle block_handle;	if (rank == 0)	{		starpu_malloc_pinned_if_possible((void **)&block,				BIGSIZE*BIGSIZE*BIGSIZE*sizeof(float));		memset(block, 0, BIGSIZE*BIGSIZE*BIGSIZE*sizeof(float));		/* fill the inner block */		unsigned i, j, k;		for (k = 0; k < SIZE; k++)		for (j = 0; j < SIZE; j++)		for (i = 0; i < SIZE; i++)		{			block[i + j*BIGSIZE + k*BIGSIZE*BIGSIZE] = 1.0f;		}		starpu_register_block_data(&block_handle, 0,			(uintptr_t)block, BIGSIZE, BIGSIZE*BIGSIZE,			SIZE, SIZE, SIZE, sizeof(float));	}	else /* rank == 1 */	{		starpu_malloc_pinned_if_possible((void **)&block,			SIZE*SIZE*SIZE*sizeof(float));		memset(block, 0, SIZE*SIZE*SIZE*sizeof(float));		starpu_register_block_data(&block_handle, 0,			(uintptr_t)block, SIZE, SIZE*SIZE,			SIZE, SIZE, SIZE, sizeof(float));	}	if (rank == 0)	{		starpu_mpi_send(block_handle, 1, 0x42, MPI_COMM_WORLD);		MPI_Status status;		starpu_mpi_recv(block_handle, 1, 0x1337, MPI_COMM_WORLD, &status);		/* check the content of the block */		starpu_sync_data_with_mem(block_handle, STARPU_R);		unsigned i, j, k;		for (k = 0; k < SIZE; k++)		for (j = 0; j < SIZE; j++)		for (i = 0; i < SIZE; i++)		{			assert(block[i + j*BIGSIZE + k*BIGSIZE*BIGSIZE] == 33.0f);		}		starpu_release_data_from_mem(block_handle);			}	else /* rank == 1 */	{		MPI_Status status;		starpu_mpi_recv(block_handle, 0, 0x42, MPI_COMM_WORLD, &status);		/* check the content of the block and modify it */		starpu_sync_data_with_mem(block_handle, STARPU_RW);		unsigned i, j, k;		for (k = 0; k < SIZE; k++)		for (j = 0; j < SIZE; j++)		for (i = 0; i < SIZE; i++)		{			assert(block[i + j*SIZE + k*SIZE*SIZE] == 1.0f);			block[i + j*SIZE + k*SIZE*SIZE] = 33.0f;		}		starpu_release_data_from_mem(block_handle);		starpu_mpi_send(block_handle, 0, 0x1337, MPI_COMM_WORLD);	}	fprintf(stdout, "Rank %d is done\n", rank);	fflush(stdout);	starpu_mpi_shutdown();	starpu_shutdown();	MPI_Finalize();	return 0;}
 |