28.10.2014 Views

Ejemplos MPI

Ejemplos MPI

Ejemplos MPI

SHOW MORE
SHOW LESS

Create successful ePaper yourself

Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.

Ejemplo <strong>MPI</strong><br />

Ivar Fernando Gómez Pedraza


Multiplicación de matrices<br />

• Hacer un programa que realice la<br />

multiplicación de dos matrices, tales que el<br />

número de columnas de la matriz A es igual al<br />

número de filas de la matriz B; es decir:


• la multiplicación de A por B, que se denota<br />

A·B, A×B o simplemente AB, está definida<br />

como:<br />

• donde cada elemento c i,j está definido por:


Gráficamente, si<br />

y<br />

Entonces


Procedimiento secuencial<br />

Un solo proceso que ejecuta:<br />

for(i=0; i


Multiplicación de Matrices<br />

Procedimiento paralelo<br />

• Un proceso maestro -> distribuye las distintas<br />

tareas al resto de procesos.<br />

• Varios procesos worker -> calcula un cierto<br />

número de filas de la matriz resultante y<br />

reenvía el resultado parcial al proceso<br />

maestro.<br />

Num_workers = num_procesos -1


Proceso en el MAESTRO<br />

• Conocer las matrices a multiplicar a y b<br />

• Inicialización de las matrices a y b<br />

• Cálculo del número de filas que hay que enviar a cada<br />

proceso worker:<br />

• nfilas = NFA / num_workers<br />

• filas_extra = NFA % num_workers<br />

• ENVIO a cada WORKER:<br />

• Numero de filas de la matriz “a” -> nfilas o nfilas+1<br />

• Elementos de “a” con los que debe operar -> nfilas*NCA<br />

elementos de “a”<br />

• Matriz “b” en su totalidad.<br />

• ESPERAR... (mientras los workers trabajan)


• RECEPCIÓN de cada WORKER<br />

– Subparte de la matriz resultado “c”-> nfilas*NCB<br />

elementos.<br />

• Atención!!! ¿¿¿dónde metemos los elementos<br />

recibidos???<br />

cada worker puede haber calculado un<br />

número de filas distintas, calcular cuántas y<br />

guardar resultado en matriz “c” con el<br />

desplazamiento adecuado.


Fase de envío:<br />

<strong>MPI</strong>_send<br />

Fase<br />

recepción:<br />

<strong>MPI</strong>_recv


Proceso en el WORKER<br />

• Desconoce tanto la matriz a como la b<br />

• Recepción del MAESTRO de:<br />

• Número de filas -> nfilas<br />

• Elementos de a con los que va a calcular -> nfilas*NCA elementos<br />

• Matriz b en su totalidad<br />

• Fase de Cálculo:<br />

for(i=0; i


Código en <strong>MPI</strong><br />

• Se colocan las librerías a usar<br />

#include "mpi.h"<br />

#include <br />

#include <br />

Librería de C que<br />

contiene las<br />

operaciones estándar<br />

de entrada y salida<br />

Librería que contiene<br />

los prototipos de<br />

funciones de C para<br />

gestión de memoria<br />

dinámica, control de<br />

procesos y otras


int main (int argc, char *argv[])<br />

{<br />

int nsize, rank, rc, i, j, k,numworkers, /* number of worker tasks */<br />

source, /* task id of message source */<br />

dest, /* task id of message destination */<br />

mtype, /* message type */<br />

rows, /* rows of matrix A sent to each worker */<br />

averow, extra, offset; /* used to determine rows<br />

sent to each worker */<br />

int NRA=4, NCA=6, NCB=3, MASTER=0;<br />

double a[NRA][NCA], /* matriz A */<br />

b[NCA][NCB], /* matriz B */<br />

c[NRA][NCB]; /* matriz resultado C */<br />

<strong>MPI</strong>_Status status;


<strong>MPI</strong>_Init(&argc,&argv);<br />

<strong>MPI</strong>_Comm_rank(<strong>MPI</strong>_COMM_WORLD,&taskid);<br />

<strong>MPI</strong>_Comm_size(<strong>MPI</strong>_COMM_WORLD,&numtasks);<br />

if (numtasks < 2 ) {<br />

printf("Need at least two <strong>MPI</strong> tasks. Quitting...\n");<br />

<strong>MPI</strong>_Abort(<strong>MPI</strong>_COMM_WORLD, rc);<br />

exit(1);<br />

}<br />

numworkers = numtasks-1;


• /***************** master task ************************/<br />

• if (taskid == MASTER)<br />

• {<br />

• printf("mpi_mm has started with %d tasks.\n",numtasks);<br />

• printf("Initializing arrays...\n");<br />

• for (i=0; i


• /* Send matrix data to the worker tasks */<br />

• averow = NRA/numworkers;<br />

• extra = NRA%numworkers;<br />

• offset = 0;<br />

• mtype = FROM_MASTER;<br />

• for (dest=1; dest


• /* Receive results from worker tasks */<br />

mtype = FROM_WORKER;<br />

for (i=1; i


• /* Print results */<br />

• printf("******************************************************\n");<br />

• printf("Result Matrix:\n");<br />

• for (i=0; i


• /**************************** worker task ************************************/<br />

• if (taskid > MASTER)<br />

• {<br />

• mtype = FROM_MASTER;<br />

• <strong>MPI</strong>_Recv(&offset, 1, <strong>MPI</strong>_INT, MASTER, mtype, <strong>MPI</strong>_COMM_WORLD, &status);<br />

• <strong>MPI</strong>_Recv(&rows, 1, <strong>MPI</strong>_INT, MASTER, mtype, <strong>MPI</strong>_COMM_WORLD, &status);<br />

• <strong>MPI</strong>_Recv(&a, rows*NCA, <strong>MPI</strong>_DOUBLE, MASTER, mtype, <strong>MPI</strong>_COMM_WORLD, &status);<br />

• <strong>MPI</strong>_Recv(&b, NCA*NCB, <strong>MPI</strong>_DOUBLE, MASTER, mtype, <strong>MPI</strong>_COMM_WORLD, &status);<br />

• for (k=0; k

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!