lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


On Wed, 2005-02-16 at 22:37, Mike Pall wrote:
> Hi,
> 
> skaller wrote:
> > It isn't. Its faster. I just measured it at twice as fast,
> > but the reality is much better, C++ is almost certainly
> > 100 times faster than C. The reason is obvious why this
> > must be so: setjump stores lots of registers in a memory
> > buffer to establish a handler. C++ probably pushes a single
> > pointer on the stack. C++ is the clear winner.
> 
> Wait ... we were talking about throwing and not just catching.

Yes, sorry I realised later reading more mails what you 
were doing.

> For catching alone the differences are minimal (~3% on my platform) and
> there is no clear winner, depending on how you measure. You get a
> doubling, I don't (but I measured including the overhead of a Lua script).

I wasn't measuring catching, my test code never threw anything,
I was measuring the time taken to establish a handler.
(But I think you meant that)

However my test wasn't rigorous.

> For catching + throwing (1:1 ratio) C++ is around 40 times slower than C
> (on my machine).

I think there is a more serious and difficult issue here,
at least for pcall. Basically, Lua claims to work as
both C and C++. Actually this isn't really true.

Setjmp/longjmp isn't compatible with C++ because
it doesn't unwind the stack, and throwing an exception
isn't compatible with C.

The only 'solution' compatible with both is to
*pass* errors up the stack properly.

> [sorry, for yet another off-topic post]

I don't see how discussion of error handling +/- coroutines
is off topic here.

My experience is that coroutines require stackless
operations. You can't 'add them' into a language
that uses the stack. This is right pain, if you want
to provide a C API (Lua) or use the C/C++ object
model (Felix) because you're stuck with a deficient
underlying model.

setjmp/longjmp doesn't work at all, not in C and
not in C++, it can't unwind the stack and so will
always fail to release essential resources in
general code. The same applies to C++ EH, not just
crossing C boundaries, but in C++ itself.

In both cases, it only works with an idiomatic
coding style -- eg don't put pointers to heap
memory in local variables between throw
and catch points, or you get a leak.

With a GC, you won't leak memory, but you can still
leak external resources, and if you try to fix that
with finalisers you'll probably deadlock or worse.

So languages like Lua (and Felix) are stuck between
a rock and a hard place. The 'pure' language can
easily avoid all these problems, but there's no
general solution when you bring C/C++ into it,
simply because there isn't any for C/C++ either,
other than to ban outright the operations actually
causing the problem. 

Exceptions are just an exceptionally bad idea,
more precisely there is no hope I can see
of them having any reasonable behaviour
in anything other than a purely functional language,
and even then they're *way* too powerful.

Python does this the hard way, which is the only
way that works IMHO: it passes the error condition
up the C stack manually, and doesn't support
either setjmp/longjmp or exceptions. 

Lua should probably do this too, and thus get
rid of pcall, or rather, get rid of the 
setjmp/longjmp implementation of it.
Unfortunately this would probably require a change
in the CAPI protocol.. 

Does anyone have any idea how much?
[I'm asking: what would change if error
conditions were just passed up the stack]

-- 
John Skaller, mailto:skaller@users.sf.net
voice: 061-2-9660-0850, 
snail: PO BOX 401 Glebe NSW 2037 Australia
Checkout the Felix programming language http://felix.sf.net