内容简介
本书是一本学习 OpenMP 编译原理和实现技术的入门级教材。内容分成三篇,第一篇是
并行计算及 OpenMP 编程的基础内容,第二篇是 OpenMP 编译及其运行环境,第三篇是实践
内容。在第二篇中,以一般编译器常见结构为主线,通过结合详细的 OMPi 源代码分析向读者
介绍 OpenMP 编译器的工作原理及其实现技术,具体包括词法分析、语法分析、AST 树的结构、
AST 树的生成及相关操作、OpenMP 编译制导指令的代码变换、OpenMP 线程与 OS 线程库的
接口、运行环境等细节。OpenMP 编译制导指令的变换是 OpenMP 编译的核心内容,需要将
OpenMP 制导指令的语义功能利用操作系统的线程库来实现,分成并行域管理问题、任务分担
和同步问题、变量数据环境问题三个核心内容。第三篇的四章给出了常见编译器、性能测试工
具以及 OMPi 源代码的框架分析。
本书是国内第一本关于 OpenMP 编译器工作原理和实现细节的尝试。读者对象是研究
OpenMP 编译技术的研究人员和高校师生,作为入门的初步阅读材料,也可以作为研究生和高
年级本科生学习并行语言编译技术相关课程的辅助参考书。由于作者才疏学浅,书中难免不少
错漏,欢迎读者指正。联系邮件:lqm@szu.edu.cn。
1
前言
编写《OpenMP 编译原理及实现技术》教材是深圳大学“计算机科学与技术国家特色专业
建设点”的建设内容之一。该教材和相应课程的设计目的有三点:衔接本科《编译原理》课程、
扩展 OpenMP 并行语言编译的知识、增强学生的动手实践和编程能力,书中以 OpenMP 的一
个开源编译器——OMPi 作为分析对象,做到理论与实践紧密结合,为进一步学习和研究打下
必要的基础。
本书读者虽然不要求对编译原理有深入理解,但是还是需要先对编译有初步认识、具备基
本概念。对于关心实现技术的读者,建议下载 OMPi 1.0.0 的源码并进行同步阅读。
书中第一篇基础部分共两章,分别讲述并行平台和 OpenMP C 编程作为预备知识。对于
没有接触过并行计算技术的读者可以作为一个补充阅读,第 2 章的 OpenMP 编程基本上将相
关的语言要素作了全面的介绍,没有特殊需要一般不再需要去阅读 OpenMP 的标准。
第二篇编译部分共八章,主要讲述 OpenMP 的编译器以及运行环境。第 3 章介绍 OpenMP
编译器基本框架。第 4 章介绍词法分析和语法分析,主要以 Lex 和 Yacc 工具实现 OpenMP 词
法和语法分析为主要内容。第 5 章介绍 OpenMP 编译中使用的 AST 中间表示。第 6 章、第 7
章和第 8 章介绍 OpenMP 编译中的并行域管理、任务分担和同步、变量数据环境三大问题,
这是 OpenMP 编译的核心所在。第 9 章讲述目标代码生成,主要是如何利用“框架”来实现
OpenMP 翻译的技术。第 10 章以 OMPi 运行环境为例讲述相应的运行环境,。
第三篇实践部共有四章内容。第 11 章给出了几种常见的 OpenMP 编译器以及性能测试工
具,用于读者测试自己设计的或修改的编译器性能。第 12 章、13 章和第 14 章是关于 OMPi
编译器工作流程和框架的内容,并有两个主要的上层源文件的代码分析,如果希望在 OMPi
的基础之上进行增强改进,那么这 3 章的内容将有所帮助。
对学习或课程的安排可以分成不同流程,比如根据教学偏向于原理性还是实践性、是否具
有并行计算基础等情况,选取书中部分章节作为参考材料,书中各章倾向性情况安排如下:
预备知识
第 1 章
第 2 章
并行计算基础
OpenMP 编程
第 9 章
目标代码
第 10 章
运行环境
原理性内容
OpenMP 专有内容
第 3 章
第 4 章
OpenMP 编译
词法语法分析
第 5 章
AST
第 6 章
并行域
第 7 章
任务分担
第 8 章
数据环境
实践性内容
第 11 章
编译器及工具
第 12 章
OMPi 框架
第 13 章
ompicc.c
第 14 章
ompi.c
虽然书中有大量的代码,但是读者在第一遍阅读时可以只作粗略浏览,第二遍阅读时再仔
细阅读代码。由于源代码阅读往往需要参考不同章节的内容,因此书中有大量的交叉引用说明。
2
如果对 OpenMP 编译有一定了解,并希望掌握 OMPi 的具体编码实现技术,可以从第 12 章开
始阅读,将整体框架看完,再根据需要返回第二篇阅读编译细节。
限于作者的学识水平,书中难免有不少错误和不足,恳请读者批评指正。作者在编写本书
时深感“抛砖引玉”一词不仅仅是场面上的客套话,更是作者的内心体会和期望。
3
致谢
本书得以顺利完稿,是许多人的共同努力!
在此首先要感谢陈国良院士的支持和帮助。陈院士于 2009 年到深圳大学主持计算机与软
件学院的教学科研的全面工作,作者作为其高性能团队成员有幸参与了众多高性能计算的科研
工作,包括参与全国产万亿次个人高性能计算机 KD-60 研制、作为核心人员研制了 SD-1 PHPC
以及正在进行基于龙芯处理器的 SD-30 十万亿次全国产化高性能计算机的研制等等。在这些工
作中,作者萌发了编写 OpenMP 编译方面的书籍,陈院士表示认可和支持并给出了非常有价
值的意见和建议,这就是本书得以编写并顺利完稿的最初原因。其次需要感谢明仲教授,在本
书的最初构思、规划和资料整理的初期,明仲教授不仅阅读了初步的稿件材料并给出了大量的
指导和修改意见,对后期稿件也提出了许多建设性意见。
刘刚老师编写了第一章的部分内容和第二章的大部分内容,毛睿老师参与了多个章节的编
写和订正工作,陆克中老师阅读了初期的稿件并给出了有益的意见。正因为有了这几位老师的
贡献,使本书的编写质量和水平得以提高。另有两位研究生参与了本书的编写,孔畅同学完成
了第 11 章的所有实验并编写了该章内容,刘成健同学是该书的第一位真正意义上的读者,并
参与了稿件查错订正工作。
对于深圳大学高性能计算团队中给本书编写工作提供了各种帮助的老师和同学,不能一一
尽数,在此一并表示衷心的感谢!
4
目录
第一篇 基础 ............................................................................................................................. 1
第 1 章 并行计算基础 ............................................................................................................. 2
1.1 基本概念................................................................................................................... 2
1.2 并行计算平台 ........................................................................................................... 3
1.2.1 典型结构 ..................................................................................................... 3
1.2.2
SMP .............................................................................................................. 5
1.2.3 NUMA .......................................................................................................... 7
1.2.4 GPU .............................................................................................................. 9
1.2.5
Cluster ........................................................................................................10
1.3 并行程序设计技术 .................................................................................................13
1.3.1 并行程序设计 ...........................................................................................14
1.3.2 OpenMP .....................................................................................................16
1.3.3 MPI .............................................................................................................16
1.3.4
CUDA ..........................................................................................................17
1.3.5 HPF .............................................................................................................18
1.4 小结 ........................................................................................................................18
第 2 章 OpenMP 编程基础 ....................................................................................................19
2.1 OpenMP 基本概念 .................................................................................................19
2.1.1 执行模式 ...................................................................................................19
2.1.2 OpenMP 编程要素 ....................................................................................20
2.2 OpenMP 编程 .........................................................................................................22
2.2.1 并行域管理 ...............................................................................................23
2.2.2 任务分担 ...................................................................................................24
2.2.3 同步 ...........................................................................................................32
2.2.4 数据环境控制 ...........................................................................................38
2.3 小结 ........................................................................................................................44
第二篇 OpenMP 编译 .............................................................................................................46
第 3 章 OpenMP 编译 ............................................................................................................ 47
3.1 OpenMP 编译系统 ................................................................................................. 47
3.1.1 编译系统 ...................................................................................................47
3.1.2 目标语言 ...................................................................................................48
3.2 OpenMP 编译器结构 .............................................................................................50
3.2.1 功能模块 ...................................................................................................50
3.2.2 工作流程 ...................................................................................................54
5
3.3 编译优化.................................................................................................................54
3.4 小结 ........................................................................................................................54
第 4 章 词法与语法分析 .......................................................................................................56
4.1 Lex 工具 ..................................................................................................................56
4.1.1
4.1.2
Lex 的正则表达式 ....................................................................................57
Lex 使用方法 ............................................................................................59
4.2 OpenMP/C 的词法分析 ..........................................................................................60
4.2.1
C 语言单词 ................................................................................................61
4.2.2 OpenMP 单词 ............................................................................................61
4.2.3 OpenMP 与 C 语言公用单词 ....................................................................62
4.3 scanner.l .................................................................................................................. 62
4.3.1 全局声明段 ...............................................................................................63
4.3.2 模式匹配规则段 .......................................................................................64
4.3.3 补充函数段 ...............................................................................................69
4.3.4
scanner.c ....................................................................................................72
4.3.5
scanner.h ...................................................................................................72
4.4 Yacc 工具................................................................................................................. 73
4.4.1
Yacc ............................................................................................................73
4.4.2
Yacc 文件实例 ...........................................................................................75
4.5 OpenMP/C 语法分析 .............................................................................................. 78
4.6 小结 ........................................................................................................................81
第 5 章 AST 的创建 ................................................................................................................ 82
5.1 中间表示................................................................................................................. 82
5.1.1 两种中间表示形式 ...................................................................................82
5.1.2 中间表示的选择 .......................................................................................83
5.2 AST 节点数据结构 ..................................................................................................84
5.2.1 语句节点 ...................................................................................................84
5.2.2 类型说明节点 ...........................................................................................87
5.2.3 声明节点 ...................................................................................................88
5.2.4 表达式节点 ...............................................................................................89
5.2.5 OpenMP 制导节点 ....................................................................................90
5.3 AST 节点维护函数 ..................................................................................................95
5.4 AST 的创建..............................................................................................................96
5.4.1 语法制导翻译 ...........................................................................................96
5.4.2 例 1 OpenMP 的 for 节点 .........................................................................99
5.4.3 例 2 C 语言 while 语句 ...........................................................................100
5.4.4 Helloworld.c 的 AST .................................................................................101
5.5 符号表 ..................................................................................................................103
6
5.5.1 字符串表 .................................................................................................104
5.5.2 符号表 .....................................................................................................105
5.5.3 符号表操作 .............................................................................................106
5.5.4 作用域管理 .............................................................................................107
5.6 小结 ...................................................................................................................... 107
第 6 章 并行域管理 .............................................................................................................108
6.1 并行域及其嵌套 ...................................................................................................108
6.2 并行域管理...........................................................................................................110
6.2.1 线程无关接口 .........................................................................................110
6.2.2 线程的供给 .............................................................................................111
6.2.3 线程层次关系 .........................................................................................111
6.2.4 并行域代码封装与标识 .........................................................................113
6.2.5 任务分担问题 .........................................................................................113
6.3 目标代码形式 .......................................................................................................114
6.4 OMPi 的并行域管理 .............................................................................................115
6.4.1 ORT 统一界面 .........................................................................................115
6.4.2 并行域代码变换 .....................................................................................117
6.4.3 线程管理与控制 .....................................................................................118
6.4.4 总览 .........................................................................................................122
6.5 小结 ......................................................................................................................123
第 7 章 任务分担与线程同步 .............................................................................................125
7.1 for 制导指令 .........................................................................................................125
7.1.1
for 任务分担 ...........................................................................................125
7.1.2 循环变量分解原则 .................................................................................126
7.1.3 目标代码功能 .........................................................................................127
7.1.4 目标代码形式 .........................................................................................128
7.1.5 OMPi 的 for 制导指令 ............................................................................129
7.2 sections 制导指令 ................................................................................................135
7.2.1
7.2.2
sections 任务分担描述 ...........................................................................135
section 划分原则 ....................................................................................136
7.2.3 目标代码功能 .........................................................................................136
7.2.4 目标代码形式 .........................................................................................136
7.2.5 OMPi 的 sections 制导指令 ....................................................................138
7.3 single 制导指令 ....................................................................................................139
7.4 nowait 问题 ..........................................................................................................140
7.5 归约操作...............................................................................................................141
7.6 线程同步...............................................................................................................143
7.6.1
atomic ......................................................................................................143
7
7.6.2
critical ......................................................................................................143
7.6.3 master ......................................................................................................144
7.6.4
ordered ....................................................................................................144
7.6.5
nowait ......................................................................................................145
7.6.6
flush .........................................................................................................145
7.6.7
barrier ......................................................................................................146
7.7 小结 ......................................................................................................................146
第 8 章 数据环境控制 ......................................................................................................... 147
8.1 共享与私有........................................................................................................... 147
8.1.1 非全局变量的共享 .................................................................................148
8.1.2 变量的私有化 .........................................................................................150
8.1.3
threadprivate 子句 ..................................................................................150
8.1.4 基于进程的问题 .....................................................................................151
8.2 并行域边界处理 ...................................................................................................151
8.2.1
8.2.2
private 变量 .............................................................................................151
threadprivate 变量 ..................................................................................151
8.3 OMPi 数据环境控制 ............................................................................................. 152
8.3.1 共享变量 .................................................................................................152
8.3.2 私有变量 .................................................................................................153
8.3.3 线程专有变量 .........................................................................................156
8.3.4 归约变量 .................................................................................................159
8.4 小结 ......................................................................................................................160
第 9 章 产生目标代码 ......................................................................................................... 162
9.1 源代码变换........................................................................................................... 162
9.1.1 变换流程 .................................................................................................162
9.1.2 支撑函数 .................................................................................................164
9.2 AST 变换 ...............................................................................................................164
9.2.1 拼接及创建函数 .....................................................................................164
9.2.2 变换函数集 .............................................................................................165
9.2.3 OpenMP 节点变换 ..................................................................................168
9.2.4
9.2.5
parallel 变换 ............................................................................................172
for 变换 ...................................................................................................175
9.2.6
sections 变换 ...........................................................................................177
9.2.7 数据环境的处理 .....................................................................................178
9.3 代码优化...............................................................................................................180
9.4 AST 输出 ...............................................................................................................181
9.4.1 OMPi 的 AST 输出 ...................................................................................181
9.4.2 OpenMP 节点输出 ..................................................................................182
8