Search Unity

Bug Dynamic buffers become corrupted

Discussion in 'NetCode for ECS' started by skiplist, Jul 15, 2021.

  1. skiplist

    skiplist

    Joined:
    Nov 9, 2014
    Posts:
    47
    I've been having a problem with garbage data appearing in dynamic buffers on the client, and after finally getting something more reproducible I think I found the problem.

    This is around line 576 in GhostReceiveSystem.c:

    Code (CSharp):
    1. buf.ResizeUninitialized((int)newCapacity);
    2. //Move buffer content around (because the slot size is changed)
    3. var sourcePtr = (byte*)buf.GetUnsafePtr() + GhostSystemConstants.SnapshotHistorySize*slotCapacity;
    4. var destPtr = (byte*)buf.GetUnsafePtr() + GhostSystemConstants.SnapshotHistorySize*newSlotCapacity;
    5. for (int i=0;i<GhostSystemConstants.SnapshotHistorySize;++i)
    6. {
    7.     destPtr -= newSlotCapacity;
    8.     sourcePtr -= slotCapacity;
    9.     UnsafeUtility.MemMove(destPtr, sourcePtr, slotCapacity);
    10. }
    11. slotCapacity = newSlotCapacity;
    Both sourcePtr and destPtr doesn't take into account the buffer header so the buffer is corrupted after the copy.

    After adding the header size to those two pointers I stopped getting corrupted values:

    Code (csharp):
    1.  
    2. var sourcePtr = (byte*)buf.GetUnsafePtr() + SnapshotDynamicBuffersHelper.GetHeaderSize()+ GhostSystemConstants.SnapshotHistorySize*slotCapacity;
    3. var destPtr = (byte*)buf.GetUnsafePtr() + SnapshotDynamicBuffersHelper.GetHeaderSize()+ GhostSystemConstants.SnapshotHistorySize*newSlotCapacity;
    4.  
    Also, there is a variable baselineDynamicDataPtr in the same file that seems to refer to that buffer. It looks like it might be used after the buffer reallocation, but not sure.
     
  2. CMarastoni

    CMarastoni

    Unity Technologies

    Joined:
    Mar 18, 2020
    Posts:
    895
    Hi Skiplist,

    There were some bug in relation to dynamic buffer in 0.6-preview-7. One of them was exactly here (the memory was not moved correctly).
    Has been already fixed (amoung others) in later version of NetCode. So sorry we didn't ship yet a new update in a while.
    The baselineDynamicDataPtr is used to decompressed the snapshot sent by server in case it is delta-compressed.
    In relation to baselineDynamicDataPtr there was another problem (again, already fixed) that was causing reading memory from a release memory location, ending in garbage data inside the buffer.

    I attached a diff with all the changes (not many) in case you need to locally fix also these.
     

    Attached Files:

    skiplist likes this.
  3. skiplist

    skiplist

    Joined:
    Nov 9, 2014
    Posts:
    47
    Thanks, that is very helpful. With this fixed I'm pretty happy with 0.6, but if we can get access to something newer soonish that would still be nice :)