Search Unity

Double support for Burst compiler and new math library

Discussion in 'Data Oriented Technology Stack' started by rz_0lento, Mar 5, 2018.

  1. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    In this video

    Joachim mentioned that there is a new math library involved with the new compiler tech but I only saw mentions about floats, half floats, float/4. This really puzzles me, is Unity still going neglect doubles? I really hope new math library will take Unity up to date and finally fully support doubles too, at least for non-mobile platforms.

    Additionally, I'd love to have (optional) scene transforms in doubles too but I doubt that will happen anytime soon as PhysX can only handle single precision floats. There are other physics engines out there that do handle doubles (Bullet for one) and it would be great to be able to keep the scene in higher precision without obvious issues when going furher away from origin. This would be especially cool now that HD Render Pipeline will have camera relative rendering as these things combined would be perfect match for huge open world games.
     
    Last edited: Mar 22, 2018
    Can-Baycay likes this.
  2. xoofx

    xoofx

    Unity Technologies

    Joined:
    Nov 5, 2016
    Posts:
    268
    The new math library will initially support what was provided by the previous math library (Vector4...) and what is actually used by the engine, so it will focus mainly on single precision floats (fp32). I don't see this changing easily soon as GPUs fp32 operations are still several times faster than fp64 operations, both in terms of compute and bandwidth (and this applies also to CPU as they can hold more fp32 registers values). Many datas passed to the GPU are not even using fp32 but fp16.

    That being said, while it is not currently planned, we may also provide support for fp64 SIMD types and math instructions
     
    Lars-Steenhoff likes this.
  3. strich

    strich

    Joined:
    Aug 14, 2012
    Posts:
    288
    Indeed I don't think anyone would debate doubles as a default format for performance reasons. However the perf loss can often be a worthwhile trade-off for certain games and supporting it as optional as suggested by OP would be quite nice for those who want to.
     
    Noisecrime likes this.
  4. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    Actually, I wouldn't even mind the lossy conversion into single precision for the camera since the camera gets values on it's origin on HD Render Pipeline, it will always appear accurate enough near origin in floats. But for example I've made my own physics math in doubles for a while already and it's plenty fast for the purpose I'm using it for.

    There are actually two different things at this discussion, other is the support for doubles in the new math lib and other is the overall support for doubles to describe the unity world. I realize latter is probably still many years off atm but would like to see the road paved for it by getting doubles taken into account on math lib, even if it means they will not get special SIMD perf improvements (you'd need AVX to be able to do four wide double math anyway). There are still people who need the additional precision for various custom physics things and having official support in the math lib would just mean they could keep using the already familiar math lib from Unity if it was supported.
     
  5. snacktime

    snacktime

    Joined:
    Apr 15, 2013
    Posts:
    2,622
    I don't think most the reasons I've seen over the years for wanting doubles were fully thought out. There is just almost always a simpler way to solve that problem then doubling the amount of data you throw around. Especially at the feature level.

    For example I'd favor moving to a system where physics was more loosely coupled to game objects. So you could then conceivably just be able to change the physics origin. Probably still a chunk of work to do that, but almost anything is better then going doubles. Even floating origin is a simpler solution at the end of the day by the time you account for everything (which most don't).
     
  6. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    In the end, floats are really imprecise and basic math in doubles isn't really THAT much more expensive. Use of floats is a compromise made decades ago for video games, based on tech limitations from that era.

    Sure, they are still faster due to less cache misses and more efficient SIMD optimizations but you can't get any precision with them once you are further from the origin. Just look at almost any fps game out there which doesn't have a tiny level, player hand and gun aren't usually in perfect sync all the time. This and many other jitter / movement differences are rooted on floats bad precision. Only way to fully avoid it with floats is if you do all animation and rendering at the world origin.

    It would be unfair to say that all of the games would benefit from double precision but it would be something modern game engine should support at this date IMO as there surely are plenty of use cases, even beyond large open worlds.

    "Better" is again, one opinion amongs others. Some prefer working with lower accuracy (when good enough for the task at hands) or just simply don't care. People doing more accurate sims would welcome double support right away.

    Currently, due to how Unity is built, you have two options really when it comes to rendering a larger world: You occasionally move every object near the camera to the origin, or just always keep the player in the origin and move the whole world around you. Both are really inefficient due to the cost of constantly moving every transform, remember that you need to even move every particle along the world.

    At the moment you would also need to move every collider and rigidbody as well, which is pretty costly operation and it additionally prevents some caching operations from physics engine side, making the whole physics sim less efficient. PhysX itself has origin shifting functionality (which isn't exposed to Unity afaik) but like mentioned before, there are physics engines that can simulate on doubles already. I also wouldn't worry too much about the physics perf on doubles unless you do some mass destruction with them, regular game use cases are just fine with them.

    Worth noting that you can already use third party physics engine with Unity that runs on doubles with custom integration (which I'm doing already), but it's kinda sad that you can't use the built-in Unity math libraries for your games double math at all, that's actually the whole point of the original post: to get same support for double math operations as for floats, half floats, float/4 etc. It wouldn't need to be as optimized, just wish they wouldn't totally neglect it from generic game math operations again.
     
    strich likes this.
  7. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    Changed the thread name to fit the topic better and edited the first line of the original post now that this topic has been moved into appropriate forum section (I wasn't initially sure where to post as ECS & Job forum section didn't exist yet).
     
  8. Enrico-Monese

    Enrico-Monese

    Joined:
    Dec 18, 2015
    Posts:
    56
    @rizu Physics origin can be set in Physics settings and also by code
     
  9. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    I know you can change world bounds center from project settings but I haven't seen anything under Physics that lets you move the origin itself at runtime.

    Edit-> nevermind, it's part of https://docs.unity3d.com/ScriptReference/Physics.RebuildBroadphaseRegions.html

    Does that actually change physx origin? Docs aren't super clear on it
     
  10. ioesten

    ioesten

    Joined:
    Feb 19, 2018
    Posts:
    11
    I, too, really would appreciate double4 etc and better double resolution support in Unity as soon as possible. With the amount of AR with real world coordinates, double resolution support is more that 'nice to have'. I am dealing with high detail real world coordinates all the time, so yes please, endorsing rizu's request.
     
  11. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
  12. rz_0lento

    rz_0lento

    Joined:
    Oct 8, 2013
    Posts:
    1,422
    Just noticed that latest Mathematics 0.0.12-preview.11 has now initial support for doubles :) Thanks Unity!
     
  13. deplinenoise

    deplinenoise

    Unity Technologies

    Joined:
    Dec 20, 2017
    Posts:
    23
    We will support doubles, but make no special effort to optimize them.

    Although more complex, it is usually better to restructure large world games to use a virtual coordinate with a high-precision local coordinate box around the origin and cache the relevant parts of the virtual world in this space as needed. Also note that world->view homogeneous transforms can be computed without worrying about the virtual world space coordinates.

    Floats in a locally cached coordinate system like this have vastly more precision than what matters for on-screen rendering anyway. Most GPUs use 8-bit subpixel precision for vertices in the rasterizer.
     
    Antypodish likes this.
  14. suityn

    suityn

    Joined:
    Nov 19, 2015
    Posts:
    9
    it would be enough if.

    Transform uses doubles coordinates.
    3D meshes uses floats as now

    3D verticies floats are relative to object, so no need for doubles as is expected to be close to it.

    When you render with a camera, you do the same as now, but you make a first step, Object transform (double precission) - Camera transform (double precision) and cast it to float precision. This shouldnt cost much to an actual GPU, even if they are doubles.

    There you go

    Your coordinate box around origin workaround sounds nice until you deal with unity stuff that uses global coordinates instead relative ones, like navigation, as an example.
     
  15. snacktime

    snacktime

    Joined:
    Apr 15, 2013
    Posts:
    2,622
    Normally what's done here is you have a 2d grid using doubles that represents your world. You then partition that into another 2d grid where each cell represents the max distance from origin you want the client to work with. Say 5000 meters. Now you assign a unique id to every cell in that second grid.

    Server and client keep track of which cell the client is in. So the client is always sending coordinates to the server in the range 0 to 5000. It's aware of the larger world grid but it only uses it to calculate which partition it's in.

    You can cleanly abstract that out so none of your game logic has to deal with it. Just do the translations in pre and post serialization hooks on both client and server.
     
unityunity