GithubHelp home page GithubHelp logo

sharedarray's Introduction

SharedArray

A SharedArray is a segment of memory that is represented both as a normal C# array T[], and a Unity NativeArray<T>.

It's designed to reduce the overhead of communicating between C# job data in NativeArray and APIs that use a normal array of structs, such as Graphics.DrawMeshInstanced(), by eliminating the need to copy data.

Installation

Minimum Unity version is 2018.4.

To install, grab the latest .unitypackage from the Releases Tab and import it to your project.

Usage

// SharedArray implicitly converts to both managed and native array
SharedArray<Vector4> shared = new SharedArray<Vector4>(8);
NativeArray<Vector4> asNative = shared;
Vector4[] asManaged = shared;

Please see the demo project for a more detailed usage example.

Safety System

Unity's job system has a safety system for reading & writing data (in the Editor only). This catches cases where a data race would occur and warns you about it.

SharedArray works with this safety system, so when you access the data on the main thread, the system knows whether it is safe to read or write, just like using a NativeArray allocated the normal way.

Here's all of the operations that include a check of the safety system.

SharedArray<T> sharedArray;            // created elsewhere 

// These 4 operations will check that no jobs are using the data, in any way
T[] asNormalArray = sharedArray; 
sharedArray.Clear();
sharedArray.Resize(32);
sharedArray.Dispose();

// Enumerating in either of these ways will check if any jobs are writing to the data, but allow other readers
foreach(var element in sharedArray) { }

var enumerator = sharedArray.GetEnumerator();

The safest way to use SharedArray is:

  1. Manipulate data in a C# job, using the NativeArray<T> representation
  2. Convert to a managed array T[] only right before you use it on the main thread.

This is important if you want the safety system to work - if you pass around a reference to the managed representation, you won't get the safety system checks.

You can see this pattern demonstrated in the demo project.

Aliasing

It's possible to have the NativeArray representation of the data be of a different type than the source managed array.

To do so, create the SharedArray with 2 types instead of 1 :

Vector4[] source = new Vector4[64];
SharedArray<Vector4, float4> shared = new SharedArray<Vector4, float4>(source);
NativeArray<float4> native = shared;
Vector4[] asManaged = shared;

The only safety check that aliasing makes is that the types are both unmanaged and the same size.

Why Alias Types ?

Aliasing was made to eliminate the overhead of converting between analogous types in Unity.Mathematics and UnityEngine (such as float4 <-> Vector4 or float4x4 <-> Matrix4x4).

These Unity.Mathematics types have optimizations specific to the Burst compiler, and replace the existing Unity math structs and methods. We want to get the compiler-specific performance advantage of using those new types, without the overhead of converting back from Unity.Mathematics types.

For types that are laid out the same in memory, we can just treat one like the other. Since we do this for the whole array, there is never any conversion between types happening, and thus no overhead - it's just a different "view" on the same memory.

sharedarray's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

sharedarray's Issues

Add WebGL asmdef platforms

Minor request - can you add WebGL to your asmdef platforms?

Seems to be working ok in 2021.3.4f1 even if Jobs are still single-threaded.

FYI - installing via git URL in Package Manager also now works for installation.

Thanks!

Non-blittable data error occurs with the struct contains Boolean in Windows IL2CPP. (Unity2021 and above)

I already have the solution. Just open an issue to let other users know.

Error log

ArgumentException: Object contains non-primitive or non-blittable data.
  at Stella3D.SharedArray`2[T,TNative].Initialize () [0x00000] in <00000000000000000000000000000000>:0 
  at NewBehaviourScript.CreateSharedArray[T] () [0x00000] in <00000000000000000000000000000000>:0 
  at NewBehaviourScript.OnGUI () [0x00000] in <00000000000000000000000000000000>:0 

How to reproduce

I made a simple script to reproduce.

void OnGUI()
{
    if (GUI.Button(new Rect(10, 10, 300, 30), "Create NativeArray A"))
    {
        CreateNativeArray<CustomStructA>();
    }
    if (GUI.Button(new Rect(10, 50, 300, 30), "Create SharedArray A"))
    {
        CreateSharedArray<CustomStructA>();
    }
}

private void CreateNativeArray<T>() where T : unmanaged
{
    Debug.Log("CreateNativeArray " + typeof(T));
    // Create a native array.
    NativeArray<T> nativeArray = new NativeArray<T>(10, Allocator.Persistent);
    nativeArray.Dispose();
}

private void CreateSharedArray<T>() where T : unmanaged
{
    Debug.Log("CreateSharedArray " + typeof(T));
    // Create a shared array.
    Stella3D.SharedArray<T> sharedArray = new Stella3D.SharedArray<T>(10);
    sharedArray.Dispose();
}

public struct CustomStructA {
    public bool booleanVar;
}
  1. Attach the script on a gameobject and build a development build in IL2CPP Windows.
  2. Press the button Create SharedArray A and you will see that creating NativeArray<CustomStructA> worked, but SharedArray<CustomStructA> throwed the exception.

Environment:

  • Unity 2021 LTS and above.
  • Windows IL2CPP (It worked properly with Mono)

How does it happen

There is an Unity issue about the same error but occurs calling NativeArray.Copy.
https://issuetracker.unity3d.com/issues/argumentexception-error-occurs-in-copy-method-of-nativearray-class-when-building-with-windows-il2cpp
I think it is the same internal issue but occured in different functions. Since it fixed in 2022.2.19f1, this issue goes away from Unity 2022 as well.

And there is a dicussion about this issue in 2020
https://forum.unity.com/threads/argument-exception-on-windows-il2cpp-build-with-burst-jobs.836059/
As tertle said, IL2CPP and Burst together may have issues with bools. This is how I found out where the issue was coming from.

Struct with bool fields causes this issue.

Solution / Workaround

Add this attribute [MarshalAs(UnmanagedType.U1)] to your boolean fields.

public struct CustomStructA {
    [MarshalAs(UnmanagedType.U1)]
    public bool booleanVar;
}

I found there is bool2 in Unity.Mathematics package and it worked well.
That is the attribute they used for bool struct series.
https://github.com/Unity-Technologies/Unity.Mathematics/blob/master/src/Unity.Mathematics/bool2.gen.cs

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.