Introdução ao Processamento Paralelo (3)

502 views

Published on

Minicurso ofericido durante a III Semana de Inverno de Geofisica, IMECC/UNICAMP, 2012, por Jairo Panetta (ITA/ICE).

Published in: Education
0 Comments
0 Likes
Statistics
Notes
  • Be the first to comment

  • Be the first to like this

No Downloads
Views
Total views
502
On SlideShare
0
From Embeds
0
Number of Embeds
20
Actions
Shares
0
Downloads
0
Comments
0
Likes
0
Embeds 0
No embeds

No notes for slide

Introdução ao Processamento Paralelo (3)

  1. 1. MIMD: Arquitetura x Modelo • Troca de mensagens usualmente implementada por processos (ex: MPI) • Fork-join usualmente implementada por threads (ex: OpenMP) Memória Central Memória Distribuída Troca de √ √ Mensagens Fork-Join √ X1 III Semana Inverno Geofísica
  2. 2. Excursionando por MPIFontes:Padrão MPI 1.1 em www.mpi-forum.orgGropp, Lusk and Skjellum: “Using MPI”, 2nd edition, MIT Press, 1999Snir, et al, “MPI – Vol 1, The MPI Core”, 2nd edition, MIT Press, 2001Pacheco, P.: “Parallel Programming with MPI”, Morgan Kaufmann, 19972 III Semana Inverno Geofísica
  3. 3. MPI • Ao paralelizar um programa, busque independências – Independências permitirem execuções simultâneas • MPI paraleliza processos que cooperam em uma mesma computação, trocando mensagens quando necessário. • Dificuldades: – Os processos executam (usualmente) o mesmo (único) texto do programa; – O texto do programa divide o trabalho entre os processos • Para reduzir o tempo de execução – A computação é o conjunto dos processos em execução • Para entender a computação, é necessário imaginar a execução simultânea de cópias do texto do programa, cada cópia atuando no seu trecho do trabalho • Não ocorre em OpenMP3 III Semana Inverno Geofísica
  4. 4. Programa Seqüencial PROGRAM bobo IMPLICIT NONE INTEGER, PARAMETER :: tam=1000000000 REAL :: vec(tam) INTEGER :: i DO i = 1, tam vec(i) = REAL(i - tam/2) ** 2 END DO DO i = 1, tam vec(i) = SQRT(vec(i)) END DO WRITE(*,(" maximo = ", f9.0,"; minimo =",f9.0))& MAXVAL(vec), MINVAL(vec) END PROGRAM bobo4 III Semana Inverno Geofísica
  5. 5. Estratégia de Paralelismo • Dividir o trabalho dos laços de inicialização e de computação entre os processos – Pois as iterações desses laços são independentes • Para tanto, basta dividir o espaço de índices dos laços. Transformar DO i = 1, tam vec(i) = REAL(i - tam/2) ** 2 END DO DO i = 1, tam vec(i) = SQRT(vec(i)) END DO em DO i = pri, ult vec(i) = REAL(i - tam/2) ** 2 END DO DO i = pri, ult vec(i) = SQRT(vec(i)) END DO onde os valores de pri e ult variam de processo para processo5 III Semana Inverno Geofísica
  6. 6. MPI Versão 0 PROGRAM bobo IMPLICIT NONE INTEGER, PARAMETER :: tam=1000000000 REAL :: vec(tam) REAL :: maxTot(0:7), minTot(0:7) INTEGER :: i, pri, ult, tamLocal, ierr, numProc, esteProc, iproc INCLUDE "mpif.h" INTEGER :: status(MPI_STATUS_SIZE)6 III Semana Inverno Geofísica
  7. 7. MPI Versão 0 Quantos processos CALL MPI_INIT(ierr) CALL MPI_COMM_SIZE(MPI_COMM_WORLD, numProc , ierr) CALL MPI_COMM_RANK(MPI_COMM_WORLD, esteProc, ierr) tamLocal = tam/numProc pri = esteProc*tamLocal + 1 IF (esteProc == numProc-1) THEN Número deste ult = tam Processo (0:numProc-1) ELSE ult = (esteProc+1)*tamLocal Divisão de Domínio: END IF DO i = pri, ult Índices do laço vec(i) = REAL(i - tam/2) ** 2 divididos entre os processos END DO Resto no último processo DO i = pri, ult vec(i) = SQRT(vec(i)) END DO7 III Semana Inverno Geofísica
  8. 8. MPI Versão 0 maxTot(esteProc) = MAXVAL(vec(pri:ult)) minTot(esteProc) = MINVAL(vec(pri:ult)) IF (esteProc /= 0) THEN CALL MPI_SEND(maxTot(esteProc), 1, MPI_REAL, 0, & 12, MPI_COMM_WORLD, ierr) CALL MPI_SEND(minTot(esteProc), 1, MPI_REAL, 0, & 13, MPI_COMM_WORLD, ierr) ELSE DO iProc = 1, numProc-1 CALL MPI_RECV(maxTot(iProc), 1, MPI_REAL, & MPI_ANY_SOURCE, 12, MPI_COMM_WORLD, status, ierr) CALL MPI_RECV(minTot(iProc), 1, MPI_REAL, & MPI_ANY_SOURCE, 13, MPI_COMM_WORLD, status, ierr) END DO END IF8 III Semana Inverno Geofísica
  9. 9. MPI Versão 0 IF (esteProc == 0) THEN WRITE(*,(" maximo = ", f12.0,"; minimo =",f12.0))& MAXVAL(maxTot(0:numProc-1)), & MINVAL(minTot(0:numProc-1)) END IF CALL MPI_FINALIZE(ierr) END PROGRAM bobo9 III Semana Inverno Geofísica
  10. 10. MPI – Versão 0 Processos Tempo CPU (s) Speed-up 1 167,87 1,00 2 84,78 1,98 3 56,90 2,95 4 --- --- 5 --- --- 6 --- ---10 III Semana Inverno Geofísica
  11. 11. MPI Versão 0 • A Versão 0 usa, por processo, a mesma quantidade de memória do programa seqüencial – Os p processos da Versão 0 do programa MPI usam, no total, p vezes a memória do programa seqüencial. – Pode esgotar a memória em máquinas de memória central (como no exemplo) • Para que o programa paralelo use (aproximadamente) a mesma quantidade de memória do programa seqüencial, é necessário reescrever o seqüencial alocando a cada processo apenas a memória necessária • Tipicamente, duas formas: 1. Mantém os índices do programa seqüencial e aloca os objetos apenas nos índices necessários; – Trivial em Fortran 2. Mapeia os índices do programa seqüencial em 1:N (ou 0:N-1), onde N é o tamanho do domínio neste processo; – Translação de indices (indice global = indice local + deslocamento)11 III Semana Inverno Geofísica
  12. 12. Dificuldades da forma 2 • Dificuldade 1: particionar o vetor entre os processos para reduzir memória • Vec(1:tamLocal) vai representar o trecho pri:ult do vetor global “vec” • Dificuldade 2: Ao particionar o vetor, mudam os índices (há índices locais ao processo que representam índices globais ao objeto) • No laço abaixo, i é índice global, mas Vec será indexado por índices locais (problema na expressão no lado direito da atribuição) DO i = 1, tamLocal vec(i) = REAL(i - tam/2) ** 2 END DO Indice local Indice global12 III Semana Inverno Geofísica
  13. 13. Particionar Objetos • Para reduzir a memória é necessário particionar os objetos entre os processos • MPI cria nProc processos, numerados de 0 a nProc-1 • Particionar array de tamanho tam entre nProc processos: tamLocal = tam/nProc resto = tam – tamLocal*nProc If (esteProc < resto) then tamLocal = tamLocal+1 end if • Exemplo tam=10 nProc=4 Proc 0 Proc 1 Proc 2 Proc 3 tamLocal 3 tamLocal 3 tamLocal 2 tamLocal 213 III Semana Inverno Geofísica
  14. 14. Índices Locais e Globais • Array global indexado 1:tam • Array local indexado 1:tamLocal • Indice global = indice local + deslocamento tamLocal = tam/nProc resto = tam – tamLocal*nProc If (esteProc < resto) then tamLocal = tamLocal+1 desloc = esteProc * tamLocal else desloc = esteProc*tamLocal + resto end if • Ex: tam=10, nProc=4Índice global 1 2 3 4 5 6 7 8 9 10Índice local 1 2 3 1 2 3 1 2 1 2 Proc 0 Proc 1 Proc 2 Proc 3 deslocamento 0 3 6 8 tamLocal3 tamLocal3 tamLocal2 tamLocal214 III Semana Inverno Geofísica
  15. 15. MPI Versão 1 PROGRAM bobo IMPLICIT NONE INTEGER, PARAMETER :: tam=1000000000 REAL, ALLOCATABLE :: vec(:) REAL :: maxTot(0:7), minTot(0:7) INTEGER :: i, tamLocal, resto, ierr, numProc, esteProc, iproc INCLUDE "mpif.h" INTEGER :: status(MPI_STATUS_SIZE)15 III Semana Inverno Geofísica
  16. 16. MPI Versão 1 CALL MPI_INIT(ierr) CALL MPI_COMM_SIZE(MPI_COMM_WORLD, numProc , ierr) CALL MPI_COMM_RANK(MPI_COMM_WORLD, esteProc, ierr) tamLocal = tam/numProc resto = tam – tamLocal * numProc IF (esteProc < resto) THEN tamLocal=tamLocal+1; ult = tamLocal; desloc=esteProc*tamLocal ELSE desloc=esteProc*tamLocal + resto END IF ALLOCATE(vec(tamLocal)) DO i = 1, tamLocal vec(i) = REAL(i+desloc - tam/2) ** 2 END DO DO i = 1, tamLocal vec(i) = SQRT(vec(i)) END DO16 III Semana Inverno Geofísica
  17. 17. MPI Versão 1 maxTot(esteProc) = MAXVAL(vec(tamLocal)) minTot(esteProc) = MINVAL(vec(tamLocal)) IF (esteProc /= 0) THEN CALL MPI_SEND(maxTot(esteProc), 1, MPI_REAL, 0, & 12, MPI_COMM_WORLD, ierr) CALL MPI_SEND(minTot(esteProc), 1, MPI_REAL, 0, & 13, MPI_COMM_WORLD, ierr) ELSE DO iProc = 1, numProc-1 CALL MPI_RECV(maxTot(iProc), 1, MPI_REAL, & MPI_ANY_SOURCE, 12, MPI_COMM_WORLD, status, ierr) CALL MPI_RECV(minTot(iProc), 1, MPI_REAL, & MPI_ANY_SOURCE, 13, MPI_COMM_WORLD, status, ierr) END DO END IF17 III Semana Inverno Geofísica
  18. 18. MPI Versão 1 IF (esteProc == 0) THEN WRITE(*,(" maximo = ", f12.0,"; minimo =",f12.0))& MAXVAL(maxTot(0:numProc-1)), & MINVAL(minTot(0:numProc-1)) END IF CALL MPI_FINALIZE(ierr) END PROGRAM bobo18 III Semana Inverno Geofísica
  19. 19. MPI – Versão 1 Processos Tempo CPU (s) Speed-up Eficiência 1 167,87 1,00 100,00% 2 84,78 1,98 99,00% 3 56,90 2,95 98,33% 4 43,37 3,87 96,75% 5 35,26 4,76 95,20% 6 30,19 5,56 92,16%19 III Semana Inverno Geofísica
  20. 20. Conclusões da Excursão Inicial • Paralelismo MPI explora independências no algoritmo – Enquanto OpenMP explora independências na codificação • Ou seja, o volume de trabalho para paralelizar um programa seqüencial em OpenMP depende do algoritmo (como MPI) e de detalhes da codificação seqüencial • Ao contrário de OpenMP, paralelismo MPI muda substancialmente o programa, pois requer: – Dividir o trabalho explicitamente – Dividir a memória explicitamente • Entretanto, aplica-se a máquinas de memória central, memória distribuída e clusters20 III Semana Inverno Geofísica
  21. 21. Detalhando MPI21 III Semana Inverno Geofísica
  22. 22. Padrão MPI • Implementa o modelo de troca de mensagens por chamadas a biblioteca de procedimentos padronizada – esconde “detalhes” da comunicação entre processos • Padrão de facto (www.mpi-forum.org) • Construído pela necessidade de portabilidade de programas paralelos, quando haviam múltiplas implementações proprietárias e não padronizadas de bibliotecas de troca de mensagens • Esforço comunitário: – grupos de usuários, acadêmicos e indústria – 1992-1998: MPI-1 e MPI-2 – 2008-...: MPI-3 em elaboração22 III Semana Inverno Geofísica
  23. 23. Compilação de programas MPI • Padrão MPI não define como compilar programas MPI (pois depende do Sistema Operacional) • Implementações de MPI tipicamente fornecem scripts para compilação • Para compilar programa MPI Fortran no LINUX: Use mpif90 (script que invoca f90 com chaves MPI) Aceita demais chaves de compilação de f90 • Para compilar programa MPI C no LINUX: Use mpicc (script que invoca cc com chaves MPI) Aceita demais chaves de compilação de cc23 III Semana Inverno Geofísica
  24. 24. Execução de programas MPI • Padrão MPI não define como executar programas MPI (pois depende do Sistema Operacional) • Implementações de MPI tipicamente fornecem scripts para execução. Na implementação MPICH no Linux: mpirun <argumentos> <executável> • Múltiplos argumentos. Dentre os principais: 1. Número de processos na execução (obrigatório): -np < número de processos> 2. Em que máquinas os processos são criados (opcional, há default): -machinefile <arquivo>24 III Semana Inverno Geofísica
  25. 25. Índice do Padrão MPI 1. Introduction to MPI 1 2. MPI Terms and Conventions 6 3. Point-to-Point Communication 16 4. Collective Communication 91 5. Groups, Contexts and Communicators 132 6. Process Topologies 176 7. MPI Environmental Management 191 8. Profiling Interface 201 Bibliography 207 A. Language Binding 210 MPI Function Index 23025 III Semana Inverno Geofísica
  26. 26. 26 III Semana Inverno Geofísica
  27. 27. Constantes Simbólicas MPI • Implementações de MPI fornecem arquivos com constantes simbólicas • Para incluir constantes simbólicas MPI em programas Fortran: – include “mpif.h”, ou use mpi – Linhas do arquivo mpif.h: INTEGER, PARAMETER :: MPI_SUCCESS=0 INTEGER, PARAMETER :: MPI_COMM_WORLD=90 • Similar em C27 III Semana Inverno Geofísica
  28. 28. MPI: Manejo do Ambiente28 III Semana Inverno Geofísica
  29. 29. Manejo do ambiente • Inicia a computação MPI: C: int MPI_Init (int *argc, char ***argv) Fortran: MPI_INIT (ierr) integer, intent(out) :: ierr • Inscreve o processo na computação MPI • Término ordenado da computação MPI: C: int MPI_Finalize(void) Fortran: MPI_FINALIZE (ierr) integer, intent(out) :: ierr • Ultimo procedimento MPI a invocar • Uso típico: – MPI_Init o mais próximo possível ao primeiro comando do programa – MPI_Finalize é o último comando do programa29 III Semana Inverno Geofísica
  30. 30. Manejo do ambiente • Quantos processos em um comunicador: (size) C: int MPI_Comm_size(MPI_Comm comm, int *size) Fortran: MPI_COMM_SIZE (comm, size, ierr) integer, intent(in) :: comm integer, intent(out) :: size integer, intent(out) :: ierr • Qual é o número deste processo no comunicador: (id) C: int MPI_Comm_rank (MPI_Comm comm, int * id) Fortran: MPI_COMM_RANK (comm, id, ierr) integer, intent(in) :: comm integer, intent(out) :: id integer, intent(out) :: ierr • Tipicamente (em C): MPI_Comm_size(MPI_COMM_WORLD, size); MPI_Comm_rank(MPI_COMM_WORLD, id);30 III Semana Inverno Geofísica
  31. 31. MPI: Comunicação Ponto a Ponto Bloqueante31 III Semana Inverno Geofísica
  32. 32. Comunicação Ponto a Ponto • Processos trocam mensagens contendo dados • Um processo solicita o envio de uma mensagem para outro processo (MPI_SEND) • Outro processo solicita a recepção de uma mensagem do primeiro (MPI_RECV) • Mensagem composta por – Envelope – Dados32 III Semana Inverno Geofísica
  33. 33. Comunicação Ponto a Ponto: Envelope • Envelope da mensagem: – Identificação do comunicador MPI – Identidade (no comunicador MPI) do processo que envia; – Identidade (no comunicador MPI) do processo que recebe; – Tag (inteiro identificador da mensagem)33 III Semana Inverno Geofísica
  34. 34. Comunicação ponto a ponto: Dados • Dados a trafegar: – Os valores: • Endereço da primeira posição de buffer na memória • O buffer é o espaço de posições contíguas de memória que contém: – A seqüência de valores a enviar, ou – Espaço para armazenar os valores recebidos – O tamanho de buffer: • Quantos valores do tipo MPI (não quantos bytes) • Inteiro não negativo, permitindo mensagens vazias – O tipo MPI dos valores comunicados: • Mesmo tipo para todos os valores34 III Semana Inverno Geofísica
  35. 35. Tipos de Dados MPI e Fortran MPI Fortran MPI_INTEGER INTEGER MPI_REAL REAL MPI_DOUBLE_PRECISION DOUBLE PRECISION MPI_COMPLEX COMPLEX MPI_LOGICAL LOGICAL MPI_CHARACTER CHARACTER(1) MPI_BYTE MPI_PACKED35 III Semana Inverno Geofísica
  36. 36. Tipos de Dados MPI e C MPI C MPI_INT signed int MPI_SHORT signed short int MPI_LONG signed long int MPI_UNSIGNED unsigned int MPI_UNSIGNED_SHORT unsigned short int MPI_UNSIGNED_LONG unsigned long int MPI_FLOAT float MPI_DOUBLE double MPI_LONG_DOUBLE long double MPI_CHAR signed char MPI_UNSIGNED_CHAR unsigned char MPI_BYTE MPI_PACKED36 III Semana Inverno Geofísica
  37. 37. Envio Bloqueante de Mensagem MPI_Send (buf, cnt, datatype, dest, tag, comm, ierr) <type>, intent(in) :: buf(:) Primeira posição dos dados a enviar integer, intent(in) :: cnt Quantos dados a enviar (≥0); Size(buf) ≥ cnt; posições contíguas integer, intent(in) :: datatype Tipo MPI dos dados a enviar integer, intent(in) :: dest Número do processo a receber a mensagem (no comunicador) integer, intent(in) :: tag Identificador da mensagem (≥0 e ≤MPI_TAG_UB) integer, intent(in) :: comm Comunicador da mensagem integer, intent(out) :: ierr Código de retorno37 III Semana Inverno Geofísica
  38. 38. Recepção Bloqueante de Mensagem MPI_Recv (buf, cnt, datatype, src, tag, comm, status, ierr)<type>, intent(out) :: buf(:) Primeira posição dos dados a receberinteger, intent(in) :: cnt Tamanho de buf (≥0); recebe ≤ cnt elementos ou reporta “overflow”integer, intent(in) :: datatype Tipo MPI dos dados a receberinteger, intent(in) :: src Número do processo que a mensagem (no comunicador)integer, intent(in) :: tag Identificador da mensagem (≥0 e ≤MPI_TAG_UB)integer, intent(in) :: comm Comunicador da mensageminteger, intent(out) :: Informações sobre a mensagem recebidastatus(MPI_STATUS_SIZE)integer, intent(out) :: ierr Código de retorno38 III Semana Inverno Geofísica
  39. 39. Tamanho da Mensagem • Semântica de cnt: – O padrão afirma que cnt é o número de elementos em bfr, mas: • Em SEND, cnt é a quantidade de dados a enviar; – Logo, size(buf) ≥ cnt; • Em RECV, cnt é o tamanho de buf – o número de elementos recebidos é ≤ cnt39 III Semana Inverno Geofísica
  40. 40. Seleção da Mensagem a Receber • Dentre as mensagens existentes, MPI seleciona a mensagem correspondente a um dado MPI_RECV se e somente se: – O comunicador da mensagem é o mesmo do RECV; – A mensagem é enviada para o processo que emite o RECV; – O tag da mensagem está de acordo com o tag do RECV; – O processo que envia a mensagem está de acordo com o src do RECV • Observe que: – Nenhuma informação sobre os dados é utilizada para escolher a mensagem a receber; – Um processo pode enviar mensagem para ele mesmo.40 III Semana Inverno Geofísica
  41. 41. MPI: Modos de Comunicação41 III Semana Inverno Geofísica
  42. 42. Modos de Comunicação Ponto a Ponto • Os dois principais modos de comunicação ponto a ponto de MPI são: – Comunicação síncrona (synchronous) – Comunicação assíncrona (buffered) – Há outros... • Os dois modos diferem em: – Obrigatoriedade do par SEND-RECV ter sido emitido (sincronização ou não) – O que significa a invocação a SEND ou a RECV42 III Semana Inverno Geofísica
  43. 43. Comunicação Síncrona • MPI copia os dados (e envia a mensagem) diretamente para o bfr do receptor • SEND termina apenas quando o receptor recebe a mensagem (e avisa o emissor) • RECV termina apenas quando os dados estão no próprio bfr • Características: – Mensagem não local no processo que emite o SEND; – Possibilita sincronização, pois SEND termina apenas após a recepção correspondente terminar; – Usa pouca memória (não há buffer intermediário); minimiza cópias43 III Semana Inverno Geofísica
  44. 44. Comunicação Assíncrona • MPI copia bfr do SEND para outro armazém local e envia o novo armazém para o processo destino • SEND termina quando dados do seu próprio bfr forem copiados para o armazém • RECV termina apenas quando os dados estão no próprio bfr • Características: – Mensagem local no processo que emite o SEND; – Não há sincronização (a recepção correspondente não precisa ter começado para o SEND terminar) – Requer mais memória (e cópias) que o modo síncrono44 III Semana Inverno Geofísica
  45. 45. Semântica de MPI_SEND, MPI_RECV • O mesmo MPI_RECV é utilizado para comunicação síncrona e assíncrona – Diferença apenas no SEND • MPI possui rotinas específicas para SEND síncrono e para SEND assíncrono; MPI_SEND não é nenhuma delas • MPI_SEND e MPI_RECV utilizam terceiro modo de comunicação, denominado padrão (“standard”)45 III Semana Inverno Geofísica
  46. 46. Modo Padrão • Uma implementação de MPI é livre para escolher entre comunicação síncrona e assíncrona na implementação de MPI_SEND • Motivo: Para garantir a correção de programas portáteis, não é possível obrigar qualquer sistema a possuir memória suficiente para comunicação assíncrona. • Ao deixar a comunicação síncrona ou assíncrona a critério da implementação, MPI impõe semântica a MPI_SEND e MPI_RECV tal que: • Semântica correta em qualquer dos dois modos • Permite uma implementação escolher, dinamicamente, um dos modos de comunicação dependendo das circunstâncias • Permite que a implementação melhore o desempenho do programa, se há espaço suficiente para comunicação assíncrona • Mantém correção de programas portáteis.46 III Semana Inverno Geofísica
  47. 47. Semântica de MPI_SEND • O MPI_SEND é bloqueante. – Retorna apenas quando os dados e o envelope forem salvos em algum outro lugar – Consequentemente, ao retornar de MPI_SEND, o bfr pode ser re-escrito • O término de MPI_SEND não garante que a mensagem chegou ao destino, mas • O término de MPI_SEND pode requerer o término do MPI_RECV correspondente.47 III Semana Inverno Geofísica
  48. 48. Semântica de MPI_RECV • O MPI_RECV é bloqueante. – Retorna apenas quando os dados e o envelope enviados chegaram ao destino – Consequentemente, ao retornar de MPI_RECV, o bfr contém os dados a receber • O término de MPI_RECV garante que o MPI_SEND correspondente foi iniciado e enviou os dados • O término de MPI_RECV requer o início do MPI_SEND correspondente (mas não garante que o MPI_SEND terminou).48 III Semana Inverno Geofísica
  49. 49. Sumário • A semântica do modo padrão de comunicação MPI não é baseada no sincronismo (ou não) da operação; é baseada no reuso do bfr – MPI_SEND termina apenas quando o bfr pode ser reusado; – MPI_RECV termina apenas quando o bfr foi recebido. • Para garantir a correção de um programa MPI, é necessário: – Garantir que pares MPI_SEND e MPI_RECV correspondentes possam ser executados simultaneamente, ou seja, que nenhum fluxo de execução impeça a execução de um dos dois49 III Semana Inverno Geofísica
  50. 50. Problema Clássico: Deadlock Escreva um programa com dois processos MPI no qual cada processo envia seu número (identidade) no comunicador para o outro processo.50 III Semana Inverno Geofísica
  51. 51. Deadlock Versão 1 program deadlock ! 2 processos!!! implicit none include “mpif.h” integer :: nProc, esteProc, outroProc integer :: ierr integer :: status(MPI_STATUS_SIZE) call MPI_INIT (ierr) call MPI_COMM_SIZE (MPI_COMM_WORLD, nProc, ierr) call MPI_COMM_RANK (MPI_COMM_WORLD, esteProc, ierr) call MPI_RECV (outroProc, 1, MPI_INTEGER, mod(esteProc+1,2), 10, MPI_COMM_WORLD, status, ierr) call MPI_SEND (esteProc, 1, MPI_INTEGER, mod(esteProc+1, 2), 10, MPI_COMM_WORLD, ierr) print *, “este e outro proc =“, esteProc, outroProc call MPI_FINALIZE (ierr) end program deadlock51 III Semana Inverno Geofísica
  52. 52. Erro em Deadlock Versão 1 • Os dois processos esperam eternamente em MPI_RECV, pois os MPI_SEND correspondentes não são executados. • O programa não garante que os pares SEND – RECV correspondentes sejam executados – pois a execução do MPI_SEND pressupõe o término da execução do MPI_RECV anterior.52 III Semana Inverno Geofísica
  53. 53. call MPI_RECV (outroProc, 1, MPI_INTEGER, 1, 10, ...) call MPI_SEND (esteProc , 1, MPI_INTEGER, 1, 10, ...) PROC 0 call MPI_RECV (outroProc, 1, MPI_INTEGER, 0, 10, ...) call MPI_SEND (esteProc , 1, MPI_INTEGER, 0, 10, ...) PROC 153 III Semana Inverno Geofísica
  54. 54. Deadlock Versão 2 (inverte a ordem de SEND e RECV) program deadlock implicit none include “mpif.h” integer :: nProc, esteProc, outroProc integer :: ierr integer :: status(MPI_STATUS_SIZE) call MPI_INIT (ierr) call MPI_COMM_SIZE (MPI_COMM_WORLD, nProc, ierr) call MPI_COMM_RANK (MPI_COMM_WORLD, esteProc, ierr) call MPI_SEND (esteProc, 1, MPI_INTEGER, mod(esteProc+1, 2), 10, MPI_COMM_WORLD, ierr) call MPI_RECV (outroProc, 1, MPI_INTEGER, mod(esteProc+1,2), 10, MPI_COMM_WORLD, status, ierr) print *, “este e outro proc =“, esteProc, outroProc call MPI_FINALIZE (ierr) end program deadlock54 III Semana Inverno Geofísica
  55. 55. Erro em Deadlock Versão 2 • A semântica do par MPI_SEND e MPI_RECV não garante que MPI_SEND seja executado sem que o MPI_RECV correspondente seja emitido. • Os dois processos podem esperam eternamente em MPI_SEND, pois os MPI_RECV correspondentes podem não são executados, caso a implementação MPI escolha utilizar o modo síncrono de comunicação. • O programa não garante que os pares SEND – RECV correspondentes (tag 10) sejam executados – pois a execução do MPI_SEND pode requerer o início da execução do MPI_RECV posterior.55 III Semana Inverno Geofísica
  56. 56. call MPI_SEND (outroProc, 1, MPI_INTEGER, 1, 10, ...) call MPI_RECV (esteProc , 1, MPI_INTEGER, 1, 10, ...) PROC 0 call MPI_SEND (outroProc, 1, MPI_INTEGER, 0, 10, ...) call MPI_RECV (esteProc , 1, MPI_INTEGER, 0, 10, ...) PROC 156 III Semana Inverno Geofísica
  57. 57. Versão sem Deadlock if (esteProc == 0) then call MPI_RECV (outroProc, 1, MPI_INTEGER, mod(esteProc+1,nProc), 10, MPI_COMM_WORLD, status, ierr) call MPI_SEND (esteProc, 1, MPI_INTEGER, mod(esteProc+1, nProc), 20, MPI_COMM_WORLD, ierr) else call MPI_SEND (esteProc, 1, MPI_INTEGER, mod(esteProc+1, nProc), 10, MPI_COMM_WORLD, ierr) call MPI_RECV (outroProc, 1, MPI_INTEGER, mod(esteProc+1,nProc), 20, MPI_COMM_WORLD, status, ierr) end if57 III Semana Inverno Geofísica
  58. 58. Porque versão correta? • Versão correta apenas para 2 processos – Mecanismo conhecido como red-black ordering – Pode ser estendido para pares de processos • O par SEND-RECV com tag 10 é executado “simultaneamente”; não pressupõe nada sobre a forma de comunicação. • O par SEND-RECV com tag 20 também é executado “simultaneamente”; só pressupõe que o par SEND- RECV anterior termina. • Obs: tags 10 e 20 apenas por razões didáticas; os dois tags poderiam ser os mesmos.58 III Semana Inverno Geofísica
  59. 59. call MPI_RECV (outroProc, 1, MPI_INTEGER, 1, 10, ...) call MPI_SEND (esteProc , 1, MPI_INTEGER, 1, 20, ...) PROC 0 call MPI_SEND (esteProc, 1, MPI_INTEGER, 0, 10, ...) call MPI_RECV (outroProc , 1, MPI_INTEGER, 0, 20, ...) PROC 159 III Semana Inverno Geofísica
  60. 60. Sumário • Compilação e Execução de Programas MPI • Comunicador MPI • Manejo do ambiente MPI • Mensagem: Envelope e Dados • Comunicação Ponto a Ponto Bloqueante • Modos de Comunicação: – Síncrona – Assíncrona – Padrão • Deadlock60 III Semana Inverno Geofísica
  61. 61. MPI: Comunicação Ponto a Ponto Não Bloqueante61 III Semana Inverno Geofísica
  62. 62. Para que Comunicação Não Bloqueante? • Para evitar “deadlocks” – SENDs e RECVs bloqueantes geram deadlock • Para permitir simultaneidade entre computação e comunicação – Impedido por comunicações bloqueantes62 III Semana Inverno Geofísica
  63. 63. Modelo de Comunicação Não Bloqueante 1. Processo requisita o início da comunicação invocando Isend ou Irecv 2. MPI inicia a comunicação e retorna controle ao processo 3. Processo continua sua computação enquanto MPI executa a comunicação 4. Quando conveniente, o processo: – Invoca Wait para aguardar o fim da comunicação, ou – Invoca Test para investigar o fim da comunicação63 III Semana Inverno Geofísica
  64. 64. Requisições • Como relacionar as duas partes da comunicação (requisição, investigação) ? – Ou seja, o par (ISEND/IRECV, WAIT/TEST)? – Podem haver múltiplas comunicações pendentes – Logo, múltiplos pares (ISEND/IRECV, WAIT/TEST) • A operação que requer a comunicação retorna um identificador da requisição denominado “request” • A operação que aguarda/investiga o fim da comunicação utiliza, como argumento de entrada, o “request” • Ao término da comunicação, o “request” recebe o valor MPI_REQUEST_NULL64 III Semana Inverno Geofísica
  65. 65. Requisita Envio Não Bloqueante MPI_Isend (buf, cnt, datatype, dest, tag, comm, request, ierr)<type>, intent(in) :: buf(:) Primeira posição dos dados a enviarinteger, intent(in) :: cnt Quantos dados a enviar (≥0); Size(buf) ≥ cntinteger, intent(in) :: datatype Tipo MPI dos dados a enviarinteger, intent(in) :: dest Número do processo a receber a mensagem (no comunicador)integer, intent(in) :: tag Identificador da mensagem (≥0 e ≤MPI_TAG_UB)integer, intent(in) :: comm Comunicador da mensageminteger, intent(out) :: request Identificador da comunicaçãoInteger, intent(out) :: ierr Código de retorno65 III Semana Inverno Geofísica
  66. 66. Requisita Recepção Não Bloqueante MPI_Irecv (buf, cnt, datatype, src, tag, comm, request, ierr)<type>, intent(out) :: buf(:) Primeira posição dos dados a receberinteger, intent(in) :: cnt Tamanho de buf (≥0); recebe ≤ cnt elementos ou reporta “overflow”integer, intent(in) :: datatype Tipo MPI dos dados a receberinteger, intent(in) :: src Número do processo que a mensagem (no comunicador)integer, intent(in) :: tag Identificador da mensagem (≥0 e ≤MPI_TAG_UB)integer, intent(in) :: comm Comunicador da mensageminteger, intent(out) :: request Identificador da comunicaçãointeger, intent(out) :: ierr Código de retorno66 III Semana Inverno Geofísica
  67. 67. Espera Bloqueante do Término da Mensagem MPI_Wait (request, status, ierr) Identificador dainteger, intent(inout) :: request comunicação Informações sobre ainteger, intent(out) :: status(mpi_status_size) comunicaçãointeger, intent(out) :: ierr Código de retorno • Espera até que a mensagem termine • No retorno, request = MPI_REQUEST_NULL67 III Semana Inverno Geofísica
  68. 68. Investigação do Término da Mensagem MPI_Test (request, flag, status, ierr) Identificador dainteger, intent(inout) :: request comunicação Operação completa oulogical, intent(out) :: flag incompleta Informações sobre ainteger, intent(out) :: status(mpi_status_size) comunicaçãointeger, intent(out) :: ierr Código de retorno • Retorna, em flag, se comunicação terminou ou não • Não bloqueante • Se operação completa, request retorna MPI_REQUEST_NULL68 III Semana Inverno Geofísica
  69. 69. Semântica da Comunicação Não Bloqueante• O retorno de IRECV/ISEND indica: – O início da comunicação solicitada – Que buf não pode ser usado/modificado – Nada sobre a comunicação correspondente à solicitada• O retorno de WAIT indica – Término da comunicação solicitada – Que buf já pode ser usado/modificado – Se a comunicação foi solicitada por IRECV, indica que o ISEND correspondente começou – Se a comunicação foi solicitada por ISEND, nada indica sobre o IRECV correspondente• O retorno de TEST com flag=.true. tem a mesma semântica que o retorno de WAIT• O retorno de TEST com flag=.false. Indica: – Que a comunicação não terminou – Que buf ainda não pode ser usado/modificado – Nada sobre a comunicação correspondente III Semana Inverno Geofísica69
  70. 70. Exemplo • Escreva um programa com dois processos MPI no qual cada processo envia seu número (identidade) no comunicador para o outro processo. • A identidade do processo é esteProc • A identidade do outro processo é outroProc70 III Semana Inverno Geofísica
  71. 71. Exemplo (fração do programa) call MPI_IRECV (outroProc, 1, MPI_INTEGER, mod(esteProc+1,2), 10, MPI_COMM_WORLD, request1, ierr) call MPI_ISEND (esteProc, 1, MPI_INTEGER, mod(esteProc+1, 2), 10, MPI_COMM_WORLD, request2, ierr) flag1=.false.; flag2=.false. do if (.not. flag1) call MPI_TEST(request1, flag1, status, ierr) if (.not. flag2) call MPI_TEST(request2, flag2, status, ierr) if (flag1 .and. flag2) exit end do Livre de Deadlock!!!71 III Semana Inverno Geofísica
  72. 72. Outras operações não bloqueantes • Há muitas outras operações • MPI_WAITALL, MPI_WAITANY, MPI_WAITSOME – Aguarda todas, qualquer uma, algumas comunicações • Idem para TEST • Etc...72 III Semana Inverno Geofísica
  73. 73. MPI: Comunicações Coletivas73 III Semana Inverno Geofísica
  74. 74. Comunicações Coletivas • Uma comunicação coletiva envolve múltiplos processos. • Todos os processos do comunicador emitem a mesma operação • O término indica que o processo pode acessar ou alterar o buffer de comunicação • Veremos apenas uma de 16 operações74 III Semana Inverno Geofísica
  75. 75. Comunicações Coletivas: BARREIRA MPI_Barrier (comm, ierr) – Integer, intent(in) :: comm – Integer, intent(out) :: ierr • Todos os processos que invocam MPI_BARRIER são bloqueados até que todos os processos do comunicador invoquem a barreira. • Sincroniza todos os processos do comunicador • Cuidado: garanta que todos os processos no comunicador invoquem a barreira75 III Semana Inverno Geofísica
  76. 76. Sumário MPI • MPI implementa modelo de troca de mensagens • Espaço de endereçamento distintos • Para reduzir memória, é necessário mapear índices e re-escrever o programa • Índice global = índice local + deslocamento • Troca de mensagens bloqueante pode gerar deadlock • Garanta que pares send/recv correspondentes possam ser executados simultaneamente • Outra possibilidade: troca de mensagens não bloqueante76 III Semana Inverno Geofísica

×