Слайд 1Разработка параллельных приложений для многоядерных систем
С.В. Ковальчук
НИИ Наукоемких компьютерных технологий, СПбГУ
ИТМО
Слайд 2НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Используемые средства
Intel C++ Compiler
Оптимизирующий компилятор
OpenMP, Intel
Threading Building Blocks
Средства распараллеливания для систем с общей памятью
Слайд 3НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Intel C++ Compiler
Архитектуры процессоров
IA-32, x86-64 (Intel
64 and AMD64), IA-64, Xscale
Операционные системы
Microsoft Windows, Linux, Mac OS
Основные возможности
Высокоуровневая оптимизация
Межпроцедурная оптимизация
Автоматическое распараллеливание кода:
Векторизация
Разделение циклов по нескольким нитям
Профилирующая оптимизация
Интеграция с VisualStudio
Слайд 4НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
OpenMP
Распараллеливание на системах с общей памятью
Стандарт
для языков C/С++, Fortran
Использование директив для распараллелива
Поддержка компиляторами Intel, Microsoft, GCC и т.п.
Расширение для разделенной памяти
Cluster OpenMP
Слайд 5НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Преимущества OpenMP
Поэтапное (инкрементальное) распараллеливание
Можно распараллеливать последовательные
программы поэтапно, не меняя их структуру
Единственность разрабатываемого кода
Нет необходимости поддерживать последовательный и параллельный вариант программы, поскольку директивы игнорируются обычными компиляторами (в общем случае)
Эффективность
Учет и использование возможностей систем с общей памятью
Стандартизованность (переносимость), поддержка в наиболее распространенных языках (C/C++, Fortran) и платформах (Windows, Unix)
Слайд 6НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Принцип организации параллелизма
Использование потоков (общее адресное
пространство)
Пульсирующий (“вилочный”, fork-join) параллелизм
Слайд 7НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Состав библиотеки
Набор директив компилятора
#pragma omp
<параметры>
Библиотека функций
omp_...()
Набор переменных окружения
Слайд 8НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Использование OpenMP
Использование директивы parallel
#include
main () {
int nthreads, tid;
#pragma omp parallel private(nthreads, tid)
{
tid = omp_get_thread_num();
printf("Hello World from thread = %d\n", tid);
if (tid == 0) {
nthreads = omp_get_num_threads();
printf("Number of threads = %d\n", nthreads);
}
}
}
Слайд 9НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Способы распараллеливания
Распараллеливание цикла
#pragma omp for
Распараллеливание секциями
#pragma
omp sections
{
#pragma omp section
{
...
}
#pragma omp section
{
...
}
}
Выполнение кода одним потоком
#pragma omp master
#pragma omp single
Слайд 10НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Расписание (schedule)
Распределение итераций в директиве for
регулируется параметром (clause) schedule
static – итерации делятся на блоки по chunk итераций и статически разделяются между потоками; если параметр chunk не определен, итерации делятся между потоками равномерно и непрерывно
dynamic – распределение итерационных блоков осуществляется динамически (по умолчанию chunk=1)
guided – размер итерационного блока уменьшается экспоненциально при каждом распределении; chunk определяет минимальный размер блока (по умолчанию chunk=1)
runtime – правило распределения определяется переменной OMP_SCHEDULE (при использовании runtime параметр chunk задаваться не должен)
Слайд 11НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Задача
Нахождение суммы тригонометрического ряда
double summ =
0;
for (int k = 0; k < N; k++)
{
double ind = k;
summ += ((k & 1) ? -1 : 1) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind)) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind));
}
}
Слайд 12НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Реализация распараллеливания
Добавление директивы OpenMP
double summ =
0;
#pragma omp parallel for
for (int k = 0; k < N; k++)
{
double ind = k;
summ += ((k & 1) ? -1 : 1) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind)) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind));
}
}
Слайд 13НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Организация синхронной работы потоков
Параллельный доступ к
переменным
double summ = 0;
#pragma omp parallel for reduction (+:summ)
for (int k = 0; k < N; k++)
{
double ind = k;
summ += ((k & 1) ? -1 : 1) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind)) *
(sin(ind*(ind + 1)) - cos(ind)*sin(ind*ind)) /
(cos(ind*(1 - ind)) - 2*sin(ind)*sin(ind*ind));
}
}
Слайд 14НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Intel Threading Building Blocks
Высокоуровневая библиотека для
разработки параллельных программ для систем с общей памятью
Реализована на языке C++ в форме классов и шаблонов
Поддерживаемые ОС: Microsoft Windows, Linux, Mac OS
Слайд 15НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Возможности Intel TBB
Решение типичных задач параллельного
программирования
распараллеливание циклов с известным числом повторений;
распараллеливание циклов с известным числом повторений с редукции;
распараллеливание циклов с условием;
распараллеливание рекурсии.
Кроме того, содержит
потокобезопасные контейнеры;
аллокаторы, операторы выделения динамической памяти;
примитивы синхронизации.
Слайд 16НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Пример кода с использованием Intel TBB
int
main() {
task_scheduler_init init;
string str[N] = { string(”a”), string(”b”) };
for (size_t i = 2; i < N; ++i)
str[i] = str[i-1]+str[i-2];
string &to_scan = str[N-1];
size_t *max = new size_t[to_scan.size()];
size_t *pos = new size_t[to_scan.size()];
parallel_for(
blocked_range(0, to_scan.size(), 100),
SubStringFinder( to_scan, max, pos ) );
for (size_t I = 0; I < to_scan.size(); ++i)
cout<<” ”< return 0;
}
Слайд 17НИИ Наукоемких компьютерных технологий, СПбГУ ИТМО
Ссылки
Intel
http://www.intel.com/
OpenMP
http://www.openmp.org/
Intel TBB
http://threadingbuildingblocks.org/