I've used unity almost every day for the last 2 years. Here are my thoughts.

I’m just going to list some of my thoughts about Unity here.

Unity is an amazing tool, without it, there’s no way I could be a one man game dev team. Everywhere I go, I sing praises of unity to anyone who will listen. There’s tons of resources available online for simple things, but more advanced topics have very little information about them, this is why most of my learning now comes from other people’s packages. In the past, I’ve struggled to find information about compute shaders, DX11 features, physics engine scripting, path finding, custom deferred rendering stages, multiple render targets, stencil buffers, custom yieldinstructions, singletons/managers.

at one point, I was very close to purchasing unity’s premium support because I couldn’t figure out whether the bugs I had were with my code, or in the engine. I was working on compute shaders and DX11 functionality and things weren’t working, and I had no idea if I was doing things correctly because the documentation is poor on this topic, and it seems like there are almost no examples of how to do them correctly, and almost no one is posting on the forums or replying to posts concerning these topics. I ultimately did not purchase premium support because it was too expensive, and I only thought I would need to use it very briefly. If a cheaper option were available for less hours of support, I would have purchased that. As an indie developer working off of savings, my budget for this is very limited.

I’ve found that it’s mostly impractical to use Boo, even though it seems like a great idea, there’s no support for it. Before I was a game developer, I was a python coder, so I miss python like syntax, but now I’ve grown used to C#. The fact that the different assembly types don’t always work together compounds this.

the first time I considered stopping using unity was when I found out I couldn’t step the physics engine manually, which is somewhat required for certain multiplayer architectures. At that point, I spent a week integrating Bullet Physics with unity, which I ultimately did not end up using. I’ve since switched to a different architecture that doesn’t require this.

The engine not being threadsafe, or not having a multithreading model makes me worry about running into scaling problems down the line.

I sometimes think that I could solve a lot of my problems (like seeing how some rendering things actually work under the hood or editing the physics engine) if I had the source code, but I have heard that this is almost impossible and also very expensive to license.

Ya the multi-threading issue is fairly big. And I think it’s getting bigger as time goes on. However, I agree that Unity is probably the best game engine for any devs working on a project alone (i.e. a one man band).

I don’t think there’s any way at all I could be as far as I am in my game development if I was using UDK or Cryengine. Perhaps the most important thing with regards to all other engines I’ve ever looked at, is that Unity’s community actually tries to help you, and information is readily available. That is a huge plus.

The only thing I’ve found Unity lacking in is out-of-the-box performance. You have to work pretty hard to get Unity to run things “well”, depending on your game genre and scope of your game.

Why? What are you going to do that’ll be limited by the lack of a threadsafe engine?

I’m making a game that has a lot of agents doing lots of things at once. And as they get more complex, this is only going to become more of a problem. Though, Unity 5 seems to mention some kind of ‘job queue’ which might be what I’m looking for.

I’m pretty sure this is only for the editor, as in the feature preview video it is mentioned under the headline “Editor”

Do they directly interact with the Unity API? You can do lots of effective threading without needing to touch the Unity API, and AI is a pretty good example of that.

–Eric

I’ve had five-thousand odd agents bounding around (balls, physics simulation) without having to worry about the engine being thread-safe. If you’re getting to the stage where you’re overloading the engine then you’re probably giving it so much input you’ll overload the end user.

You’re right about AI being a good example for multithreading if I can isolate their behaviors from the unity API and I might look into that when or if it becomes relevant.

job queues being only for the editor seems weird because they were showing it in the profiler.

You don’t “need” a threadsafe API, just like you don’t “need” to code in C# because you could write a CLI DLL by tapping in the ones and zeros of the compiled binary using a telegraph. But a threadsafe API would certainly make multithreaded code much cleaner and easier.

Not necessarily. Making stuff thread-safe isn’t magic, especially if you want to minimise performance issues, and it doesn’t guarantee that your code will work as you intended. It can sometimes be easier to simply use non-thread safe code in a safe threaded manner than it is use thread-safe code in a safe manner (especially if you’re lulled into think it’s ‘safe’).

Just as a simple example, what does the following print?

transform.position = Vector3.zero;
transform.Translate(1,0,0);
print(transform.position);

It would print whatever the position was at the time it hit that line, if it was set in a different thread, which is what I expect. Devs are going to have to learn how multithreading works; it’s not an optional thing anymore. Multi-core CPUs are the way of the future, and so is asynchronous programming. Trying to block it in an API because you’re worried that noobs will make mistakes isn’t going to be doable for much longer. Hopefully Unity will eventually keep up with .NET as well, which has been introducing a lot of new features to make parallel programming easier.

If they wanted to do something extra to help devs with thread safety, they could add an “allowAsync” field in MonoBehaviour or GameObject that would be disabled by default, which would make that script only accessible by the main thread as it is now. You could also keep the current Start, Update, etc as synchronous and handled on the main thread, but introduce new StartAsync, UpdateAsync methods that would launch on a separate thread. That way people used to the way things work now would be pretty insulated.

Seems to me that mobile devices would be loath to allow games to multi-thread…

They all already allow it, and most modern phones have quad-core CPU’s.

Whoa… who’s blocking it in a API? Multithreaded code runs just fine in Unity - the api isn’t blocking anything.

Which is useful how exactly? I like to be able to easily reason what my code is doing, not simply say ‘well, it’ll do something… hopefully’.

Wouldn’t it be much easier to wrap it in a lock, or, if possible contention is an issue, wrap it in a task that will be executed at an appropriate time?

lock (uniqueObjectLock)
{
    transform.position = Vector3.zero;
    transform.Translate(1,0,0); 
    print(transform.position);
}
DoSafely( () =>
    transform.position = Vector3.zero;
    transform.Translate(1,0,0); 
    print(transform.position);
});

Notice how suddenly we know exactly what is going on, it’s easy to reason about, it’s fast, we still have all the power of multithreading… oh and it does not require a thread-safe API.

Yes, unity could do a few things to make multithreaded code a little bit nicer… but no, making the API thread-safe isn’t necessary.

I better get my multithreaded games apps off the market then…

You do know you can do that… right now? The basic version could be written in, I don’t know, 20 mins?

Yes it does. The API blocks itself from being accessed from separate threads. You are blocked from accessing almost anything Unity-related from other threads. Try it yourself and see, you will get a “___ can only be accessed from the main thread” for pretty much everything.

Of course, but you didn’t ask me how to make it better, you asked me what it printed.

Yes it does. Try running that code in a separate thread, and you get this error: “InternalGetTransform can only be called from the main thread.”

No you can’t, and I’m thinking you’ve never actually tried to run on a separate thread before. FYI, Unity Coroutines are not separate threads.

Which does not block multithreading :slight_smile:

Well, you’re the one proposing a thread-safe API as a significant barrier. Did you not say the lack of a thread-safe API is akin to programming by binary via telegraph? How would you design a thread-safe API?

So? We remove that warning… does that make the engine threadsafe?

Hint: I can access a Dictionary<TKey, TValue> by multiple threads without any exception, does this make it threadsafe?

Really? Coroutines are not threads? What a surprise! Maybe I’d known that if I’d manually reimplemented coroutines before…

Oh wait I have, so maybe I *have dealt with threading before? Heck, here’s an example from two plus years ago! I’m programming multi-threaded WPF code as we speak, as well as building highly scalable servers using async and tasks that interface with a thread running inside of Unity3d! And yes, It’s entirely possible to build what you described.

are you suggesting that these warnings do not matter? I have to admit, I haven’t done much with unity multiprogramming because I have heard such bad things about it, but if it just spits out warning that don’t matter then that seems pretty cool.

No the warnings matter (at least, as far as I’m aware), but they are easy to work with.

In the context of this discussion, that’s entirely untrue. What engines have their game logic/scripts generically threaded, or threaded at all? If .1% of games do it, at best, how would that not be optional? I’d be interested to know the names of the games you know to have this type of multithreading.

I’ve got decent experience with multithreading, and this idea of a threadsafe API sounds magical, but in practice it’s far more complex than you seem to think. The example given by npsf3000 is rather excellent, and here’s the part of it that’s really bad: Threading issues such as that one will not cause you a problem the vast majority of the time. That’ll likely pop in a bad way 1 in 1M iterations, so now you have a super intermittent bug, which will suck development time, development time that could have been spent on anything (including optimization). Multi-threading, even for the best devs, is a bug spawner, plain and simple. For some systems, it’s well worth it, but any change that boils down to ‘let’s sacrifice developer time for an optimization’ better really, really need it.

So, the end question is not an argument of is multithreading good, sure, multithreading is good, but it’s also already being done alot (rendering, physics, audio, animation, all threaded/threadable services without impacting end users). The question is what are your cores doing when the scripts are running, ie, do you have idle cores waiting for scripting to complete, and can they be doing nothing else but running scripts? That’s kinda hard to answer right now, Unity needs a telemetry style profiler to answer that, like the thread profiler shown here.

But this idea that it’s a truly game blocking thing… no, not buying it, not by a long shot.