Главная страница

Программирование для многопроцессорных систем в стандарте MPI - Шпаковский Г.И., Серикова Н.В.. Программирование для многопроцессорных систем в стандарте MPI -. Организация вычислений в многопроцессорных системах


Скачать 1.61 Mb.
НазваниеОрганизация вычислений в многопроцессорных системах
АнкорПрограммирование для многопроцессорных систем в стандарте MPI - Шпаковский Г.И., Серикова Н.В..pdf
Дата15.03.2018
Размер1.61 Mb.
Формат файлаpdf
Имя файлаПрограммирование для многопроцессорных систем в стандарте MPI - .pdf
ТипКонтрольные вопросы
#16702
КатегорияИнформатика. Вычислительная техника
страница18 из 26
1   ...   14   15   16   17   18   19   20   21   ...   26
Глава 11. ОБРАБОТКА ИСКЛЮЧЕНИЙ И ОТЛАДКА
11.1. ОБРАБОТКА ИСКЛЮЧЕНИЙ
Реализация MPI может обрабатывать некоторые ошибки, которые возникают при выполнении вызовов MPI. Это могут быть ошибки, ко- торые генерируют исключения или прерывания, например, ошибки для операций с плавающей точкой или при нарушении доступа. Набор ошибок, которые корректно обрабатываются MPI, зависит от реализа- ции. Каждая такая ошибка генерирует исключение MPI.
Пользователь может связывать обработчик ошибок с коммуника- тором. Вновь созданный коммуникатор наследует обработчик оши- бок, который связан с “родительским” коммуникатором. В частности, пользователь может определить “глобальный” обработчик ошибок для всех коммуникаторов, связывая этот обработчик с коммуникатором
MPI_COMM_WORLD
сразу после инициализации.
В MPI доступны предопределенные обработчики ошибок:
MPI_ERRORS_ARE_FATAL – обработчик, который после вызо- ва прерывает работу программы на всех процессах. Это имеет тот же эффект, как если бы процессом, который запустил обработчик,
был вызван MPI_ABORT.
MPI_ERRORS_RETURN – обработчик не делает ничего, кроме представления кода ошибки пользователю.
Реализации могут обеспечивать дополнительные обработчики ошибок, программисты также могут написать свои собственные об- работчики ошибок.
Обработчик ошибок MPI_ERRORS_ARE_FATAL связан по умолчанию с MPI_COMM_WORLD после его инициализации. Та- ким образом, если пользователь не желает управлять обработкой ошибок самостоятельно, то каждая ошибка в MPI обрабатывается как фатальная. Так как все вызовы MPI возвращают код ошибки, пользо- ватель может работать с ошибками в головной программе, используя возвращенные вызовами MPI коды и выполняя подходящую програм- му восстановления при неуспешном вызове. В этом случае будет ис- пользоваться обработчик ошибок MPI_ERRORS_RETURN. Обычно

226
более удобно и более эффективно не проверять ошибки после каждого вызова, а иметь специализированный обработчик ошибок.
После того, как ошибка обнаружена, состояние MPI является не- определенным. Это означает, что даже если используется определен- ный пользователем обработчик ошибок или обработчик
MPI_ERRORS_RETURN
, не обязательно, что пользователю будет разрешено продолжить использовать MPI после того, как ошибка оп- ределена. Цель таких обработчиков состоит в том, чтобы пользователь получил определенное им сообщение об ошибке и предпринял дейст- вия, не относящиеся к MPI (такие, как очистка буферов ввода/вывода) перед выходом из программы. Реализация MPI допускает продолже- ние работы приложения после возникновения ошибки, но не требует, чтобы так было всегда. Обработчик ошибок MPI является скрытым объектом, связанным с дескриптором. ПроцедурыMPI обеспечивают создание новых обработчиков ошибок, связывают обработчики оши- бок с коммуникаторами и проверяют, какой обработчик ошибок свя- зан с коммуникатором. Существует несколько функций MPI, обеспе- чивающих обработку ошибок.
MPI_ERRHANDLER_CREATE( function, errhandler )
IN function установленная пользователем процедура обработки ошибок
OUT errhandler MPI обработчик ошибок (дескриптор) int MPI_Errhandler_create(MPI_Handler_function *function,
MPI_Errhandler *errhandler)
MPI_ERRHANDLER_CREATE(FUNCTION, ERRHANDLER, IERROR)
EXTERNAL FUNCTION
INTEGER ERRHANDLER, IERROR
Функция MPI_ERRHANDLER_CREATE регистрирует процеду- ру пользователя в качестве обработчика исключений. Возвращает в
errhandler
дескриптор зарегистрированного обработчика исключе- ний. В языке C процедура пользователя должна быть функцией типа
MPI_Handler_function
, которая определяется как:
typedef void (MPI_Handler_function) (MPI_Comm *, int *, ...);
Первый аргумент является идентификатором используемого ком- муникатора, второй является кодом ошибки, который будет возвра- щен процедурой MPI,выявившей ошибку. Если процедура возвратила
MPI_ERR_IN_STATUS
, то это значит, что код ошибки возвращен в статусный объект обращения, которое запустило обработчик ошибок.

227
Остающиеся аргументы есть аргументы “stdargs”, чьи номер и значе- ние являются зависимыми от реализации. В реализации должны быть ясно документированы эти аргументы. Адреса используются так, что- бы обработчик мог быть написан на языке Fortran.
MPI_ERRHANDLER_SET( comm, errhandler )
IN comm
Коммуникатор для установки обработчика ошибок (дескриптор)
IN errhandler новый обработчик ошибок для коммуникатора (дескриптор) int MPI_Errhandler_set(MPI_Comm comm, MPI_Errhandler errhandler)
MPI_ERRHANDLER_SET(COMM, ERRHANDLER, IERROR)
INTEGER COMM, ERRHANDLER, IERROR
Функция MPI_ERRHANDLER_SET связывает новый обработчик ошибок errorhandler с коммуникатором comm на вызывающем про- цессе. Обработчик ошибок всегда связан с коммуникатором.
MPI_ERRHANDLER_GET( comm, errhandler )
IN comm коммуникатор, из которого получен обработчик ошибок
(дескриптор)
OUT errhandler
MPI обработчик ошибок, связанный с коммуникатором (де- скриптор) int MPI_Errhandler_get(MPI_Comm comm, MPI_Errhandler *errhandler)
MPI_ERRHANDLER_GET(COMM, ERRHANDLER, IERROR)
INTEGER COMM, ERRHANDLER, IERROR
Функция MPI_ERRHANDLER_GET возвращает в errhandler де- скриптор обработчика ошибок, связанного с коммуникатором comm.
Пример: библиотечная функция может записать на входной точке те- кущий обработчик ошибок для коммуникатора, затем установить соб- ственный частный обработчик ошибок для этого коммуникатора и восстановить перед выходом предыдущий обработчик ошибок.
MPI_ERRHANDLER_FREE( errhandler )
INOUT errhandler MPI обработчик ошибок (дескриптор) int MPI_Errhandler_free(MPI_Errhandler *errhandler)
MPI_ERRHANDLER_FREE(ERRHANDLER, IERROR)
INTEGER ERRHANDLER, IERROR void MPI::Errhandler::Free()

228
Эта функция маркирует обработчик ошибок, связанный с
errhandler
,дляудаления и устанавливает для errhandler значение
MPI_ERRHANDLER_NULL
. Обработчик ошибок будет удален по- сле того, как все коммуникаторы, связанные с ним, будут удалены.
MPI_ERROR_STRING
( errorcode, string, resultlen )
IN errorcode код ошибки, возвращаемый процедурой MPI
OUT string текст, соответствующий errorcode
OUT resultlen длина (в печатных знаках) результата, возвращаемого в string
int MPI_Error_string(int errorcode, char *string, int *resultlen)
MPI_ERROR_STRING(ERRORCODE, STRING, RESULTLEN, IERROR)
INTEGER ERRORCODE, RESULTLEN, IERROR
CHARACTER*(*) STRING void MPI::Get_error_string (int errorcode, char* name, int& resulten)
Функция MPI_ERROR_STRING возвращает текст ошибки, свя- занный с кодом или классом ошибки. Аргумент string обязан иметь длину не менее MAX_ERROR_STRING знаков. Число фактически записанных символов возвращается в выходном аргументе resultlen.
Коды ошибок, возвращаемых MPI, приведены в реализации MPI
(за исключением MPI_SUCCESS). Это сделано для того, чтобы по- зволить реализации представить как можно больше информации об ошибках (для использования с MPI_ERROR_STRING).
Чтобы приложения могли интерпретировать код ошибки, проце- дура MPI_ERROR_CLASS преобразует код любой ошибки в один из кодов небольшого набора кодов стандартных ошибок, названный
классом ошибок.
Классы ошибок являются подмножеством кодов ошибок: функция
MPI может возвращать номер класса ошибки, а функция
MPI_ERROR_STRING
может использоваться, чтобы вычислить строку ошибки, связанную с классом ошибки.
Коды ошибок удовлетворяют выражению:
0 = MPI_SUCCESS < MPI_ERR_... ≤ MPI_ERR_LASTCODE.
MPI_ERROR_CLASS
( errorcode, errorclass )
IN errorcode код ошибки, возвращаемый процедурой MPI
OUT errorclass класс ошибки, связаный с errorcode int MPI_Error_class(int errorcode, int *errorclass)

229
MPI_ERROR_CLASS(ERRORCODE, ERRORCLASS, IERROR)
INTEGER ERRORCODE, ERRORCLASS, IERROR int MPI::Get_error_class(int errorcode)
Функция MPI_ERROR_CLASS отображает код каждой стандарт- ной ошибки (класс ошибки) на себя.
Правильные классы ошибок включают:
MPI_SUCCESS
Ошибки нет
MPI_ERR_BUFFER
Неправильный указатель буфера
MPI_ERR_COUNT
Неверное количество аргумента
MPI_ERR_TYPE
Неправильный тип аргумента
MPI_ERR_TAG
Неправильный тэг аргумента
MPI_ERR_COMM
Неправильный коммуникатор
MPI_ERR_RANK
Неправильный номер
MPI_ERR_REQUEST
Неверный запрос (дескриптор)
MPI_ERR_ROOT
Неверный корневой идентификатор
MPI_ERR_GROUP
Неправильная группа
MPI_ERR_OP
Неправильная операция
MPI_ERR_TOPOLOGY
Неверная топология
MPI_ERR_DIMS
Неправильная размерность аргумента
MPI_ERR_ARG
Ошибка аргумента некоторого другого типа
MPI_ERR_UNKNOWN Неизвестная ошибка
MPI_ERR_TRUNCATE Неправильное округление
MPI_ERR_OTHER
Известная ошибка не из этого списка
MPI_ERR_INTERN
Внутренняя ошибка реализации MPI
MPI_ERR_IN_STATUS Неправильный код статуса
MPI_ERR_PENDING
Зависший запрос
MPI_ERR_LASTCODE Последний код в списке
11.2. ОТЛАДКА ПАРАЛЛЕЛЬНЫХ ПРИЛОЖЕНИЙ
Средства отладки являются необходимой принадлежностью лю- бой системы программирования. Отладчик должен позволять: запус- тить программу; остановить программу в заданной точке и обеспечить в случае необходимости пошаговый просмотр программы; просмот- реть значения нужных переменных; изменить некоторые части про- граммы.
Для реализации этих функций существуют несколько общеизвест- ных возможностей отладки:
• Трассировка отлаживаемой программы
• Использование последовательных отладчиков

230
• Использование псевдопараллельных отладчиков
• Использование полноценных параллельных отладчиков
Большой срок существования ОС Unix и систем на ее основе при- вели к тому, что состав средств параллельной отладки для них богаче, чем для Windows NT, поэтому далее рассматриваются в основном средства отладки для систем на базе Unix.
11.2.1. Трассировка
Как и при обычной отладке, чтобы отследить последовательность событий в программе, необходимо выводить соответствующие сооб- щения. Трасса – журнал событий, произошедших во время выполне- ния программы. Для трассировки в текст программы вставляются операторы, которые позволяют получить временной срез – состояние всех процессов программы в некоторый фиксированный момент вре- мени, выводимый на экран дисплея или на печать. Для параллельных приложений необходимо идентифицировать сообщения номером про- цесса, пославшего его. Это делается непосредственным помещением номера в сообщение трассировки.
В программе для вычисления значения
π на языке С (параграф 1.5) это может быть, например, сделано так:
#include "mpi.h"
#include int main ( int argc, char *argv[ ] )
{ int n, myid, numprocs, i; double PI25DT
= 3.141592653589793238462643; double mypi, pi, h, sum, x;
MPI_Init(&argc, &argv);
MPI_Comm_size(MPI_COMM_WORLD, &numprocs);
MPI_Comm_rank(MPI_COMM_WORLD,&myid);
printf ("begin process %d /n",myid);
while (1)
{ if (myid == 0) { printf ("Enter the number of intervals: (0 quits) "); scanf ("%d", &n);
}
MPI_Bcast(&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
printf (" process %d recieve n /n",myid);
if (n == 0) break; else { h
= 1.0/ (double) n; sum
= 0.0;

231
for (i
= myid +1; i <= n; i+= numprocs) { x
= h * ( (double)i – 0.5); sum += (4.0 / (1.0 + x*x));
} mypi = h * sum;
printf (" mypi in process %d = %f /n",myid,mypi);
MPI_Reduce(&mypi, &pi, 1, MPI_DOUBLE, MPI_SUM, 0,
MPI_COMM_WORLD); if (myid == 0) printf ("pi is approximately %.16f. Error is %.16f\n", pi, fabs(pi – PI25DT));
}
}
MPI_Finalize(); return 0;
}
Каждый процесс отмечает начало работы, получение переменной
n
и вычисление частичной суммы. Эти операции в программе выде- лены жирным шрифтом. В результате будет получена трассировка программы, анализ которой позволит найти ошибку.
11.2.2. Использование последовательных отладчиков
Параллельная программа может содержать различные исполняе- мые файлы. Этот стиль параллельного программирования называется
MPMD (множество программ при множестве данных). Во многих случаях программу MPMD можно преобразовать в программу SPMD
(одна программа при множестве данных), которая использует номер процесса для вызова различных процедур. Это облегчает старт парал- лельных программ и их отладку, поскольку тексты процессов стано- вятся идентичными. Для таких программ часто достаточно отладить единственный процесс, обычно процесс 0. Такая отладка производит- ся обычными отладчиками, например, отладчиками dbx, gdb, xdbx для
Unix или обычным отладчиком msdev studio для Windows.
В Unix существует возможность запустить один из процессов с помощью обычного отладчика. Например, команда: mpirun -dbg= -np 2 program запускает program на двух машинах, но отладчик работает только на одной, а, именно, на хост машине.
Часто удобно запускать отладчик, когда в программе возникает ошибка. Если mpich сконфигурирован с опцией -mpedbg, то это вы-

232
зовет попытку mpich запустить отладчик (обычно dbx или gdb), когда возникает ошибка. Команда может, например, выглядеть следующим образом: mpirun –np 4 a.out -mpedbg
Если преобразование программы MPMD в SPMD невозможно или принципиально необходимо отлаживать одновременно несколько вет- вей (пусть идентичных по тексту), то в этом случае нельзя для за- пуска программ использовать mpirun. Вместо этого можно запустить процессы вручную, каждый под управлением обычного отладчика.
Опишем возможность параллельной отладки двух процессов про- извольной параллельной программы program для ОС Windows.
Для организации параллельной отладки создадим два файла с расширением bat, в которых произведем установку необходимых пе- ременных окружения для запуска приложений вручную [1] и вызов msdev studio. Файлы могут выглядеть следующим образом:
Первый файл:
Второй файл:
set MPICH_JOBID=parallel.2000
set MPICH_JOBID=parallel.2000
rem номер процесса = 0
rem номер процесса = 1
set MPICH_IPROC=0
set MPICH_IPROC=1
rem всего 2 процесса rem всего 2 процесса set MPICH_NPROC=2
set MPICH_NPROC=2
set MPICH_ROOT=parallel:12345
set MPICH_ROOT=parallel:12345
msdev program.exe msdev program.exe
Из командной строки (command prompt) запускаем файл номер один. В результате его работы запустится msdev studio с программой
program
и номером процесса, равным 0. Аналогично из другой ко- мандной строки (second command prompt) запускаем файл номер два.
Запускается еще раз msdev studio с программой program и номером процесса, равным 1. Затем вызываем в обоих окнах отладчик msdev.
Переключаясь между окнами, можно шаг за шагом выполнять оба процесса. При этом имеем все необходимые возможности отладки: выполнение по шагам, установки точек прерываний, просмотр необ- ходимых переменных и т. д.
11.2.3. Псевдопараллельный отладчик
Устройство ADI ch_p4mpd в mpich содержит “параллельный от- ладчик”, который состоит просто из нескольких копий отладчика gdb и механизма перенаправления stdin. Команда mpigdb является верси-

233
ей mpirun, оторая запускает каждый процесс под управлением gdb и управляет stdin для gdb. Команда `z' позволяет направить ввод с тер- минала в определенный процесс или разослать его всем процессам.
Продемонстрируем это запуском просраммы cpi на языке Си для вы- числения числа π под управлением простого отладчика: donner% mpigdb -np 5 cpi # по умолчанию вывод от всех
(mpigdb)
b 29 # задать точку останова для всех
0-4: Breakpoint 1 at 0x8049e93: file cpi.c, line 29.
(mpigdb
) r # запустить все 0-4:
Starting program:/home/lusk/mpich/examples/basic/cpi
0: Breakpoint 1, main (argc=1, argv=0xbffffa84) at cpi.c:29 1-4: Breakpoint 1, main (argc=1, argv=0xbffffa74) at cpi.c:29 0-4: 29 n = 0; # все достигли точки останова
(mpigdb)
n # пошаговый режим для всех
0: 38 if (n==0) n=100; else n=0;
1-4: 42 MPI_Bcast (&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
(mpigdb)
z 0 # stdin только для процесса 0
(mpigdb)
n # пошаговый режим процесса 0 0: 40 startwtime = MPI_Wtime ();
(mpigdb)
n # до останова
0: 42 MPI_Bcast (&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
(mpigdb)
z # stdin возвращен для всех процесов
(mpigdb
) n # пошаговый режим для всех до
# интересующего места
…..
(mpigdb
) n
0-4: 52 x = h * ( (double)i -0.5);
(mpigdb
) p x # вывод от всех процессов
0: $1 = 0.0050000000000000001 # значение x процесса 0 1: $1 = 0.014999999999999999 # значение x процесса 1 2: $1 = 0.0250000000000000001 # значение x процесса 2 3: $1 = 0.0350000000000000003 # значение x процесса 3 4: $1 = 0.044999999999999998 # значение x процесса 4
(mpigdb)
c # продолжить все
0: pi is approximately 3.141600986923, Error is 0.000008333333 0-4 Program exited normally.
(mpigdb)
q # выход donner%
Если отлаживаемый процесс зависает (нет приглашения mpigdb) из-за ожидания текущим процессом действий другого процесса, ctrl-C вызовет меню, позволяющее переключать процессы. mpigdb не так развит, как параллельный отладчик TotalView, но часто полезен и свободно распространяется с mpich.

234
11.2.4. Отладка программ MPI с помощью TotalView
Коммерческий отладчик TotalView (TV)является переносимым отладчиком для параллельных программ [26]. TotalView – единствен- ный встроенный высокоуровневый отладчик оконного типа, специ- ально спроектированный для современных распределенных многоза- дачных систем. TotalView воспринимает множество реализаций MPI, включая mpich. С помощью TV разработчики способны быстро и точ- но отладить приложения с многими процессами, потоками и процес- сорами. TV имеет следующие возможности:
• Процессы и потоки могут быть легко запущены, остановлены, пе- резапущены, просмотрены и удалены.
• Пользователь может легко подключиться к любому процессу в системе простым щелчком мыши. Точки останова легко управля- ются и изменяются.
• Программа может быть исправлена «на лету», поэтому различные сценарии исполнения проверяются быстро и без перекомпиляции.
• Множественные процессы на множественных процессорах могут быть сгруппированы, и когда один процесс достигает точки оста- нова, все сгруппированные процессы будут остановлены. Это мо- жет существенно помочь при отладке распределенных систем, по- строенных по принципу клиент-сервер.
• Распределенная архитектура TV позволяет отлаживать удаленные программы на всей сети.
Для реализации указанных возможностей в TV имеется три окна:
• Root Window – корневое окно,
• Process Window – окно процесса,
• Variable Window – вспомогательное окно.
Root Window дает обзор состояния выполняемой программы. Его также можно использовать как навигационный инструмент. Это окно появляется при запуске TV. Окно имеет следующие четыре выделен- ные страницы:
1. Attached (подключенные процессы). Показывает список всех от- лаживаемых процессов и нитей.
2. Unattached (неподключенные процессы). Показывает процессы, над которыми TV имеет контроль. Если нельзя подключиться к какому-то процессу, например, нельзя подключиться к процессу
TV, то TV изображает этот процесс серым.

235 3. Groups (группы). Представляет список групп, используемых вы- полняемой программой.
4. Log (регистрация). Окно отображает собранную отладочную ин- формацию о процессе и потоке внутри этого процесса. Панели внутри этого окна показывают трассу стека, границу стека и код для избранной нити. В этом окне в основном и затрачивается ос- новная часть времени отладки.
Process Window
имеет пять информационных панелей:
1. Source Pane (панель исходного кода). Эта панель содержит исход- ный код. Левый край этой панели, называемый областью поля тэ- га, показывает номера строк и иконки, указывающие определен- ные свойства программы. Можно разместить точку останова на любой строке программы. При этом TV заменяет номер строки на иконку STOP. Стрелка в поле тэгов указывает текущее положение программного счетчика.
2. Threads Pane (панель нитей) – показывает список нитей, которые существуют в процессе. Когда выбирается некоторая нить в этом процессе, TV изменяет содержимое Stack Trace Pane, Stack Frame
Pane и Source Pane, показывая информацию по этой нити.
3. Stack Trace Pane (панель трассы стека) показывает стек вызова процедур, которые выполняет выделенная нить.
4. Stack Frame Pane (панель фрейма стека) показывает функцио- нальные параметры, локальные переменные и регистры для из- бранного фрейма стека. Информация, представляемая панелями
Stack Trace и Stack Frame, отражает состояние процесса на момент его последней остановки. Соответственно, эта информация не кор- ректируется во время выполнения нити.
5. Action Points Pane (панель активных точек) показывает список точек останова, точек вычислений и точек наблюдения за процес- сом.
Variable Window
(переменное окно) содержит список адресов, типов данных, значения локальных переменных, регистров или гло- бальных переменных. Окно также показывает значения, хранимые в памяти.
КОНТРОЛЬНЫЕ ВОПРОСЫ К ГЛАВЕ 11
Контрольные вопросы к 11.1
1.
Что такое ошибки времени исполнения?
2.
Какие предопределенные обработчики ошибок доступны в MPI?

236 3.
Опишите возможности предопределенных обработчиков ошибок.
4.
Какие функции используются для создания новых обработчиков ошибок?
5.
Что такое классы ошибок?
Контрольные вопросы к 11.2
1.
Назовите основные функции отладчика.
2.
Какие способы отладки параллельных приложений используются на прак- тике?
3.
Что такое трассировка?
4.
Как использовать последовательный отладчик для параллельных приложе- ний?
5.
Как можно использовать последовательный отладчик для отладки не- скольких параллельных процессов, выполняемых под Windows NT?
6.
Что такое псевдопараллельные отладчики и как они используются?
7.
Опишите возможности параллельного отладчика программ MPI TotalView.
1   ...   14   15   16   17   18   19   20   21   ...   26


написать администратору сайта