Skip to content

Issues in new PonyRT

Kiko edited this page Nov 27, 2015 · 2 revisions

These are the issues I have encountered when trying to move to the new PonyRT and the proposed solutions:

Problem1:

The pony interface has changed. Pretty much all functions require a new argument of type pony_ctx_t (opaque type). There's a method for getting the context (pony_ctx()). The problem is that we need to change all the code generation for the functions that use the ctx.

Solution: Mimic the old pony.h (without ctx) in encore.h and remove all references to pony_*. Internally, all pony calls in encore.h will do a call to pony_ctx() and, afterwards, call the corresponding pony function. i.e.

//pony.h

pony_actor_t* pony_create(pony_ctx_t* ctx, pony_type_t* type);

//encore.h
pony_actor_t* encore_create(pony_type_t* type);

//encore.c
pony_actor_t* encore_create(pony_type_t* type){
  pony_ctx_t* ctx = pony_ctx();
  return pony_create(ctx, type);
}

This means changing the code generation in the encore compiler and change the name pony_create to encore_create. The number of arguments are the same (less changes). This also means that there is an extra overhead inside each encore method call. The reason is that we might have:

let a = new Actor
    b = new Actor
in
  a.send(b)

which creates actors and sends messages and, each one will perform a call to get the same ctx. In this case, we call the same function (at least) 3 times to get the same ctx.

Problem2:

Global functions are defined as closures and called from the main method:

int main(int argc, char** argv){
  _enc__closure_compose = closure_mk(_enc__global_fun_compose, NULL, NULL);
  return encore_start(argc, argv, (&(_enc__active_Main_type)));
}

In closure.h, we do a trick to check if we should use malloc or pony_alloc.

#define ALLOC(size) (actor_current() ? pony_alloc(size) : malloc(size))

Currently, actor_current() would need a context and, since we have no context (a context should point to the scheduler and the current actor, we have no info about these yet) before we run encore_start, calling the actor_current() at this point will produce a segfault.

Solution: Either we use malloc for now and live with this memory leak or we start refactoring code and make top level functions to not behave as closures.

Clone this wiki locally