Message Passing Interface - Pedro de Botelho Marcos Maio/2008 1
Sumário Introdução; Conceitos básicos; Comunicação; Principais rotinas; Compilando e executando códigos ; Exemplos; Referências; 2
Introdução = Message Passing Interface; É uma biblioteca que define rotinas para comunicação entre processos paralelos; É portável para qualquer arquitetura; É compatível com as linguagens C/C++ e Fortran; O paralelismo é explicito, ou seja, o programador é responsável pela distribuição; 3
Estrutura do código com #include<stdio.h> #include mpi.h int main(int argc, char *argv[ ]) { _Init(&argc, &argv);.. Código usando rotinas do... _Finalize(); // Inicializa //Encerra return 0; } 4
Conceitos Básicos Mensagem: É o conteúdo de uma comunicação. É formado por duas partes: Endereço: Destino e origem da mensagem; Dados: A informação a ser transmitida; Rank: É o identificador único do processo. Varia de 0 a N-1; 5
Conceitos Básicos Grupo: É um conjunto de processos que podem se comunicar. Sempre está associado a um comunicador; Comunicador: É um objeto local que representa o domínio de uma comunicação. 6
Conceitos Básicos Application Buffer: É o endereço de memória que armazena um dado que o processo necessita receber ou enviar. System Buffer: É o endereço de memória reservado pelo sistema para armazenar mensagens. 7
Conceitos Básicos Overhead: É um desperdício de tempo que ocorre durante a execução do processo. Existem dois tipos de overhead: System Overhead: Tempo gasto pelo sistema na transferência de dados para o processso destino. Synchronization Overhead: Tempo gasto para a sincronização dos processos. 8
Tipos de Dados 9
Técnicas de Comunicação entre Processos Buffering; Blocking; Non-Blocking; Assíncrona; Síncrona; 10
Buffering É a cópia temporária de mensagens entre endereços de memória efetuada pelo sistema como parte de seu protocolo de comunicação. A cópia ocorre entre o buffer do usuário (application buffer) definido pelo processo e o buffer do sistema (system buffer) definido pela biblioteca. Exemplo: Processo já começou o envio, porém, o processo que recebe ainda não. 11
Blocking A finalização da execução da rotina é dependente de determinados eventos. O processo só prosseguirá quando tiver certeza de que o application buffer pode ser usado novamente. Exemplo: Quando se deseja obter confirmação do recebimento de dados para continuar o processamento. 12
Non-Blocking A finalização da rotina não é dependente de outros eventos. Exemplo: Quando não existem dependências ou necessidade de controle intensivo sobre o programa. 13
Assíncrona O processo que envia a mensagem não espera uma confirmação de recebimento para prosseguir. Exemplo: Usada em comunicação confiável. 14
Síncrona O processo que enviou uma mensagem aguarda uma confirmação de recebimento para prosseguir a sua execução. Exemplo: Utilizada quando se torna necessária a confirmação de recebimento. Por exemplo, se a rede for instável. 15
Tipos de Comunicação Ponto a ponto: Executa a transferência de dados entre dois processos; Coletiva: Envolve comunicação entre dois ou mais processos; 16
Ponto a Ponto Síncrona (Synchronus); Imediata (Ready); Bufferizada (Buffered); 17
Síncrona O processo não retorna sua execução enquanto não houver uma confirmação de recebimento da mensagem 18
Imediata Sabe-se, a priori, que o recebimento de uma mensagem já foi realizado pelo processo destino. 19
Bufferizada A operação de envio utiliza uma quantidade específica para buffer alocada pelo usuário. Exemplo: Se o tamanho da mensagem ultrapassar 4Kbytes(buffer padrão). 20
Coletiva Difusão (Broadcast); Redução (Reduction); Coleta (Gather); Espalhamento (Scatter); 21
Difusão Um único processo envia os mesmos dados para todos os processos com o mesmo comunicador. 22
Redução Um processo coleta dados nos demais processos e aplica uma determinada operação sobre estes dados. O resultado será armazenada em um processo definido pelo usuário. Exemplo: Maior valor, menor valor. 23
Coleta A estrutura dos dados distribuída é coletada por um único processo. 24
Espalhamento A estrutura dos dados que está armazenada em um único processo é distribuída para todos os processos do comunicador. 25
Principais Rotinas Rotinas de Inicialização/Encerramento; Rotinas de Grupo; Rotinas de Envio/Recebimento de Mensagens; 26
Inicialização e Encerramento _Init Inicializa o ambiente ; _Finalize Finaliza o ambiente ; 27
_Init Sintaxe: Em C: int _Init (int *argc, char *argv[]) Em Fortran: call _INIT (mpierr) Parâmetros: argc Apontador para a quantidade de parametros da linha de comando; argv Apontador para um vetor de strings com os comandos recebidos; 28
_Finalize Sintaxe: Em C: int _Finalize (void) Em Fortran: call _FINALIZE (mpierr) 29
Informações sobre o comunicador _Comm_rank Identifica um processo dentro de um determinado grupo; _Comm_size Retorna o número de processos dentro do grupo; 30
_Comm_rank Sintaxe: Em C: int _Comm_rank (_Comm comm, int *rank) Em Fortran: call _COMM_RANK (comm, rank, mpierr) Parâmetros: comm Comunicador do ; rank Variável inteira com o numero de identificação do processo. 31
_Comm_size Sintaxe: Em C: int _Comm_size (_Comm comm, int *size) Em Fortran: call _COMM_SIZE (comm, size, mpierr) Parâmetros: comm Comunicador do ; size Variável interna que retorna o número de processos iniciados pelo. 32
Troca de Mensagens _Send Rotina básica para envio de mensagens; _Recv Rotina básica para recebimento de mensegens; 33
_Send Sintaxe: Em C: int _Send (void *sndbuf, int count, _Datatype dtype, int dest, int tag, _Comm comm) Em Fortran: call _SEND (sndbuf, count, dtype, dest, tag, comm, mpierr) Parâmetros: sndbuf Identificação do buffer; count Número de elementos a serem enviados; dtype Tipo de dado dest Identificação do processo destino; tag Rótulo (label) da mensagem; comm Communicator 34
_Recv Sintaxe: Em C: int _Recv (void *recvbuf, int count, _Datatype dtype, int source, int tag, _Comm comm, _Status status) Em Fortran: call _RECV (recvbuf, count, dtype, source, tag, comm, status, mpierr) Parâmetros: recvbuf Identificação do buffer (endereço inicial do "application buffer" de onde os dados estão sendo enviados); count Número de elementos a serem recebidos; dtype Tipo de dado source Identificação do processo emissor; tag Rótulo (label) da mensagem; comm Communicator status Vetor de informações envolvendo os parâmetros source e tag. 35
Compilando Em C/C++ mpicc [fonte.c] -o [executável] [parâmetros] Em Fortran mpif77 [fonte.f] -o [executável] [parâmetros] 36
Executando Em C/C++/Fortran mpirun [argumentos] [executável] Exemplos de argumentos: -np Número de processadores; -nolocal Não executa na máquina local; -h Mostra todas opções disponíveis; -machinefile Especifica arquivo com nomes das máquinas; 37
Exemplo Cada processo escreve um Hello! #include "mpi.h #include <stdio.h> Int main( int argc, char * argv[ ] ) { int processid; /* rank dos processos */ int noprocesses; /* Número de processos */ int namesize; /* Tamanho do nome */ char computername[50]; _Init(&argc, &argv); _Comm_size(_COMM_WORLD, &noprocesses); _Comm_rank(_COMM_WORLD, &processid); _Get_processor_name(computerName, &namesize); fprintf(stderr,"hello from process %d on %s\n", processid, computername); _Finalize( ); return 0; } 38
Exemplo Master envia mensagem para demais processos #include <stddef.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include "mpi.h" main(int argc, char *argv[]) { char message[20]; int i, rank, size, type = 99; _Status status; _Init(&argc, &argv); _Comm_size(_COMM_WORLD, &size); _Comm_rank(_COMM_WORLD, &rank); if (rank == 0) { strcpy(message, "Hello, world"); for (i = 1; i < size; i++) _Send(message, 13, _CHAR, i, type, _COMM_WORLD); } else _Recv(message, 20, _CHAR, 0, type, _COMM_WORLD, &status); printf( "Message from process = %d : %.13s\n", rank,message); _Finalize(); } 39
Referências http://www.llnl.gov/computing/tutorials/mpi/ http://www.dartmouth.edu/ %7Erc/classes/intro_mpi/ 40