Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

glDrawElements with GL_LINES forces gleRunVertexSubmitARM? (or: why drawing wireframes is slow on iOS?)

while doing some tests for a small project for iPhone/iPad that I'm working on, I observed that there is a big CPU performance penalty in drawing wireframes using glDrawElements with GL_LINES.

This is the scenario:

  • a model with 640 vertexes ( 4 floats for position, 3 floats for normals, no alignment problems… all on 4 bytes boundaries )
  • 3840 indexes ( unsigned short )
  • both vertexes and indexes use VBOs ( no VAO )
  • the above model drawn with glDrawElements with GL_TRIANGLES works fine

Then:

  • same model with 640 vertexes
  • 2560 indexes
  • VBOs and no VAO
  • drawn with glDrawElements with GL_LINES triggers continuous calls to gleRunVertexSubmitARM, CPU usage sky rockets...

In both cases the models look as expected and no glErrors around...

It seems that the issue is device dependent. I experience it on an iPhone 3GS and iPhone 4, NOT on an iPad 2 nor the simulators. On an iPad 2 frame-time CPU = 1ms and no calls to gleRunVertexSubmitARM, on an iPhone 4 frame-time CPU = 12ms and continuous calls to gleRunVertexSubmitARM.

Can anyone explain this behaviour or point out what mistakes I might be making?

Any insight is highly appreciated. Thanks in advance,

Francesco

like image 633
Francesco Avatar asked Nov 13 '22 13:11

Francesco


1 Answers

not an easy answer to a not easy question I would say.

Anyway, the reason why 2 devices of the same "family" behave in different ways could depend on many factors.

First of all, they mount different GPUs (I am very sure you know already it so, sorry to state the obvious) which brings the following differences:

  • Iphone 4 and Iphone 3GS mount the same GPU, the PowerVR SGX535
  • IPAD 2 uses the PowerVR SGX543MP2

First of all, the latter is an evolution of the first with a much different throughput and a newer architecture.

This alone does not anyway explain everything, the reason why you notice much more calls to gleRunVertexSubmitARM could be explained to the OpenGL driver implementation performed by PowerVR on its GPUs, most probably the SGX535 GPU driver performs the operations you require over an hook on that function.

Last, but not least, performance wise, drawing with GL_LINES is most of the time very inefficient for several reasons:

  • Does not perform any hidden geometry detection
  • Does not perform any face culling
  • Reading around (and about my own experience of 2-3 years ago), using GL_LINE_WIDTH or GL_LINE_SMOOTH causes the driver to perform a "software" render not using any HW acceleration. This depends on the GPU and its OpenGL driver implementation
  • When a filled polygon is rendered, the driver can optimize the operations with "Hierarchical Depth Buffer", with GL_LINES it cannot (again, this depends a lot on the driver but this is a very common aspect)
  • Some drivers translates your GL_LINES mesh in triangles at the moment of the rendering. This is something I cannot prove but a very common topic with past game engines developers friends.

I hope to have helped you in some way.

Ciao Maurizio

like image 118
Maurizio Benedetti Avatar answered Nov 15 '22 06:11

Maurizio Benedetti