Live data from Hacker News

Portable and Interoperable Async Rust

ncameron.org

51–60 of 71 posts

Re: Portable and Interoperable Async Rust

#51
post #50

Earlier quoted context omitted.

Rust also has the vocabulary types required for interoperability, such as Future and Waker. Or what exactly make C++ more interoperable?

Does it? https://book.async.rs/overview/std-and-library-futures.html C++ ones can interoperate with any type that plugs into the compiler magic expected by the co-routines code rewrite. If you want to deep dive into how Visual C++ does it, and how WinRT gets plugged into C++ co-routines, here is a very lengthy set of blog posts. https://devblogs.microsoft.com/oldnewthing/20210504-01/?p=10... Now back to Rust, how can…

The std::future::Future from the rust standard library works with every runtime.

Not sure I understand, what kind of interoperability you are talking about. What kinds of code works in C++ across runtimes, for which the equivalent in Rust doesn't?

Re: Portable and Interoperable Async Rust

#52
This is good info, and will be very useful for people porting code from other languages like Javascript. But I'm still in mourning that async took over the world.

I grew up with cooperative multitasking on Mac OS and used Apple's OpenTransport heavily in the mid-90s before Mac OS X provided sockets. Then I spent several years working on various nonblocking networking approaches like coroutines for games before the web figured out async. I went about as far down the nonblocking IO rabbit hole as anyone would dare.

But there's no there there. After I learned Unix sockets (everything is a stream, even files) it took me to a different level of abstraction where now I literally don't even think about async. I put it in the same mental bin as mutexes, locking IO, busy waiting, polling, even mutability. That's because no matter how it's structured, async code can never get away from the fact that it's a monad. The thing it's returning changes value at some point in the future, which can quickly lead to nondeterministic behavior without constant vigilance. Now maybe my terminology here is not quite right, but this concept is critical to grasp, or else determinism will be difficult to achieve.

I think a far better programming pattern is the Actor model, which is basically the Unix model and piping immutable data around. This is more similar to how Go and Erlang work, although I'm disappointed in pretty much all languages for not enforcing process separation strongly enough.

Until someone really understands everything I just said, I would be very wary of using async and would only use it for porting purposes, never for new development. I feel rather strongly that async is something that we'll be dealing with and cleaning up after for the next couple of decades, at least.

Re: Portable and Interoperable Async Rust

#53

This is good info, and will be very useful for people porting code from other languages like Javascript. But I'm still in mourning that async took over the world. I grew up with cooperative multitasking on Mac OS and used Apple's OpenTransport heavily in the mid-90s before Mac OS X provided sockets. Then I spent several years working on various nonblocking networking approaches like coroutines for games before the we…

Rust is hard at the start, but easy after. But I feel async keep it hard. The sad part is that async is SO infectious that you are forced to move all on it to align with the rest of the ecosystem.

I also believe the way all of this is presented is not the right abstraction. Actors + CSP is probably the best way. Plus, even if concurrency parallelism I think the parallelism idioms make more sense (pin to the "thread", do fork-joins, use ring-buffer for channels, etc).

However, I suppose the whole issue is that async as-is is easier for the mechanical support that work for the compilers and allows to squeze the performance/resource usage, that is important for Rust.

But maybe keep it hidden and surface another kind of api?

Re: Portable and Interoperable Async Rust

#55

I take the opposite tack. Who, precisely is clamoring for this? Why not "let 100 flowers grow" (present condition) and allow the various solutions to mature to the point that a de facto standard emerges? The claim is made: "choosing a runtime locks you into a subset of the ecosystem," to which I answer, "So, what?" If I want to log my server events or take advantage of a protocol encoding method or compress my data -…

> By the way, using Go as an example is a joke since -- from the early Go bootcamp I attended in 2014, the best practice has been to use a 3rd-party http router (these days: gorilla? httprouter? chi? etc) instead of the one provided in the standard library.

You're mistaken. Using a third party router doesn't lock you into a particular subset of the ecosystem. E.g., I tend to use the Gorilla router by default, but I can use it with any middleware that implements the standard http.Handler interface.

Re: Portable and Interoperable Async Rust

#56
post #50

Earlier quoted context omitted.

Does it? https://book.async.rs/overview/std-and-library-futures.html C++ ones can interoperate with any type that plugs into the compiler magic expected by the co-routines code rewrite. If you want to deep dive into how Visual C++ does it, and how WinRT gets plugged into C++ co-routines, here is a very lengthy set of blog posts. https://devblogs.microsoft.com/oldnewthing/20210504-01/?p=10... Now back to Rust, how can…

The std::future::Future from the rust standard library works with every runtime. Not sure I understand, what kind of interoperability you are talking about. What kinds of code works in C++ across runtimes, for which the equivalent in Rust doesn't?

In C++ you don't have the scenario like in Rust, where one is forced to use a specific async runtime for library xyz, because it depends on having tokio as runtime.

Or has that situation been sorted out by now?

Re: Portable and Interoperable Async Rust

#57
post #56

Earlier quoted context omitted.

The std::future::Future from the rust standard library works with every runtime. Not sure I understand, what kind of interoperability you are talking about. What kinds of code works in C++ across runtimes, for which the equivalent in Rust doesn't?

In C++ you don't have the scenario like in Rust, where one is forced to use a specific async runtime for library xyz, because it depends on having tokio as runtime. Or has that situation been sorted out by now?

In Rust you only are forced to use a specific runtime if you want to use its API. For example to spawn new tasks, or to block on a future. I believe that would be the same in C++.

In Rust, you don't need to use a specific runtime if you just want to use async function in your library.

Re: Portable and Interoperable Async Rust

#58

This is good info, and will be very useful for people porting code from other languages like Javascript. But I'm still in mourning that async took over the world. I grew up with cooperative multitasking on Mac OS and used Apple's OpenTransport heavily in the mid-90s before Mac OS X provided sockets. Then I spent several years working on various nonblocking networking approaches like coroutines for games before the we…

> But I'm still in mourning that async took over the world.

I agree, it does seem like a step backwards in general. However, for Rust it makes sense. There is no runtime, so there is nothing to preempt the green threads/lightweight processes etc. But yeah, with higher level languages like Python, I was disappointed to see how async was emphasized in 3.x over green threads which were already used by a number of projects.

Re: Portable and Interoperable Async Rust

#59

Why has Rust struggled so much with this, where Go has succeeded from the start with its language-level “goroutine” concept and runtime? Maybe it just wasn’t a focal area for the original Rust designers?

Rust doesn't want to impose its own one-size-fits-all runtime on all users of the language, because Rust wants to work in places where Go isn't a good fit, e.g. microcontrollers, kernels, or seamlessly on top of other languages' runtimes.

Architecture of an efficient async runtime is going to be different for 128-core server vs single-threaded chip with barely any RAM. In Rust you can write your own runtime to your needs, rather than fight overhead of a big runtime on a small device, or struggle to scale a dumb runtime to complex workloads.

Re: Portable and Interoperable Async Rust

#60
post #53

This is good info, and will be very useful for people porting code from other languages like Javascript. But I'm still in mourning that async took over the world. I grew up with cooperative multitasking on Mac OS and used Apple's OpenTransport heavily in the mid-90s before Mac OS X provided sockets. Then I spent several years working on various nonblocking networking approaches like coroutines for games before the we…

Rust is hard at the start, but easy after. But I feel async keep it hard. The sad part is that async is SO infectious that you are forced to move all on it to align with the rest of the ecosystem. I also believe the way all of this is presented is not the right abstraction. Actors + CSP is probably the best way. Plus, even if concurrency parallelism I think the parallelism idioms make more sense (pin to the "thread",…

> The sad part is that async is SO infectious that you are forced to move all on it to align with the rest of the ecosystem.

That's the problem with monadic stuff in general. One solution to that might be to keep the async part on the "edge" of your programs (a bit like the functional core, imperative shell pattern or the hexagonal architecture), write all your logic without async and use async only on the edge.

Post reply on HN