中文第一计算机图形学社区OpenGPU 版权所有2007-2018

 找回密码
 注册

扫一扫,访问微社区

搜索
查看: 2162|回复: 8

请教一个TBDR实现的问题

[复制链接]
发表于 2016-11-7 15:57:24 | 显示全部楼层 |阅读模式
本帖最后由 chuckson 于 2016-11-7 16:04 编辑

  最近大致了解了TBDR:
  TBDR就是把Render Target分成多个size较小的Tile(例如32x32),对于一帧的所有triangle,测试出它们与所有tile的覆盖情况,然后逐个Tile地,对覆盖该Tile的每个triangle进行raster,这样可以在on-chip上放z-buffer和color buffer,在整一帧的Raster过程中不需要访问framebuffer,再加上DR的效果,有效减少了带宽压力。
  但有个问题一直不明白:
  既然每个Tile都有可能用到整一帧所有triangle(经过Shader各种计算后输出)的信息,那在实现TBDR的硬件里面,triangle的数据是在pipeline里buffer住的吗:
  (1)如果不buffer住,让driver重复送draw command,那么如果屏幕上有100个tile的话,一帧的所有triangle都要让Shader执行100次,performance降低太多
  (2)如果buffer住,一帧的triangle数量可能是成千上万的,每个顶点有多个attributes,为了TBDR增加这么大的芯片面积也不现实
  (3)把一帧的三角形分成多个子帧吗?那画个子帧的第一个Tile结束后,on-chip上的Z buffer总得写回framebuffer上去吧,毕竟下一个子帧画第一个Tile时是要用到的(第一个子帧跟第一个子帧属于同一个场景,需要用前面结果来做z test),这样岂不是只有第一个子帧支持TBDR了?
  求指点

发表于 2016-11-9 14:16:50 | 显示全部楼层
在绘制一个tile的时候不是每个triangle都参与计算的。只有那些有交集的才会。
发表于 2016-11-9 14:58:51 | 显示全部楼层
是buffer住的,只不过不是在片上,而是存在内存里
 楼主| 发表于 2016-11-9 16:00:50 | 显示全部楼层
hotdog 发表于 2016-11-9 14:16
在绘制一个tile的时候不是每个triangle都参与计算的。只有那些有交集的才会。 ...

对的,Raster一个tile时用到的triangle可能很少,但这一帧所有的triangle数据都得一直放buffer里,毕竟raster其他tile可能用到。
 楼主| 发表于 2016-11-9 16:07:28 | 显示全部楼层
本帖最后由 chuckson 于 2016-11-15 15:48 编辑
浙滨 发表于 2016-11-9 14:58
是buffer住的,只不过不是在片上,而是存在内存里

我也觉得triangle太多的时候放到内存没法避免了。查了一下,PowerVR也是这么做的:Raster里做edge setup跟z test,在texture之前才做pixel的attribute差值,都是从memory读Vertex数据

但是如果不使用TBDR(IMR),shader输出的triangle数据都是放在片上缓存的,读取速度很快。实现TBDR并且triangle过多时则需要放到memory里。
1)TBDR的初衷是减少memory的访问,triangle过多memory的访问反而增加了。当然有增有减看最终trade off的结果,但triangle越多功耗越大
2)DR剔除遮挡Pixel减少了Pixel Shader的运算量,但一个大triangle可能覆盖多个Tile,这样一来Raster要对同一个triangle setup多次,拉低Performance,也是Trade off
所以,可以认为TBDR不适合triangle密集型的场景吗?




本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
发表于 2016-11-9 16:45:17 | 显示全部楼层
chuckson 发表于 2016-11-9 16:07
我也觉得triangle太多的时候放到内存没法避免了。但是如果不使用TBDR(IMR),shader输出的triangle数据都 ...

你分析得有道理
TBDR通过on-chip blending和kill overdraw可以节约带宽,但是中间缓存的display list确实带来了额外开销的。当然这部分是可以优化的,比如说用strip形式缓存,采用一些压缩算法等。
关于triangle setup,其实大部分工作可以一个三角形做一次,可以在多个tile之间共享。当然这要求把这些额外setup的参数也缓存起来,会带来额外带宽消耗。具体硬件会怎么做我也不太清楚。
 楼主| 发表于 2016-11-11 14:17:25 | 显示全部楼层
本帖最后由 chuckson 于 2016-11-13 15:03 编辑
浙滨 发表于 2016-11-9 16:45
你分析得有道理
TBDR通过on-chip blending和kill overdraw可以节约带宽,但是中间缓存的display list确实 ...

搜到了Imagination压缩display list的专利,寄存器,命令等状态也得保存在Display list里边

Vertex Attribute被做了压缩,附上附件,有兴趣的可以看下。





本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
发表于 2016-11-14 10:01:41 | 显示全部楼层
chuckson 发表于 2016-11-11 14:17
搜到了Imagination压缩display list的专利,寄存器,命令等状态也得保存在Display list里边

Vertex Attri ...

感谢分享
 楼主| 发表于 2016-11-15 15:48:00 | 显示全部楼层
本帖最后由 chuckson 于 2016-11-15 15:51 编辑

    关于场景primtive过多可能导致display list overflow的问题
    最近看了PowerVR一篇2001年的专利(附件),那时候Memory size有限,给display list用的memory可能无法存下所有primitive,这种情况PowerVR确实像帖子里的case3,即一旦存满了就把数据flush给ISP,TSP去render,叫Partial Render,因为只是子帧。每个tile结束后要把local的z/frame buffer store到System memory里边去。除第一个子帧外,其他子帧在render都要把z/frame buffer从system memory load到local memory。这种方法解决了memory overflow的问题,同时也不可避免地加大了带宽。
  另外,为了让memory尽快被release让后面的子帧利用,将多个Tile拼成一个macro tile,覆盖每个macro tile的primtive都被存在display list里,只要一个macro tile的render结束,它就可以被release以供剩余子帧利用,这样就避免了使用double display list隐藏延时。










本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
您需要登录后才可以回帖 登录 | 注册

本版积分规则

关于我们|小黑屋|Archiver|手机版|中文第一计算机图形学社区OpenGPU

GMT+8, 2018-4-19 19:50 , Processed in 0.042256 second(s), 20 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表