Announcement

Collapse
No announcement yet.

Civilization: Beyond Earth Overcoming Linux GPU Driver Problems

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • #41
    Originally posted by emblemparade View Post
    Yes, Direct3D is significantly easier to work with with than OpenGL/ES: more coherent API and better tools (some would say much better). Various historical reasons for this, but the most important one is that D3D has never been collaborative: MS could always control the spec, which made it straightforward. Meanwhile, OpenGL is made up out of a lot of extensions, which according to spec may or may not be available on any particular device. This is a nightmare for programmers, because it means you have to test for the availability of certain features and then decide what to do if they are not available. This could mean coding two, three or even more versions of each particular workflow, and of course having to test and maintain each. At some point you may want to throw your hands up in despair and just target the lowest common denominator, which means you will not be able to leverage advanced features.
    Since you're experienced with this, can you give an example of "extension nightmare"?

    Comment


    • #42
      Originally posted by Ancurio View Post
      Since you're experienced with this, can you give an example of "extension nightmare"?
      A few I yanked from current code:

      GL_ARB_texture_rectangle

      Without it, all textures must be square. In some cases, this could be a waste of GPU RAM (although... some drivers actually support this extension but still reserve RAM as if it were a square), in which case you'd want to pack multiple images into a single texture. Your code of course will have to be designed for both possibilities.

      Also, when you use the extension, texcoords are on the scale of your dimensions. If you don't use the extension, they are on a scale of 0 to 1. So ... you will need two different GLSL shaders for each case (for all cases!), or else pass some kind of scaling var (as a uniform).

      This issue is a huge pain. You'd think this extension would be available everywhere, but you can't assume so if you stick to the spec, and still want to support older versions of OpenGL (older Macs, open source Linux drivers). And of course it's not available in most versions of OpenGL ES.

      GL_EXT_texture_filter_anisotropic

      Not too bad -- without this, you can't call glTexParameterf with GL_TEXTURE_MAX_ANISOTROPY_EXT. Do you still want to support anistropic filters? You might have to implement yourself with a shader, then. Or just don't support the feature.

      GL_ARB_texture_multisample

      Without this, you can't support MSAA in framebuffers. Again, you could implement a shader for this.

      Supporting OpenGL ES is another huge pain, because so many other important features are not available:

      * 2D Array textures. So, no simple texture atlases! I've created an abstraction layer that allows packing textures into a single texture (rect or 2D), so that it would work whether the feature is support or not. There's a lot of code here: loading the textures from PNG, optimizing using a bin-packing algorithm, and of course keeping track of the coordinates and scaling factors. All totally unnecessary if the feature were supported.
      * Single channel textures. Not a big deal -- but could be a nice memory saver if you're using textures for things like specular light maps (which would only need a single channel, not the 3 RGB channels). Since I want to be able to support this optimization, I have to allow for both options.
      * Row-major matrices. OpenGL ES supports only column-major. You could standardize on that, or you could allow for support for both via simple translation within your engine. I opted for the latter.

      I can't wait for OpenGL ES to die. Very excited about the Tegra K1, and hope it's a sign that we will be able to target OpenGL in the future, even for mobile.

      All the above are really minimal features, but have cost me many hours in coding and testing on various platforms. You can say that it's my fault for building an engine from scratch rather than using a ready-made one -- but in any case, this is the kind of stuff that all engines have to deal with. And I'm not even getting into advanced stuff that would affect stencils for shadows and lights!

      Comment


      • #43
        I only worked with OpenGL on PC.
        Of course if you chose to use a very low OpenGL version you depend on many extensions. But most of that stuff is integrated in non rusty versions. E.g. GL_ARB_texture_rectangle (Core in 3.1), GL_ARB_texture_multisample (Core in 3.2).
        The 3.2 spec was released ~2009.

        What matters more are API only extensions (do not depend on hardware) that remove a lot of the pain.
        Take DSA for example. It finaly became core in 4.5. Its a big difference in how you interact with OpenGL. Mesa and some intel drivers still do not support the ext version.

        Or GL_ARB_multi_bind(Core in 4.4) and GL_ARB_vertex_attrib_binding(Core in 4.3). I tryed to make surrogate functions. Even got a nice abstraction for the vertex bindings. But old style binding textures/buffers is just so stupid and impossible to abstract if you don't want to save all kind of extra informations, just so later you can tell OpenGL what kind of binding target to use... which OpenGL KNOWS.

        Thankfully the last two extensions are supported by all current driver versions. So by depending on them you only exclude shity notebooks that depend on custom drivers that may never get updates.

        But if you are new to OpenGL you also have to invest a lot of time to first learn all about this circumstances*!


        *=shit

        Comment


        • #44
          @emblemparade
          I don't really understand the problem, at least for GL_ARB_texture_rectangle and GL_ARB_texture_multisample. These are mandatory part of OpenGL 3.1 and OpenGL 3.2 respectively. So if your game (or engine) wants to target a specific market (the players with OpenGL 3.0+ compliant GPU for instance) you know what to implement or not. I guess this is exactly what happen in the Direct3D world. A game/engine targets a specific Direct3D revision, and the player must buy a compatible GPU to play.

          I'm not sure if Direct3D have the same optional extensions scheme than OpenGL. Correct me if I'm wrong, I'm not a graphic programmer at all. But what you describe as a pain seems to be just an optional feature of OpenGL : you can use optional extensions if you want.
          Last edited by whitecat; 28 October 2014, 03:24 PM.

          Comment


          • #45
            Originally posted by Kraut View Post
            Thankfully the last two extensions are supported by all current driver versions. So by depending on them you only exclude shity notebooks that depend on custom drivers that may never get updates.
            But I do want to support notebooks and other low-power devices (that are still being made). And why not? Not every game has to do photo-realistic 3D to be great, and weak computers can still be great for some basic 3D gaming. So why not have my engine support that? Targetting only the latest and greatest means that a wide rage of uses is immediately impossible.

            Comment


            • #46
              Originally posted by whitecat View Post
              I'm not sure if Direct3D have the same optional extensions scheme than OpenGL. Correct me if I'm wrong, I'm not a graphic programmer at all. But what you describe as a pain seems to be just an optional feature of OpenGL : you can use optional extensions if you want.
              You are wrong, D3D doesn't have this problem.

              I'll repeat myself for your benefit: 1) if you, as a game designer, decide to require an extension, then you are limiting your audience. 2) if you want to make this usage optional, then you have to program a reliable fallback for those who don't have the necessary hardware or driver support, which is extra work.

              Devs who have been spoiled with D3D consistency are quite horrified when they switch to OpenGL (just read the many exasperated blog posts about it online). But in the end, even if it's extra work, it's worth it: you get cross-platform portability, and are free from MS control over your platform.

              Comment


              • #47
                OK you confirm what I was saying : Direct3D doesn't have extensions. You must match a specific revision.

                The fact is that you can do exactly the same with OpenGL. The OpenGL 3.2 API (for instance) is the same on NVIDIA, AMD and Intel. The implementation is certainly different in some case, but that's another topic, and anyway I guess it's the same problem between Direct3D implementation of NVIDIA, AMD and Intel.

                Comment


                • #48
                  Originally posted by emblemparade View Post
                  But I do want to support notebooks and other low-power devices (that are still being made). And why not? Not every game has to do photo-realistic 3D to be great, and weak computers can still be great for some basic 3D gaming. So why not have my engine support that? Targetting only the latest and greatest means that a wide rage of uses is immediately impossible.
                  I was talking from a PC developer perspective only. And you are still supporting notebooks with this, just not notebooks with shitty driver politics.
                  I think what matters more in this case (For PC) is that many users don't have current drivers installed. Any as a dev you still want your applications to run there anyway. Some years ago valve already talked about the problem that many users use outdated drivers.

                  Comment


                  • #49
                    Originally posted by emblemparade View Post
                    A few I yanked from current code:

                    GL_ARB_texture_rectangle

                    Without it, all textures must be square. In some cases, this could be a waste of GPU RAM (although... some drivers actually support this extension but still reserve RAM as if it were a square), in which case you'd want to pack multiple images into a single texture. Your code of course will have to be designed for both possibilities.

                    Also, when you use the extension, texcoords are on the scale of your dimensions. If you don't use the extension, they are on a scale of 0 to 1. So ... you will need two different GLSL shaders for each case (for all cases!), or else pass some kind of scaling var (as a uniform).

                    This issue is a huge pain. You'd think this extension would be available everywhere, but you can't assume so if you stick to the spec, and still want to support older versions of OpenGL (older Macs, open source Linux drivers). And of course it's not available in most versions of OpenGL ES.

                    GL_EXT_texture_filter_anisotropic

                    Not too bad -- without this, you can't call glTexParameterf with GL_TEXTURE_MAX_ANISOTROPY_EXT. Do you still want to support anistropic filters? You might have to implement yourself with a shader, then. Or just don't support the feature.

                    GL_ARB_texture_multisample

                    Without this, you can't support MSAA in framebuffers. Again, you could implement a shader for this.

                    Supporting OpenGL ES is another huge pain, because so many other important features are not available:

                    * 2D Array textures. So, no simple texture atlases! I've created an abstraction layer that allows packing textures into a single texture (rect or 2D), so that it would work whether the feature is support or not. There's a lot of code here: loading the textures from PNG, optimizing using a bin-packing algorithm, and of course keeping track of the coordinates and scaling factors. All totally unnecessary if the feature were supported.
                    * Single channel textures. Not a big deal -- but could be a nice memory saver if you're using textures for things like specular light maps (which would only need a single channel, not the 3 RGB channels). Since I want to be able to support this optimization, I have to allow for both options.
                    * Row-major matrices. OpenGL ES supports only column-major. You could standardize on that, or you could allow for support for both via simple translation within your engine. I opted for the latter.

                    I can't wait for OpenGL ES to die. Very excited about the Tegra K1, and hope it's a sign that we will be able to target OpenGL in the future, even for mobile.

                    All the above are really minimal features, but have cost me many hours in coding and testing on various platforms. You can say that it's my fault for building an engine from scratch rather than using a ready-made one -- but in any case, this is the kind of stuff that all engines have to deal with. And I'm not even getting into advanced stuff that would affect stencils for shadows and lights!
                    Thanks for your input. Please don't regard anything I'm about to write as an attack, I'm just trying to clarify and discuss various scenarios.

                    About rectangle textures specifically, I think you might have interpreted the spec a little wrong. Old OpenGL versions did indeed have limitations on texture dimensions, mostly that each side had to be a power of two, but both didn't have to be the same, so there was never a "square" limitation. I'm not sure about desktop OpenGL, but OpenGL ES 2.0 guarantees you NPOT functionality (the only limitation being that you can't set a repeating wrap mode for them), and I'm pretty sure any hardware capable of D3D9 supports them (please correct me if I'm wrong). Going by the D3D9 documentation, there is no POT restriction on textures, so if you're target systems without POT support, you're effectively targeting pre D3D9 hardware, and as such if you had developed your engine using Direct3D, you'd have two code paths (one for D3D9 and one for pre) all the same. Again, please correct me on this if I'm wrong.

                    As for your other examples, I'd like to ask you, do you know with which Direct3D version equal functionality is supported? So, in a scenario where you would develop against Direct3D instead of OpenGL, what would you do if you required certain functionality that was part of Direct3D version X, but on the system only D3D version X-1 was available? You would have the exact same dilemna: Do I create two code paths, one per D3D version? And how would that differ from the OpenGL situation, where you can at least fall back to alternative implementations?

                    For example, in my own project, I require OpenGL 2.0 + FBO extensions. If FBO extensions are not present, my engine cannot run at all. Now, one might say "see, you can't even rely on version 2.0 to deliver the needed functionality", but in practice, any hardware that supports Direct3D 9.0c effectively supports OpenGL 2.0 as well as FBOs, so if FBO extensions aren't available, the hardware is either below D3D9 level (in which case no game created in the last ~6 years would work on it as well), or the driver writers did a horrible job (which is really nothing Khronos can enforce).

                    Comment


                    • #50
                      Originally posted by Ancurio View Post
                      Old OpenGL versions did indeed have limitations on texture dimensions, mostly that each side had to be a power of two, but both didn't have to be the same, so there was never a "square" limitation. I'm not sure about desktop OpenGL, but OpenGL ES 2.0 guarantees you NPOT functionality (the only limitation being that you can't set a repeating wrap mode for them)
                      You are correct -- I oversimplified by using the term "square" because I didn't want to get into the sticky details. But ... note that if you are supporting OpenGL ES before version 2.0 (virtually all current devices?), then this problem still exists.

                      Originally posted by Ancurio View Post
                      As for your other examples, I'd like to ask you, do you know with which Direct3D version equal functionality is supported?
                      I'm afraid I don't have recent hands-on experience. Years ago, when I decided to switch to free operating systems and focus on open standards, I just lost interest in investing in MS-owned technologies. The closet I've done recently is this project, which is an OpenGL/D3D bridge. But very minimal D3D work there, just some buffer issues.

                      Generally, I would say that "functionality" is usually wrong to attribute to APIs, at least in OpenGL. There have been a few real advances over the years, of course, but often it's more about conveniences for devs. The rect/square issue above is a perfect example. But once shaders became standard in D3D and OpenGL, that was pretty much it in terms of major features. What has improved dramatically is APIs that improve performance, which indirectly have allowed more features in games. But, those features could have been done with older APIs, too.

                      MS did a good thing in standardizing the API together with the hardware. So, when you buy a GPU, you know that it supports "D3D 11", and that means all those features. A game can simply advertise that as a requirement and you know you're good. OpenGL is more fragmented, especially when you add OpenGL ES to the mix. Even the most recent OpenGL 4.4 has some optional extensions (very cool stuff from NVIDIA), so putting a "OpenGL 4.4 capable" label on a GPU is still not enough information about what it's capable of doing.

                      Originally posted by Ancurio View Post
                      but on the system only D3D version X-1 was available? You would have the exact same dilemna: Do I create two code paths, one per D3D version? And how would that differ from the OpenGL situation, where you can at least fall back to alternative implementations?
                      You're right -- the difference is in degree, not in kind. These problems seem to be an order of magnitude more painful in OpenGL, with many more versions and extensions. BTW, I totally skipped over the whole issue of GLSL versions, the most baffling aspect of OpenGL advances. Why break the shader language with almost every release? My current project has four versions of each shader.

                      I discuss some of these issues in this blog post.

                      Comment

                      Working...
                      X