[llvm-dev] Fwd: [RFC] LLVM Coroutines

Gor Nishanov via llvm-dev llvm-dev at lists.llvm.org
Fri Jun 10 17:42:51 PDT 2016

Hi Josh:

> Sorry for the novice question, but how are coroutines lowered in the
> backend? It requires making operating system calls to something like
> pthreads right?

No OS, no target specific code required. Just simple rewriting of a function
during the middle optimizer. One of the first examples in the RFC shows
that a coroutine is optimized down to a constant. Try doing that with
pthreads :-)

>>   generator<int> range(int from, int to) {
>>      for(int i = from; i < to; ++n)
>>         co_yield i;
>>   }
>>   int main() {
>>      int sum = 0;
>>      for (auto v: range(1,100))
>>         sum += v;
>>      return sum;
>>   }
>> And translate it down to this:
>>   define i32 @main() #5 {
>>   entry:
>>     ret i32 4950
>>   }

Very briefly:

LLVM coroutines are functions that have one or more `suspend points`_.
When a suspend point is reached, the execution of a coroutine is suspended and
control is returned back to its caller. A suspended coroutine can be resumed
to continue execution from the last suspend point or be destroyed.

Let's say you get coroutine that looks something like this

  void *f(int n) {
     for(;;) {
       <suspend> // magic: returns a coroutine handle on first suspend

We will split it up into start, resume and destroy functions and will create
a coroutine frame that will keep values that need to be live across suspension

  struct f.frame { int n; }

  void* f(int n) {
    auto s = new f.frame{n};
    return s;

  void f.resume(f.frame* s) {

  void f.destroy(f.frame* s) {
    delete s;

You can read more details in the doc/Coroutines.rst up for review at


or in the RFC that started this thread.


More information about the llvm-dev mailing list