// lambda lifted
// this version uses stack allocation of continuation closures.

#include <stdio.h>

struct _cont;

typedef void (*factk)(int, struct _cont *);

typedef struct _cont {
  factk fun;
  struct _cont * k;
  int n;
} cont;

int the_result = 0;

// note that ret_cps ignores its continuation
void
ret_cps (int n, cont * k)
{
  the_result = n;
}

void
factcps_3 (int f, cont * k) {
  k->fun (k->n * f, k->k);
}

void
factcps (int n, cont * k)
{
  if (n == 0) {
    k->fun (1, k->k);
  } else {
    cont k0 = { factcps_3, k, n };
    factcps (n-1, &k0);
  }
}

int
main (int argc, char * argv[])
{
  cont k = { ret_cps, NULL, 1 };
  factcps (5, &k);
  fprintf (stdout, "factcps(5)==%d\n", the_result);
  return 0;
}