http://hi.baidu.com/pengkuny/item/c8070b388d75d481b611db7a



以前以为 shared memory 是一个万能的 L1 cache,速度很快,只要数据的 size 够小,能够放到 shared memory,剩下的事情我就不用操心啦。实际上不是这样,bank conflict 是一个绕不过去的问题,否则,性能会降得很低,很低,很低。。。



---------------------------------------------------------------



为什么 shared memory 存在 bank  conflict,而 global memory 不存在?因为访问 global memory 的只能是 block,而访问 shared memory 的却是同一个 half-warp 中的任意线程。

http://stackoverflow.com/questions/3843032/why-arent-there-bank-conflicts-in-global-memory-for-cuda-opencl 



----------------------------------------------------------------



摘自这个要翻墙的网页:Introduction to GPU Programming (HPC Summer Institute at Rice University) http://davidmedinawiki.wordpress.com/2012/06/08/introduction-to-gpu-programming/



Now that we know a little about shared memory, we need to see how this memory is accessed within the thread block. There are these memory managers called “memory banks” that are in charge of distributing the memory they manage.



Ok, that sentence sounded like it just stated the obvious but that is what memory banks do. The question now is, what memory are they in charge of?









Memory Bank Architecture (From the HPC Session)



Above is a diagram that shows how a GPU with 8 memory banks would store shared memory. Using basic math we get the following equation:



// mem is the memory location

bank = mem/8;



So why are these memory banks so important?



Well, the memory banks distribute data stored in their bank of shared memory one call at a time. This means that a parallel code can easily be turned into serial code due to bank conflicts (when each thread accesses from the same bank at the same time). There is, however, one exception to bank conflicts” which is when threads access the same memory from the same memory bank.

Here are some examples that show good and bad uses of bank memory (Images taken from the HPC Session):















---------------------------------------------------------------



下面的文字来自:http://hi.baidu.com/dwdxdy/item/e5d66f40168f852810ee1ef7 

 

共享存储器被组织为16个bank,每个bank拥有32bit的宽度。

一个warp中的线程对共享存储器的访问请求会被划分为两个half-warp的访问请求。

无 bank conflict 时,一个half-warp内的线程可以在一个内核周期中并行访问

对同一 bank 的同时访问导致 bank conflict 只能顺序处理 访存效率降低

如果half-warp的线程访问同一地址时,会产生一次广播,不会产生 bank conflict













__shared__ float shared[256];

float foo = shared[threadIdx.x];

没有访问冲突







__shared__ float shared[256];

float foo = shared[threadIdx.x * 2];

产生2路访问冲突



__shared__ float shared[256];

float foo = shared[threadIdx.x*8];

产生8路访问冲突



---------------------------------------------------------------



Number of shared memory banks

来源:http://en.wikipedia.org/wiki/CUDA 

GPU device 1.x : 16

GPU device 2.x : 32



---------------------------------------------------------------



书上说:“每个 bank 的宽度固定为 32 bit,相邻的 32 bit 字被组织在相邻的 bank 中,每个 bank 在每个时钟周期可以提供 32 bit 的带宽。”



由上面这句话可以看出来:将 shared memory 看成一个二维存储空间,每个 bank 就是一列,每一行就是 16(或 32)个 banks。要么,尽量让一个 half-warp(或 full warp)中的线程分散访问不同列(即访问不同的 bank,同行不同行没有关系);要么,让一个 half-warp(或 full warp)中的线程务必全部访问同一列且同一行(即访问同一个地址,仅对读操作有效)。



对于计算能力 1.0 的设备,前个 half-warp 和 后个 half-warp 不存在 bank conflict;

对于计算能力 2.0 的设备,前个 half-warp 和 后个 half-warp 可能存在 bank conflict,因为 shared memory 可以同时让 32 个 bank 响应请求;



如果是写操作,一个 half-warp(或 full warp) 中所有线程访问同一地址的时候,此时会产生不确定的结果(也只需要一个 clock cycle,不确定哪个线程会胜出),发生这种情况时应使用原子操作——但是原子操作对性能影响太大。



“Shared memory features a broadcast mechanism whereby a 32-bit word can be read and broadcast to several threadssimultaneously when servicing one memory read request. ”——从这个描述来看,只要是多个线程访问同一地址都可以产生一次广播,多个线程访问同一地址将有效减少 bank conflict 的数量。若 half-warp(或 full warp) 中所有线程都要访问同一地址,则完全没有 bank conflict。



对于大于 32 bit 的 struct 来说,对它的访问将编译成多个独立的存储器访问。– “Share memory only supports 32 bit reads/writes”



因此,shared memory 的写操作的 bank conflict 是一个很头疼的问题。

【并行计算-CUDA开发】CUDA bank conflict in shared memory的更多相关文章

  1. CUDA开发 - CUDA 版本

    "CUDA runtime is insufficient with CUDA driver"CUDA 9.2: 396.xx CUDA 9.1: 387.xx CUDA 9.0: ...

  2. 【并行计算-CUDA开发】CUDA shared memory bank 冲突

    CUDA SHARED MEMORY shared memory在之前的博文有些介绍,这部分会专门讲解其内容.在global Memory部分,数据对齐和连续是很重要的话题,当使用L1的时候,对齐问题 ...

  3. CUDA ---- Shared Memory

    CUDA SHARED MEMORY shared memory在之前的博文有些介绍,这部分会专门讲解其内容.在global Memory部分,数据对齐和连续是很重要的话题,当使用L1的时候,对齐问题 ...

  4. 【并行计算-CUDA开发】关于共享内存(shared memory)和存储体(bank)的事实和疑惑

    关于共享内存(shared memory)和存储体(bank)的事实和疑惑 主要是在研究访问共享内存会产生bank conflict时,自己产生的疑惑.对于这点疑惑,网上都没有相关描述, 不管是国内还 ...

  5. 【CUDA开发-并行计算】NVIDIA深度学习应用之五大杀器

    来自吉浦迅科技 整理发布 http://mp.weixin.qq.com/s?__biz=MjM5NTE3Nzk4MQ==&mid=2651231163&idx=1&sn=d4 ...

  6. 【并行计算-CUDA开发】有关CUDA当中global memory如何实现合并访问跟内存对齐相关的问题

    ps:这是英伟达二面面的一道相关CUDA的题目.<NVIDIA CUDA编程指南>第57页开始          在合并访问这里,不要跟shared memory的bank conflic ...

  7. CUDA中Bank conflict冲突

    转自:http://blog.csdn.net/smsmn/article/details/6336060 其实这两天一直不知道什么叫bank conflict冲突,这两天因为要看那个矩阵转置优化的问 ...

  8. 【并行计算-CUDA开发】CUDA编程——GPU架构,由sp,sm,thread,block,grid,warp说起

    掌握部分硬件知识,有助于程序员编写更好的CUDA程序,提升CUDA程序性能,本文目的是理清sp,sm,thread,block,grid,warp之间的关系.由于作者能力有限,难免有疏漏,恳请读者批评 ...

  9. 【并行计算-CUDA开发】warp是调度和执行的基本单位而harf-warp为存储器操作基本单位

    1.在用vs运行cuda的一些例子时,在编译阶段会报出很多警告: warning C4819 ...... 解决这个警告的方法是打开出现warning的文件,Ctrl+A全选,然后在文件菜单:file ...

随机推荐

  1. 创建虚拟机(kvm)

    --virsh console virt_name -- virsh nodeinfo                     # 查看kvm节点(服务器)信息 --virsh list [--all ...

  2. mysql日常优化细节

    # sql语句优化> 1)使用limit限制一次性查询出的数据量2)链接查询代替子查询3)尽量不要使用select * ,将需要查找的字段列出来4)如果数据量特别大的话尽量将一条复杂的sql拆分 ...

  3. MySQL原理解析

    逻辑架构 MySQL逻辑架构整体分为三层: 客户端层,连接处理.授权认证.安全等功能均在这一层处理. 核心服务层,包括查询解析.分析.优化.缓存.内置函数(比如:时间.数学.加密等函数).所有的跨存储 ...

  4. 5.rabbitmq--通配符模式Topics

    rabbitmq--通配符模式Topics topic模式也称为主题模式,其实他相对于routing模式最大的好处就是他多了一种匹配模式的路由,怎么理解匹配呢,其实就相当于我们之前正则的.*这种,不过 ...

  5. 13.调整数组顺序使奇数位于偶数前面 Java

    思路 两次遍历,第一次把奇数加到list中,第二次把偶数加到list中,时间复杂度为O(n). 利用类似于插入排序的方法,但时间复杂度为O(n^2). 代码 import java.util.Arra ...

  6. RxJava(一):响应式编程与Rx

    一,响应式编程 响应式编程是一种关注于数据流(data streams)和变化传递(propagation of change)的异步编程方式. 1.1 异步编程 传统的编程方式是顺序执行的,必须在完 ...

  7. Spring Boot ERROR StatusLogger No Log4j 2 configuration file found

    1. 问题描述 项目之前的 log4j2 配置没问题,把 pom 文件中的 spring-boot-starter-web 依赖删除后,然后启动项目就报错找不到 log4j2.yml 文件. 之前引用 ...

  8. Python中Bool为False的情况

    在python中,以下数值会被认为是False: 为0的数字,包括0,0.0空字符串,包括'', ""表示空值的None空集合,包括(),[],{}其他的值都认为是True. No ...

  9. nginx 部署前端项目(vue)

    前提:安装好nginx 打开nginx目录,一般是(/usr/local/nginx) npm run build 打好vue包 一般放到(/usr/local/nginx/html/)目录下 配置: ...

  10. C++ STL——map和multimap

    目录 一 map和multimap 注:原创不易,转载请务必注明原作者和出处,感谢支持! 一 map和multimap map相对于set的区别:map具有键值和实值,所有元素根据键值自动排序.pai ...