A discussion on Hacker New/the Rust boards about whether or not their `async`/`await` can implement structured synchronous concurrency

16 views
Skip to first unread message

Job van der Zwan

unread,
Nov 10, 2019, 1:09:44 AM11/10/19
to The Programming Language Céu
So Rust landed `async`/`await` this week, and in the HN discussion someone said, and I quote, that "async/await lets you write non-blocking, single-threaded but highly interweaved firmware/apps in allocation-free, single-threaded environments (bare-metal programming without an OS). The abstractions around stack snapshots allow seamless coroutines and I believe will make rust pretty much the easiest low-level platform to develop for".

Of course, I couldn't resist asking if they had ever taken a look at Céu and the synchronous concurrency model:


That got a surprisingly positive response, with people saying Céu looks neat and were curious to learn more about how worked. Ditto for the concurrency paradigm. One person in particular just opened a discussion on the Rust discussion forums about it:


The actual discussion still has to get going, but it might be worth keeping an eye on. I suspect people tend to be so locked into the type of concurrency that they are already familiar with, that they might not realize how Céu is different at first glance. So some help with clarifying things probably won't hurt.

Would be nice some of Céu's good ideas escape into the wild and find a place in other languages, no? :)

/Job

Francisco Sant'anna

unread,
Nov 12, 2019, 8:31:25 AM11/12/19
to ceu-...@googlegroups.com
Thank you Job!

On Sun, Nov 10, 2019 at 4:09 AM Job van der Zwan
<j.l.van...@gmail.com> wrote:
>
> So Rust landed `async`/`await` this week, and in the HN discussion someone said, and I quote, that "async/await lets you write non-blocking, single-threaded but highly interweaved firmware/apps in allocation-free, single-threaded environments (bare-metal programming without an OS). The abstractions around stack snapshots allow seamless coroutines and I believe will make rust pretty much the easiest low-level platform to develop for".

Looks interesting, I'll read about it...
Do you know how they handle the stacks?

> That got a surprisingly positive response, with people saying Céu looks neat and were curious to learn more about how worked. Ditto for the concurrency paradigm. One person in particular just opened a discussion on the Rust discussion forums about it:
>
> https://users.rust-lang.org/t/can-rusts-async-await-model-the-synchronous-concurrency-paradigm/34472?u=batmanaod
>
> The actual discussion still has to get going, but it might be worth keeping an eye on. I suspect people tend to be so locked into the type of concurrency that they are already familiar with, that they might not realize how Céu is different at first glance. So some help with clarifying things probably won't hurt.
>
> Would be nice some of Céu's good ideas escape into the wild and find a place in other languages, no? :)

Sure! :)

Francisco Sant'anna

unread,
Nov 12, 2019, 10:44:58 AM11/12/19
to ceu-...@googlegroups.com
On Tue, Nov 12, 2019 at 11:31 AM Francisco Sant'anna
<francisco...@gmail.com> wrote:
>
> > So Rust landed `async`/`await` this week, and in the HN discussion someone said, and I quote, that "async/await lets you write non-blocking, single-threaded but highly interweaved firmware/apps in allocation-free, single-threaded environments (bare-metal programming without an OS). The abstractions around stack snapshots allow seamless coroutines and I believe will make rust pretty much the easiest low-level platform to develop for".
>
> Looks interesting, I'll read about it...
> Do you know how they handle the stacks?

They use generators which don't require stacks.

Job van der Zwan

unread,
Nov 12, 2019, 4:23:50 PM11/12/19
to The Programming Language Céu
Hehe, you already know more than I do :)

I vaguely recall you writing at some point that you figured Céu will always remain a research language, which I can understand - but that's all the more reason I hope other languages like Rust will look at it and take ideas from it when possible.

Daniel Austin

unread,
Nov 13, 2019, 12:00:01 AM11/13/19
to ceu-...@googlegroups.com
Francisco, would you mind describing or pointing to resources that describe the issue you are investigating with regard stacks?  How are Rust and Ceu different or the same in this regard and what are the implications?  I think I can read between the lines a bit and guess but I'd love to get a complete picture.

--

---
You received this message because you are subscribed to the Google Groups "The Programming Language Céu" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ceu-lang+u...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/ceu-lang/5c12daea-9eb0-414a-a91d-0db3ed8feacc%40googlegroups.com.

Francisco Sant'anna

unread,
Nov 13, 2019, 1:29:24 PM11/13/19
to ceu-...@googlegroups.com
On Wed, Nov 13, 2019 at 3:00 AM Daniel Austin <daniel....@gmail.com> wrote:
>
> Francisco, would you mind describing or pointing to resources that describe the issue you are investigating with regard stacks? How are Rust and Ceu different or the same in this regard and what are the implications? I think I can read between the lines a bit and guess but I'd love to get a complete picture.

I found this link that might help:
https://blog.panicsoftware.com/coroutines-introduction/

Each stackful coroutine (fiber, green thread) keeps its own stack for
local variables when suspending execution.
With 1000 coroutines you'll need 1000 stacks. Having a separate stack
allows the coroutines to suspend at any level of depth in the call
stack.

Stackless coroutines share the main single stack. When resumed, the
coroutine must receive from the caller its own state (local variables,
program counter) which must be preallocated and known in advance.
Hence, stackless systems require some compiler support in order to
infer which functions have to be considered "async" to be modified
accordingly (moving locals to a struct and preparing points of
suspension/resumption).
If a stackless function calls a normal function, this function cannot
suspend since their locals and program counter are not tracked.
Typically, only the main body of an async function is allowed to
suspend.

Lua supports stackful coroutines. Céu trails resemble stackless coroutines.

Regards,
Francisco

Luke Whittlesey

unread,
Nov 13, 2019, 3:11:10 PM11/13/19
to ceu-...@googlegroups.com
Correct me if I'm wrong, but I think the parent/child hierarchy comes
into play here as well. Céu creates a large C struct with a number of
unions, so the memory is pre-allocated, but reused. It is safe to
reuse memory since the semantics don't allow a child process to
outlive its parent, i.e. you can't detach a process from its parent;
if the parent dies, the child goes with it.
Other than unbounded vectors is there any dynamic allocation happening in Céu?
> --
>
> ---
> You received this message because you are subscribed to the Google Groups "The Programming Language Céu" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to ceu-lang+u...@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/ceu-lang/CAD4QiZs_FkAThuydEVeYtCdT26xhN4Hm%3D9VV6y3nDsft6MFLCA%40mail.gmail.com.

Francisco Sant'anna

unread,
Nov 14, 2019, 5:01:14 PM11/14/19
to ceu-...@googlegroups.com
On Wed, Nov 13, 2019 at 6:11 PM Luke Whittlesey
<luke.wh...@gmail.com> wrote:
>
> Correct me if I'm wrong, but I think the parent/child hierarchy comes
> into play here as well. Céu creates a large C struct with a number of
> unions, so the memory is pre-allocated, but reused. It is safe to
> reuse memory since the semantics don't allow a child process to
> outlive its parent, i.e. you can't detach a process from its parent;
> if the parent dies, the child goes with it.
> Other than unbounded vectors is there any dynamic allocation happening in Céu?

It also happens with "spawn" which requires an explicit "pool" to
determine where the instance will live.
If the pool is unbounded, the instances go to the heap.
Just like unbounded vectors, pools also respect the scope hierarchy.

Luke Whittlesey

unread,
Nov 14, 2019, 10:40:12 PM11/14/19
to ceu-...@googlegroups.com
I know some developers might not agree with this... but as I see it
Ceu provides a couple of advantages for small embedded systems (i.e.
kB's of memory) if unbounded vectors or pools are not used:

1. There are no malloc/free calls and I don't have to worry about the
heap becoming fragmented and the possibility of a malloc call
eventually failing.

2. With Ceu's use of "CEU_API static tceu_app CEU_APP;" I know that
Ceu won't use more than sizeof(tceu_app) static amount of memory for
any possible state.

Of course I have to similarly restrict/manage my own C patterns to
have the same guarantees.

I don't really understand the "zero allocation" part of the HN
discussion. Are they suggesting that everything needed to resume an
async fn (continuation) is stored on the call stack of the function
where the continuation was created, and nothing is dynamically
allocated (malloc/free) on the heap? The link shared by Francisco
leads me to believe that C++20 would would still have a small dynamic
allocation on the heap for each continuation spawned.
> --
>
> ---
> You received this message because you are subscribed to the Google Groups "The Programming Language Céu" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to ceu-lang+u...@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/ceu-lang/CAD4QiZsTXRgbu6qnXVnDVAKvUcEePzrbSKSD3%2BSafpZkVhfc0g%40mail.gmail.com.

Francisco Sant'anna

unread,
Nov 17, 2019, 10:08:14 AM11/17/19
to ceu-...@googlegroups.com
On Fri, Nov 15, 2019 at 1:40 AM Luke Whittlesey
<luke.wh...@gmail.com> wrote:
> I don't really understand the "zero allocation" part of the HN
> discussion. Are they suggesting that everything needed to resume an
> async fn (continuation) is stored on the call stack of the function
> where the continuation was created, and nothing is dynamically
> allocated (malloc/free) on the heap? The link shared by Francisco
> leads me to believe that C++20 would would still have a small dynamic
> allocation on the heap for each continuation spawned.

I believe some allocation is require to place these continuations on
lists of listeners of event-driven APIs, such as GUIs and network
libraries, but I did not go that far...
Reply all
Reply to author
Forward
0 new messages