Search Unity

  1. Unity 6 Preview is now available. To find out what's new, have a look at our Unity 6 Preview blog post.
    Dismiss Notice
  2. Unity is excited to announce that we will be collaborating with TheXPlace for a summer game jam from June 13 - June 19. Learn more.
    Dismiss Notice
  3. Dismiss Notice

Bug BatchRendererGroup random crash when adding new render object with material properties changed

Discussion in 'Graphics for ECS' started by furm, Dec 4, 2023.

  1. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    When using the batchrenderergroup on a mobile device, I encountered an issue that could cause the application to freeze and eventually crash. It happens on 2022.3.0 - 2022.3.14 URP
    Code (CSharp):
    1. void Start()
    2. {
    3.     m_BatchRendererGroup = new BatchRendererGroup(OnPerformCulling, IntPtr.Zero);
    4.     return;
    5. }
    6.  
    7. void Update()
    8. {
    9. //Test code for adding new cube
    10.     for (int i = 0; i < 200; i++)
    11.     {
    12.         var obj = Instantiate(cube,transform);
    13.     }
    14. }
    15.  
    16. public JobHandle OnPerformCulling(BatchRendererGroup rendererGroup, BatchCullingContext cullingContext, BatchCullingOutput cullingOutput, IntPtr userContext)
    17. {
    18.     return new JobHandle();
    19. }
    After create a BatchRendererGroup, all you need is keep adding new render object (such as cubes) to the scene. The application will freeze and then crash after reaching a certain quantity.
    The probability of crash depends on device, the better the lower, so sometimes app will die lack of memory before freeze. But it do occur on almost every device we tested.

    This is the stack just before crash.
    image-2023-11-28-13-22-03-902.png
    I wonder if this is a bug or it is not allowed to use batchrenderergroup this way.
    Please reply to me asap, thx.
    PS. sorry for the pool English...
     
  2. LorinAtzbergerUnity

    LorinAtzbergerUnity

    Unity Technologies

    Joined:
    Apr 11, 2023
    Posts:
    17
    Hello.

    It seems like you are not using the BatchRendererGroup the way it was meant to be used. It is not meant to be used with GameObjects directly and instead you're supposed to upload all the data and prepare the draw commands yourself. Please refer to this article: https://blog.unity.com/engine-platform/batchrenderergroup-sample-high-frame-rate-on-budget-devices

    In your code, it seems you're instantiating 200 cubes on every update but aren't ever destroying them so they add up and eventually cause the runtime to crash because of memory constraints.
     
  3. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    Thank you for the reply. This code is just a demo to show how to reproduce crash. Original project is quite large. In fact, I use brg to draw static scenes with self prepared data , I also baked my own occ data and added complex logic in OnPerformCulling funciton. But when I together add some dynamic objects like characters use triditional way, crash occurs. It took me quite a long time to finally locate the problem. It seems that once m_BatchRendererGroup = new BatchRendererGroup(OnPerformCulling, IntPtr.Zero);
    is used,it will crash after you add game object to the scene.
    And I can tell difference between my issue and memory constraints.Its just a demo.
     
    Last edited: Dec 4, 2023
  4. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    By the way ,if you dispose BatchRendererGroup obj and recreate it every single frame, crash can be avoided. While its not a good solution, it make me doubt if there is some unexcepted mem access ?
     
  5. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    When this issue occurs, it first freeze the screen for a longtime, meanwhile memory begin to increase, finally app crash for lack of memory
     
  6. LorinAtzbergerUnity

    LorinAtzbergerUnity

    Unity Technologies

    Joined:
    Apr 11, 2023
    Posts:
    17
    You're not supposed to create and dispose BRGs every frame. While that's a valid code path, it's definitely not what is intended.
    I'm afraid I have you all the feedback I could given the code snippet you pasted. If you need more support you're going to have to create an example where the issue reproduces. Just last week I made a demo with game objects and BRG rendering and it does work well with the latest 2022 version.
     
  7. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    Problem solved. When adding new object, change material property will cause crash.
    Code (CSharp):
    1. using System.Collections.Generic;
    2. using UnityEngine;
    3. public class test : MonoBehaviour
    4. {
    5.     public GameObject cube;
    6.     private Queue<GameObject> q;
    7.  
    8.     private const int cap = 20000;
    9.  
    10.     void Start()
    11.     {
    12.         q = new Queue<GameObject>(cap);
    13.         for (int i = 0; i < cap; i++)
    14.         {
    15.             var obj = Instantiate(cube,transform);
    16.             obj.transform.position = cube.transform.position + new Vector3(Random.Range(-5f, 5f),Random.Range(-5f, 5f), Random.Range(-5f, 5f));
    17.             q.Enqueue(obj);
    18.         }
    19.     }
    20.  
    21.     // Update is called once per frame
    22.     void Update()
    23.     {
    24.         for (int i = 0; i < 200; i++)
    25.         {
    26.             DestroyImmediate(q.Dequeue());
    27.             var obj = Instantiate(cube,transform);
    28.             obj.transform.position = cube.transform.position + new Vector3(Random.Range(-5f, 5f),Random.Range(-5f, 5f), Random.Range(-5f, 5f));
    29.             q.Enqueue(obj);
    30.         }
    31.     }
    32. }
    Code (CSharp):
    1. using UnityEngine;
    2.  
    3. // add this script to cube
    4. public class testMat : MonoBehaviour
    5. {
    6.     private Material m;
    7.     private MeshRenderer mr;
    8.     private int id = Shader.PropertyToID("_BaseColor");
    9.     private MaterialPropertyBlock mpb;
    10.  
    11.     void Start()
    12.     {
    13.         // Crash
    14.         m = GetComponent<MeshRenderer>().material;
    15.         m.SetColor(id,Color.blue);
    16.      
    17.         // Crash again
    18.         //mr = GetComponent<MeshRenderer>();
    19.         //mpb = new MaterialPropertyBlock();
    20.         //mr.GetPropertyBlock(mpb);
    21.         //mpb.SetColor(id,Color.blue);
    22.         //mr.SetPropertyBlock(mpb);
    23.     }
    24. }
    25.  
    Once you use m_BatchRendererGroup = new BatchRendererGroup(OnPerformCulling, IntPtr.Zero) in your proj, crash occurs with test code. Any idea?
    I tested mpb instead, but still crash. Wonder if this is a bug or change mat properties is not allowed to use with brg?
    PS, try build apk with development build , crash probability is low with a release build.
     
    Last edited: Dec 12, 2023
  8. furm

    furm

    Joined:
    Apr 24, 2016
    Posts:
    13
    Test mpb again, change mpb to static is ok, with mpb create once, crash prob is close to zero. I will use this solution for now,