upvote
> especially with the new IO mechanism which allows supper efficient code that looks good whether it's implemented single-threaded, multi-threaded or just via an event loop!

I had some trouble understanding how the async/await mechanism works:

  var foo_future = io.async(foo, .{args});
  defer if (foo_future.cancel(io)) |resource| resource.deinit() else |_| {}

  var bar_future = io.async(bar, .{args});
  defer if (bar_future.cancel(io)) |resource| resource.deinit() else |_| {}

  const foo_result = try foo_future.await(io);
  const bar_result = try bar_future.await(io);
My assumption is that calling io.async using an event loop implementation of IO, it will internally start a "task" (or whatever it should be called) and that the future is a handle to it. So far so good.

The part that I don't understand is what happens when you call future.await(io). Will the IO implementation somehow suspend the current function and resume once the future is resolved? If so, does that mean that every function in zig is a stackless coroutine?

reply
For future reference you can format code on hn with a newline first then indenting each line by 2+ spaces. (Rather than triple tick)
reply
Fixed it. thanks!
reply
the “(super) efficient” is not there yet. Io is still dynamic dispatch with multiple layers of indirection. afaik it’s slower than before.

the upcoming releases are expected to provide a solution to this “dispatch is comptime-known, but still dynamic” problem, and drop the loses in efficiency.

reply
Hmm in the 2025 talk ( https://youtu.be/f30PceqQWko?si=qZESxMaSyt7fYMfz ), Andrew emphasizes that this approach is more efficient than before- even showing compiled assembly iirc. I guess that was a one-off?
reply
My guess is that one of these (Andrew) is measuring syscalls and the other is measuring vtable indirections.
reply
A vtable indirection is essentially free when you're going to perform a syscall. What matters is that the buffer is above the vtable (which is already the case for the current implementation) so that you don't pay for the indirection when hitting the buffer.
reply
Wow that’s gnarly it’s using dynamic dispatch. I mean I get it, but I thought zig was some sort of performance demon.
reply
if youre doing io, one pointer indirection seems unlikely tp be rate limiting. same for allocation (the other dynamic dispatch in zig)
reply
The parent seems to be talking about efficient code style, not necessarily performance implementation, as they go on to discuss how it looks.

That is, I think the point was DevX not io performance.

reply
Maybe one day it'd be possible to use these new features, but I find myself using `.use_llvm = true` in my zig builds for stability and lesser tested targets.
reply