Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Resolved DynamicBuffer allows getting elements at negative indices. EDIT: due to safety checks being disabled

Discussion in 'Entity Component System' started by Rupture13, Sep 14, 2022.

  1. Rupture13

    Rupture13

    Joined:
    Apr 12, 2016
    Posts:
    129
    Today I experienced that trying to get an element at a negative index of a DynamicBuffer works "perfectly fine" in the sense that it doesn't throw an exception. As far as I can see, internally the index function first calls the
    CheckBounds(index)
    function, which only seems to check for the upper bound (i.e. index cannot be equal to or greater than buffer length). So what I think happens is that it takes the memory before the buffer pointer and makes interprets it as a buffer element, essentially reading junk data as if it is a valid buffer element.

    This to me seems like unintended behaviour, as I'd expect a good old
    IndexOutOfRangeException
    . Getting junk data without an error seems like something that would increase the possibility of mistakes flying under the radar and slipping into the code unnoticed.
     
    StickyKevin, xVergilx and StickyJordi like this.
  2. julian-moschuering

    julian-moschuering

    Joined:
    Apr 15, 2014
    Posts:
    529
    Did you try it? CheckBounds casts to uint which results in everything below 0 being above int.MaxValue.
    For me accessing -1 (from non-burst) gives `Index -1 is out of range in DynamicBuffer of '1' Length.`
     
    Last edited: Sep 14, 2022
    Rupture13 likes this.
  3. Rupture13

    Rupture13

    Joined:
    Apr 12, 2016
    Posts:
    129
    Hmmm, I see the uint cast and it should indeed work as intended.

    However, that CheckBounds function doesn't seem to get called for me at all, even when trying to access elements beyond the length (which is weird because I think I remember having gotten errors from that before).

    The method does have two ConditionalAttributes for
    ENABLE_UNITY_COLLECTIONS_CHECKS
    and
    UNITY_DOTS_DEBUG
    , so I added those to the Scripting Define Symbols in the Player Settings, but I still can't get the exception to be thrown :confused:

    So there doesn't seem to be a bug in the DynamicBuffer's index or CheckBounds functions, but I still don't know why I'm not getting the errors.

    I'm working from a bursted job, so I'll check to see if that makes any difference.
     
  4. Anthiese

    Anthiese

    Joined:
    Oct 13, 2013
    Posts:
    72
    I don't think adding that define to Player Settings affects what Burst emits.
    The normal method for adding safety checks to Bursted jobs is:
    "Jobs > Burst > Safety Checks > On" (or "Force On")
     
    xVergilx and Rupture13 like this.
  5. Rupture13

    Rupture13

    Joined:
    Apr 12, 2016
    Posts:
    129
    Alright, that indeed was the issue.
    The exception works fine and is thrown if either called from non-burst or from burst with safety checks enabled.
    Thanks everyone for helping me clear that up! :)