《OpenACC并行程序设计:性能优化实践指南》一 2.4 优化循环

简介: 本节书摘来自华章出版社《OpenACC并行程序设计:性能优化实践指南》一 书中的第2章,第2.4节,作者:[美] 罗布·法伯(Rob Farber),更多章节内容可以访问云栖社区“华章计算机”公众号查看。

2.4 优化循环

此刻,测试代码可以比原始代码加速2倍了。但这是能够获得的性能最好的代码吗?目前添加的导语可以在任何加速器上实现代码的提速,但为了在特定的测试机器上取得最佳性能,需要使用特定目标设备优化技术。万幸的是,OpenACC提供了一种指定devcie_type的优化手段,因此特定的子句仅在编译为指定设备的代码时才会生效。首先从分析目前代码的编译器反馈信息着手,针对matvec子程序,因为它是最为耗时的代码段(见图2-22)。

screenshot

编译器提供了它如何并行化两个矩阵循环(第30和24行)的信息。但为了理解这些信息,需要理解OpenACC的三层并行层级:工作组(gang),工作项(worker)和向量(vector)。从最底层开始研究,向量化并行层级是针对细粒度并行的,对多个数据元素实施同样的操作。例如,有两个数组想要进行相加操作,有些硬件支持特殊的指令集,可以在成组的数据中同时进行加法操作。同时相加操作的数据个数称为向量长度,这一值随着不同硬件有所不同。顶层并行层级是工作组。工作组运行完全独立的操作,操作相互间不可能进行同步,且无法保证什么时候每个工作组会与其他工作组发生通信。由于工作组并行层级是粗粒度的,故具有很好的可扩展性。工作项并行层级介于工作组和向量之间。工作组由一个或多个工作项组成,每个工作项操控一个向量。同一个向量内的工作项可进行同步操作,且可以共享同一个高速缓存。每个由OpenACC编译器并行化的循环将被映射到以上三层并行层级中的至少一层,或串行执行(如果由seq修饰)。图2-23展示了OpenACC的三层并行层级。
基于以上背景知识,能够研究OpenACC编译器如何将二重循环映射到三层并行层级中的。它将第30行的循环映射到gang和vector并行层级,隐式地为每个gang建立了一个worker,且将向量长度设置为128。第34行的循环是串行执行的。有了这些信息,现在可以告知编译器额外的信息,引导获知编译器如何将这些循环映射到不同的并行层级。

screenshot

2.4.1 缩短向量长度

使用NVIDIA GPU运行测试程序,作者会利用对NVIDIA GPU的理解和应用经验来更好地决策如何进行循环并行化。例如,知道NVIDIA GPU在向量循环在stride-1范围内进行数据访问时效率最高,即每个连续的循环体访问的是连续的数组元素。外层循环以跨度1访问row_offsets数组,内层循环也以跨度1访问Acols,Acoefs和xcoefs数组,这样使得代码更适合于向量化目标处理器。为内层循环添加loop导语允许进一步标明内层循环属于哪一个并行度层级。此外,可以说明向量长度是多少。编译器更倾向于使用128作为向量长度,但内层循环永远处理27个非零元素,这样会在每次运行循环时损失101个向量通道的性能。这里缩减向量长度是更好的选择,当然前提是提前知道循环次数。理想情况下,将向量长度缩减为27,因为已知循环迭代次数就是27,但NVIDIA GPU具有硬件向量长度,NVIDIA称为warp宽度,即32。因此,将向量宽度缩减为32,仅浪费掉5个向量通道而不是101个。图2-24展示了内层循环映射为vector并行层级且向量长度为32的matvec循环。注意:device_type子句需要添加到循环导语中,该子句表明列举的多条子句仅适用于nvidia类型的设备。这表明在其他设备上,编译器不进行这些特殊处理。

screenshot

screenshot

如图2-25所示,这一改动实际上降低了程序整体性能。可以尝试性地将代码改回原样,因为这一改动没有提升性能。但作者认为向量化最内层循环是一个正确的决定,故使用性能调试器来运行程序,以便能更好地理解为什么没有获得理想中的加速效果。

screenshot

2.4.2 增加并行度

为了确定为何修改向量宽度后并未获得期望的性能提升效果,将使用PGProf指导分析模式来辅助监测性能瓶颈点。指导性分析是默认开启的,因此在当前可执行文件中开启一个新代码段时,需要选择“分析”选项卡并遵循文档建议的操作。分析过程最终将集中于GPU占用率,这是一个瓶颈,如图2-26所示。占用率是NVIDIA提出的一个术语,标志GPU工作强度的饱满程度,即GPU当前工作强度与其理论最大工作能力之间的比较。NVIDIA GPU由1个或多个流多处理器组成,通常称为SM。每个SM可以操控多达2048个并行线程,但这些线程不一定能够同时处于激活和运行状态。性能调试器输出结果显示对于可能激活的2048条线程,SM仅运行了512条线程,导致占用率为25%。图2-26中的红线说明了原因:SM可以最多调度16个线程块,对应于OpenACC的gang,但根据gang的尺度大小,需要有64个线程块才能达到最大占用率,但从“Threads/Block”行中发现仅有32个线程。以上情况说明通过缩减向量宽度至32,每个线程块的总线程数也被缩减到32,因此需要引入更大的并行度来更好地“喂饱”GPU。
可以通过两种途径增加gang的并行度:增加向量宽度和增加工作项。从前述章节可知,增加向量宽度是无效的,因为没有足够的计算量适应更长的向量宽度。因此将尝试增加工作项的数目。GPU线程块中的总任务可以认为是工作项数×向量宽度。因此,最多可以利用32个工作项,因为32×32=1024个GPU线程。图2-27展示了最终的matvec循环的代码。图2-28展示了通过改变每个工作组中的工作项数获得的加速效果。

screenshot

screenshot

在本书使用的测试系统中,8个worker和32个线程对应于最优gang。因为使用了device_type子句,这些优化仅作用于NVIDIA GPU,不会影响其他加速器设备对应的代码。

screenshot

相关实践学习
在云上部署ChatGLM2-6B大模型(GPU版)
ChatGLM2-6B是由智谱AI及清华KEG实验室于2023年6月发布的中英双语对话开源大模型。通过本实验,可以学习如何配置AIGC开发环境,如何部署ChatGLM2-6B大模型。
相关文章
|
机器学习/深度学习 人工智能 自然语言处理
视觉 注意力机制——通道注意力、空间注意力、自注意力
本文介绍注意力机制的概念和基本原理,并站在计算机视觉CV角度,进一步介绍通道注意力、空间注意力、混合注意力、自注意力等。
13309 58
|
5月前
|
监控 数据库 数据安全/隐私保护
微信自动抢红包永久免费软件, 自动抢红包软件微信,脚本插件抢红包【python】
该实现包含三个核心模块:主监控程序、数据库记录模块和配置模块。主程序使用itchat监听微信消息
|
Rust 前端开发 jenkins
Tauri 开发实践 — 使用 CI/CD 自动构建发布 Tauri 桌面端应用
本文介绍如何使用 CI/CD 自动构建发布 Tauri 应用。Tauri 是一个轻量级跨平台客户端框架,适合个人应用。文章首先概述了 CI/CD 的基本流程,并介绍了 GitHub Actions、GitLab CI 和 Jenkins 三种工具。最终选择了 GitHub Actions 进行配置。文中详细展示了使用 GitHub Actions 脚本实现 Tauri 应用构建的过程,并解决了权限和安全问题。项目源码可在 GitHub 上获取。
850 5
Tauri 开发实践 — 使用 CI/CD 自动构建发布 Tauri 桌面端应用
|
机器学习/深度学习 存储 自然语言处理
SeACo-Paraformer
【6月更文挑战第14天】
865 6
|
存储 Java
Java——图书管理系统
该文档详细介绍了一个图书管理系统的设计与实现。系统包含普通用户和管理员两种角色,通过书架操作图书,如添加、查找、借阅、归还及删除图书等功能。文档展示了各个功能的具体代码实现,并使用继承和接口等方式优化了系统结构。通过多态技术实现了不同用户角色调用相应功能。整体设计清晰,逻辑严谨,便于理解和实现。
586 18
Java——图书管理系统
|
自然语言处理 Java 测试技术
通义灵码个人版体验
作为一名Java开发工程师,我利用通义灵码个人版高效地熟悉新项目、实现新需求,效率提升超过30%。从项目导入、代码理解、新需求实现到代码优化与提交,通义灵码提供了全面的支持,显著加速了开发流程。
|
机器学习/深度学习 自然语言处理
预训练语义模型作为特征提取器的方法
预训练语义模型作为特征提取器的方法
|
机器学习/深度学习 算法 数据可视化
8种数值变量的特征工程技术:利用Sklearn、Numpy和Python将数值转化为预测模型的有效特征
特征工程是机器学习流程中的关键步骤,通过将原始数据转换为更具意义的特征,增强模型对数据关系的理解能力。本文重点介绍处理数值变量的高级特征工程技术,包括归一化、多项式特征、FunctionTransformer、KBinsDiscretizer、对数变换、PowerTransformer、QuantileTransformer和PCA,旨在提升模型性能。这些技术能够揭示数据中的潜在模式、优化变量表示,并应对数据分布和内在特性带来的挑战,从而提高模型的稳健性和泛化能力。每种技术都有其独特优势,适用于不同类型的数据和问题。通过实验和验证选择最适合的变换方法至关重要。
501 6
8种数值变量的特征工程技术:利用Sklearn、Numpy和Python将数值转化为预测模型的有效特征
|
机器学习/深度学习 人工智能 算法
技术开源|FunASR升级第三代热词方案
技术开源|FunASR升级第三代热词方案
3599 62
|
机器学习/深度学习 人工智能 文字识别
ultralytics YOLO11 全新发布!(原理介绍+代码详见+结构框图)
本文详细介绍YOLO11,包括其全新特性、代码实现及结构框图,并提供如何使用NEU-DET数据集进行训练的指南。YOLO11在前代基础上引入了新功能和改进,如C3k2、C2PSA模块和更轻量级的分类检测头,显著提升了模型的性能和灵活性。文中还对比了YOLO11与YOLOv8的区别,并展示了训练过程和结果的可视化
20506 0