5 MPIprogramming
5 MPIprogramming
Objectives
• MPI communicators
• Sample programs
1
Introduction to MPI
2
A very brief history of MPI
3
Basic structure of MPI code
• declare variables
Notes:
4
MPI header files
In Fortran, we type
INCLUDE ‘mpif.h‘
In C, the equivalent is
#include <mpi.h>
5
MPI naming conventions
MPI XXXXX(parameter,...,IERR)
For example,
MPI INIT(IERR)
MPI Xxxxx(parameter,...)
6
MPI subroutines and return values
7
MPI handles
For example,
8
MPI data types
9
Basic MPI data types
10
Communicators
11
Communicators
12
Getting communicator rank
13
Getting communicator size
14
Finalizing MPI
15
hello, world — serial Fortran
PROGRAM helloWorld
hello, world
16
hello, world with MPI
PROGRAM helloWorldMPI
INCLUDE ’mpif.h’
INTEGER IERR
! Initialize MPI environment
CALL MPI_INIT(IERR)
17
hello, world with MPI
hello, world
hello, world
hello, world
hello, world
18
hello, world, the sequel
INCLUDE ’mpif.h’
! Declare variables
INTEGER RANK, SIZE, IERR
19
Running this code on 6 processes could produce
something like:
spiteri@robson:~/test> mpirun -np 6 ./helloWorld2MPI
Process 0 of 6 says, ’hello, world’
Process 2 of 6 says, ’hello, world’
Process 1 of 6 says, ’hello, world’
Process 3 of 6 says, ’hello, world’
Process 4 of 6 says, ’hello, world’
Process 5 of 6 says, ’hello, world’
20
hello, world, the sequel
int main(void)
char greeting[MAX_STRING]; /* String storing message */
int comm_sz; /* Number of processes */
int my_rank; /* My process rank */
/* Start up MPI */
MPI_Init(NULL, NULL);
21
if (my_rank != 0)
/* Create message */
sprintf(greeting, "Greetings from process %d of %d!",
my_rank, comm_sz);
/* Send message to process 0 */
MPI_Send(greeting, strlen(greeting)+1, MPI_CHAR, 0, 0,
MPI_COMM_WORLD);
else
/* Print my message */
printf("Greetings from process %d of %d!\n", my_rank, comm_sz);
for (int q = 1; q < comm_sz; q++)
/* Receive message from process q */
MPI_Recv(greeting, MAX_STRING, MPI_CHAR, q,
0, MPI_COMM_WORLD, MPI_STATUS_IGNORE);
/* Print message from process q */
printf("%s\n", greeting);
return 0;
/* main */
22
hello, world, the sequel
will be
23
hello, world, the sequel
24
hello, world, the sequel
25
hello, world, the sequel
26
hello, world, the sequel
27
hello, world, the sequel
28
hello, world, the sequel
29
hello, world, the sequel
30
hello, world, the sequel
31
hello, world, the sequel
32
Sample Program: Trapezoidal Rule
33
Sample Program: Trapezoidal Rule
34
Sample Program: Trapezoidal Rule
b−a
∆x = .
n
Let xi = a + i∆x, i = 0, 1, . . . , n.
n
∆x X
Tn = (f (xi−1) + f (xi))
2 i=1
" n−1
#
f (a) + f (b) X
= ∆x + f (xi) .
2 i=1
35
Sample Program: Trapezoidal Rule
/* input a, b, n */
dx = (b-a)/n;
approx = (f(a)+f(b))/2;
for (i = 1; i <= n-1; i++){
x_i = a + i*dx;
approx += f(x_i);
}
approx = dx*approx;
36
Sample Program: Trapezoidal Rule
37
Sample Program: Trapezoidal Rule
/* File: mpi_trap1.c
* Purpose: Use MPI to implement a parallel version of the trapezoidal
* rule. In this version the endpoints of the interval and
* the number of trapezoids are hardwired.
*
* Input: None.
* Output: Estimate of the integral from a to b of f(x)
* using the trapezoidal rule and n trapezoids.
*
* Compile: mpicc -g -Wall -o mpi_trap1 mpi_trap1.c
* Run: mpiexec -n <number of processes> ./mpi_trap1
*
* Algorithm:
* 1. Each process calculates "its" interval of
* integration.
* 2. Each process estimates the integral of f(x)
* over its interval using the trapezoidal rule.
* 3a. Each process != 0 sends its integral to 0.
* 3b. Process 0 sums the calculations received from
* the individual processes and prints the result.
*
* Note: f(x), a, b, and n are all hardwired.
*
* IPP: Section 3.2.2 (pp. 96 and ff.)
*/
#include <stdio.h>
38
/* Function we’re integrating */
double f(double x);
int main(void) {
int my_rank, comm_sz, n = 1024, local_n;
double a = 0.0, b = 3.0, dx, local_a, local_b;
double local_int, total_int;
int source;
39
total_int += local_int;
}
}
return 0;
} /* main */
/*------------------------------------------------------------------
* Function: Trap
* Purpose: Serial function for estimating a definite integral
* using the trapezoidal rule
* Input args: left_endpt
* right_endpt
* trap_count
* base_len
* Return val: Trapezoidal rule estimate of integral from
* left_endpt to right_endpt using trap_count
* trapezoids
*/
double Trap(
double left_endpt /* in */,
double right_endpt /* in */,
int trap_count /* in */,
double base_len /* in */) {
double estimate, x;
int i;
40
estimate = (f(left_endpt) + f(right_endpt))/2.0;
for (i = 1; i <= trap_count-1; i++) {
x = left_endpt + i*base_len;
estimate += f(x);
}
estimate = estimate*base_len;
return estimate;
} /* Trap */
/*------------------------------------------------------------------
* Function: f
* Purpose: Compute value of function to be integrated
* Input args: x
*/
double f(double x) {
return x*x;
} /* f */
41
Summary
42