I am trying to understand ARC, which seems to be promised as the future for Nim. That, in turn, redirects to this document, so I am reading that, but I cannot make head or tails of the whole document.
It starts with a motivating example, which I cannot follow because I don't know yet the meaning of the procs declared there, like sink=. The example is not explained in English, so even if it purports to explain how to implement seqs as a library, I fail to see what is the design behind that, and what features make this possible with ARC that were missing before (or is it the new runtime? I am not sure what is the difference between the two).
It goes on by saying
The memory management for Nim's standard string and seq types as well as other standard collections is performed via so called "Lifetime-tracking hooks" or "type-bound operators".
which is... weird. I mean, I would expect a high level panoramic of what this document is even about. Why talking about memory management for strings and seqs? What about other things? At this point in the document I am still wondering about much higher level things, like: will still there be ptr and ref? Are things garbage collected or do I need to put some annotations like Rust to track lifetimes?
It then goes on into hooks, starting with destroy=.
Variables are destroyed via this hook when they go out of scope or when the routine they were declared in is about to return.
Fine? I guess... How do things survive out of a scope? I am still lacking a high level description of what we are even trying to do
Then there is this example
proc `=destroy`(x: var T) =
# first check if 'x' was moved to somewhere else:
if x.field != nil:
freeResource(x.field)
x.field = nil
First check if x was moved somewhere else? What is a move? Isn't it explained later in the document?
Then we go into =sink.
A =sink hook moves an object around, the resources are stolen from the source and passed to the destination. It is ensured that source's destructor does not free the resources afterwards by setting the object to its default value (the value the object's state started in)
I cannot make any sense of the above sentence. And so on.
For me, this is completely unreadable. I cannot tell
and so on. If we look at, say, the _chapter in Rust's book <https://doc.rust-lang.org/book/ch04-00-understanding-ownership.html>`_ about ownership, it describes which rules are in place, what they mean in simple examples, how they help to track memory. I understand that ARC is still in development and do not expect this level of polish in the documentation, but if library authors should port their libraries to work with ARC, there needs to be a minimum level of explanation of how this will work.
Are there any other resources to understand the way this will work and impact Nim developers?
This document is the spec we follow in our implementation and it served us well for this purpose. It's not for end users (but then it's also not meant to be incomprehensible either :-/ ), we'll have an ARC tutorial soon, I hope.
Here is the summary: "Compile your code with --gc:arc". That's it, the rest are details, the document describes how --gc:arc is implemented.
"Compile your code with --gc:arc". That's it, the rest are details, the document describes how --gc:arc is implemented.
Don't you need to at least mention --gc:orc as well? The difference between them at least is useful knowledge, since as soon as someone compiles async code with --gc:arc they will get demotivated.
TL;DR: (as far as I understand, I'm not expert on these new mechanisms) --gc:orc is --gc:arc with cycle collection which is necessary for async (which produces many cycles).
@Araq I appreciate all of the work done by you and others, and I think a cycle collector is useful even without async. That said, you know that some will ask "Why does Nim async need a cycle collector when Rust/C++ async does not?". So, I'll ask now.
Still looking forward to the day when I can use Nim at work...
So, I'll ask now.
I think the primary reason is different API design.