On 15/02/2014, at 8:32 AM, Martin DeMello wrote:

> I was trying to rewrite the CopyFiles code not to call exit() when it hit an 
> error, but let the calling code handle it instead, but I couldn't figure out 
> what the proper way to do that was.

I can't either :)

Seriously this is an open issue, and not just in Felix.

For the moment, Felix uses the C method: a return code.
Which means you have to propagate the error all the way up.

There are alternatives. One is to use a goto. Non-local gotos aren't
safe in general, but they can be used safely.

In particular you can require the caller to provide the error handler in a 
closure,
and the closure can exit with a goto. It's safe provided the caller is live at
the point the closure is invoked.

For example the service routine says:

        proc dostuff (x:T, error: 1 -> 0) { 
                ...
                error(); // we got an error, get out of here!!
                ...
        }

and the client routine says:

        proc client (y:T) {
                blah;
                dostuff (y, myerror);
                return;
        handler:>
                println$ "Woops we got an error";
                return;
        proc myerror () { goto handler; }
        }

This technique is low level, requires ugly housekeeping, and it isn't safe if a
myerror closure escapes outside the client context that created it (it won't
crash, it just results in nonsense).

I have tried several times to make a DSSL for this, in other words find
some nice syntax. But it isn't so easy. 

And there's another issue: you cannot do that non-local goto across a function
boundary.

In fact you can C++ throw a continuation (closure) along the stack.
The scheduler has a try/catch handler and if it sees a continuation being
thrown .. well it just schedules it :)



> I read in the docs that exceptions were mostly for C++ interop, and not 
> recommended for use in felix code.

C++ exceptions can't work in Felix because procedures use a spaghetti stack,
that is, heap allocated stack frames linked with pointers. Whereas a C++
exception requires the machine stack, and Felix procedures run
stackless of necessity.

Functional code in Felix uses the machine stack for the return address though.
The compiler does try to get rid of it by converting functions to procedures.
However it can't do that universally because embedding Felix expressions
in C expressions mandates using the stack ABI. I don't just mean callbacks,
but trivial stuff like

        fun + : int * int -> int = "$1+$2";

could never work unless  a Felix expression was a C++ expression.


> But there's also nothing corresponding to haskell's Either type.

Sure there is: we have an Option type. For any situation you can invent a type
if you can't find a suitable one. eg

        union CopyResult = 
        | CopyOk
        | ClobberSrc
        | ClobberDst
        | IOError of int
        ;

Some of the detailed filesystem/execution stuff uses union (variant/sum) types
to return a result or a detailed error code.

Of course the mainline tool will need to translate that to an exit code.

But this isn't the problem I think, the problem is propagating the error.


--
john skaller
skal...@users.sourceforge.net
http://felix-lang.org




------------------------------------------------------------------------------
Android apps run on BlackBerry 10
Introducing the new BlackBerry 10.2.1 Runtime for Android apps.
Now with support for Jelly Bean, Bluetooth, Mapview and more.
Get your Android app in front of a whole new audience.  Start now.
http://pubads.g.doubleclick.net/gampad/clk?id=124407151&iu=/4140/ostg.clktrk
_______________________________________________
Felix-language mailing list
Felix-language@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/felix-language

Reply via email to