当前位置: 首页 > news >正文

CUDA编程(一) —— 相关概念基础知识

      CUDA(Compute Unified Device Architecture)的中文全称为计算统一设备架构。做图像视觉领域的同学多多少少都会接触到CUDA,毕竟要做性能速度优化,CUDA是个很重要的工具,CUDA是做视觉的同学难以绕过的一个坑,必须踩一踩才踏实。CUDA编程真的是入门容易精通难,具有计算机体系结构和C语言编程知识储备的同学上手CUDA编程应该难度不会很大

GPU架构

       现在的计算机体系架构中,要完成CUDA并行计算,单靠GPU一人之力是不能完成计算任务的,必须借助CPU来协同配合完成一次高性能的并行计算任务

      一般而言,并行部分在GPU上运行,串行部分在CPU运行,这就是异构计算。具体一点,异构计算的意思就是不同体系结构的处理器相互协作完成计算任务。CPU负责总体的程序流程,而GPU负责具体的计算任务,当GPU各个线程完成计算任务后,我们就将GPU那边计算得到的结果拷贝到CPU端,完成一次计算任务。

 

       所以应用程序利用GPU实现加速的总体分工就是:密集计算代码(约占5%的代码量)由GPU负责完成,剩余串行代码由CPU负责执行。

CUDA线程模型

      我们都知道,线程是程序执行的最基本单元,CUDA的并行计算就是通过成千上万个线程的并行执行来实现的。下面的结构图说明了GPU的不同层次的结构。

 CUDA的线程模型从小往大来总结就是:

①Thread: 线程,并行的基本单位

②Thread Block: 线程块,互相合作的线程组。

    线程块有如下几个特点:

  • 允许彼此同步
  • 可以通过共享内存快速交换数据
  • 以1维、2维或3维组织

③Grid: 一组线程块

  • 以1维、2维组织
  • 共享全局内存

④Kernel:在GPU上执行的核心程序,这个kernel函数是运行在某个Grid上的。

  • One kernel 对应 One Grid

每一个block和每个thread都有自己的ID,我们通过相应的索引找到相应的线程和线程块。

  • threadIdx,blockIdx
  • Block ID: 1D or 2D
  • Thread ID: 1D, 2D or 3D

       理解kernel,必须要对kernel的线程层次结构有一个清晰的认识。

       首先GPU上很多并行化的轻量级线程。kernel在device上执行时实际上是启动很多线程,一个kernel所启动的所有线程称为一个网格(grid),同一个网格上的线程共享相同的全局内存空间,grid是线程结构的第一层次,而网格又可以分为很多线程块(block),一个线程块里面包含很多线程,这是第二个层次。线程两层组织结构如上图所示,这是一个gird和block均为2-dim的线程组织。grid和block都是定义为dim3类型的变量,dim3可以看成是包含三个无符号整数(x,y,z)成员的结构体变量,在定义时,缺省值初始化为1。因此grid和block可以灵活地定义为1-dim,2-dim以及3-dim结构,kernel调用时也必须通过执行配置<<<grid, block>>>来指定kernel所使用的网格维度和线程块维度。

      举个例子,我们以上图为例,分析怎么通过<<<grid,block>>>>这种标记方式索引到我们想要的那个线程。CUDA的这种<<<grid,block>>>其实就是一个多级索引的方法,第一级索引是(grid.xIdx, grid.yIdy),对应上图例子就是(1, 1),通过它我们就能找到了这个线程块的位置,然后我们启动二级索引(block.xIdx, block.yIdx, block.zIdx)来定位到指定的线程。这就是我们CUDA的线程组织结构

SP & SM

①SP:最基本的处理单元,streaming processor,也称为CUDA core。
      最后具体的指令和任务都是在SP上处理的。GPU进行并行计算,也就是很多个SP同时做处理。

②SM:多个SP加上其他的一些资源组成一个streaming multiprocessor。也叫GPU大核。

      SM还包含其他资源如warp scheduler,register,shared memory等。SM可以看做GPU的心脏(对比CPU核心),register和shared memory是SM的稀缺资源。CUDA将这些资源分配给所有驻留在SM中的threads。因此,这些有限的资源就使每个SM中active warps有非常严格的限制,也就限制了并行能力。

      简而言之,SP是线程执行的硬件单位,SM中包含多个SP,一个GPU可以有多个SM(比如16个),最终一个GPU可能包含有上千个SP。这么多核心“同时运行”,速度可想而知,这个引号只是想表明实际上,软件逻辑上是所有SP是并行的,但是物理上并不是所有SP都能同时执行计算(比如我们只有8个SM却有1024个线程块需要调度处理),因为有些会处于挂起,就绪等其他状态,这有关GPU的线程调度。

      每个SM包含的SP数量依据GPU架构而不同,Fermi架构GF100是32个,GF10X是48个,Kepler架构都是192个,Maxwell都是128个。

下面从硬件角度和软件角度展示CUDA的线程模型。

  •  每个线程由每个线程处理器(SP)执行
  • 线程块由多核处理器(SM)执行
  • 一个kernel其实由一个grid来执行,一个kernel一次只能在一个GPU上执行

      block是软件概念,一个block只会由一个sm调度,程序员在开发时,通过设定block的属性,告诉GPU硬件,我有多少个线程,线程怎么组织。而具体怎么调度由sm的warps scheduler负责,block一旦被分配好SM,该block就会一直驻留在该SM中,直到执行结束。一个SM可以同时拥有多个blocks,但需要序列执行。

GPU内部的硬件架构

CUDA内存模型

CUDA中的内存模型分为以下几个层次:

  • 每个线程都用自己的registers(寄存器)
  • 每个线程都有自己的local memory(局部内存)
  • 每个线程块内都有自己的shared memory(共享内存),所有线程块内的所有线程共享这段内存资源
  • 每个grid都有自己的global memory(全局内存),不同线程块的线程都可使用
  • 每个grid都有自己的constant memory(常量内存)和texture memory(纹理内存),),不同线程块的线程都可使用

线程访问这几类存储器的速度是register > local memory >shared memory > global memory

下面这幅图表示就是这些内存在计算机架构中的所在层次。

 

 

https://www.cnblogs.com/skyfsm/p/9673960.html

相关文章:

  • CUDA编程(二) —— CUDA编程模型
  • Python Fastai框架
  • ubuntu安装docker
  • Linux(ubuntu)(十三) —— (系统)服务管理 (systemctlservicechkconfig)服务的运行级别(Runlevel)
  • linux 文件/目录名 颜色
  • nvcc(CUDA编译器)
  • docker使用GPU(nvidia-docker)
  • Pytorch分布式训练/多卡训练(二) —— Data Parallel并行(DDP)(2.3)(torch.multiprocessing(spawn) Apex)
  • OpenStack
  • Python logging日志模块
  • CUDA编程(三) —— 编程实践
  • Python函数传参(*星号)
  • Python调用函数带括号和不带括号的区别
  • Microsoft CMT 系统
  • Python导入上层目录中的包(..) / 导入同级目录的包 (相对导入)
  • HTTP 简介
  • Javascript Math对象和Date对象常用方法详解
  • OSS Web直传 (文件图片)
  • RxJS 实现摩斯密码(Morse) 【内附脑图】
  • SpingCloudBus整合RabbitMQ
  • 猴子数据域名防封接口降低小说被封的风险
  • 使用Gradle第一次构建Java程序
  • 小程序开发中的那些坑
  • 终端用户监控:真实用户监控还是模拟监控?
  • 阿里云IoT边缘计算助力企业零改造实现远程运维 ...
  • ​​​​​​​GitLab 之 GitLab-Runner 安装,配置与问题汇总
  • ​RecSys 2022 | 面向人岗匹配的双向选择偏好建模
  • ​比特币大跌的 2 个原因
  • #控制台大学课堂点名问题_课堂随机点名
  • #我与Java虚拟机的故事#连载02:“小蓝”陪伴的日日夜夜
  • $ is not function   和JQUERY 命名 冲突的解说 Jquer问题 (
  • $HTTP_POST_VARS['']和$_POST['']的区别
  • (02)Cartographer源码无死角解析-(03) 新数据运行与地图保存、加载地图启动仅定位模式
  • (delphi11最新学习资料) Object Pascal 学习笔记---第5章第5节(delphi中的指针)
  • (八)Spring源码解析:Spring MVC
  • (分布式缓存)Redis哨兵
  • (论文阅读40-45)图像描述1
  • (排序详解之 堆排序)
  • (三) prometheus + grafana + alertmanager 配置Redis监控
  • (三)elasticsearch 源码之启动流程分析
  • (十八)SpringBoot之发送QQ邮件
  • (十二)devops持续集成开发——jenkins的全局工具配置之sonar qube环境安装及配置
  • (四)汇编语言——简单程序
  • (译)计算距离、方位和更多经纬度之间的点
  • (轉貼) 2008 Altera 亞洲創新大賽 台灣學生成果傲視全球 [照片花絮] (SOC) (News)
  • .NET Core实战项目之CMS 第十二章 开发篇-Dapper封装CURD及仓储代码生成器实现
  • .NET MVC第五章、模型绑定获取表单数据
  • .NET Standard / dotnet-core / net472 —— .NET 究竟应该如何大小写?
  • .Net Web窗口页属性
  • .net 设置默认首页
  • .NET/C# 中设置当发生某个特定异常时进入断点(不借助 Visual Studio 的纯代码实现)
  • .net的socket示例
  • .net利用SQLBulkCopy进行数据库之间的大批量数据传递
  • .net中我喜欢的两种验证码
  • .sh文件怎么运行_创建优化的Go镜像文件以及踩过的坑