I'll try to stick up for tail calls, at least down the road (I'd say having 
them in the first release doesn't really matter).

A few points:

- As you guys have said, this issue seems pretty tied in with the memory 
management semantics, particularly with refcounting. But I'm still not 
convinced that refcounting has proved itself. We'll need to have a GC before 
long, and once we do, I think it would still be worthwhile to consider the 
possibility of decreasing or eliminating our use of refcounting. If we were to 
move away from refcounting, the "callee-drops" semantics goes away.

- Separate from the take/drop issue, I'm probably too far away from the 
compiler to know what the stack movement is that's hurting the non-tail-call 
cases. What's the issue there?

- I find the state machine use case pretty compelling. It's a pretty natural 
style, which is easy to code up; it might not be as efficient as loops, 
depending on how we implemented it, but if it's more 
understandable/maintainable it can be worth the trade-off.

- A variation of state machines is jump tables, e.g. in a bytecode interpreter.

- Full disclosure: I agree that tail calls are less important for Rust than 
for, say, Erlang, because of loops and because of iteration abstractions 
(either iterators or blocks, depending on which way we go). But I still think 
they make for a nice tool that's hard to replicate when it's not provided by 
the language.

Dave

> Yeah. I concur. Tail calls are something I'm willing to give up for a few 
> reasons.
> 
>  - Linkage models don't guarantee the ability to do cross-crate tail
>    calls. Sad but apparently true.
> 
>  - Tail calling hurts optimization in the non-tail-call case a fair
>    bit, both in the codegen (stack movement) sense and in the sense of
>    permitting the compiler to pair up take/drop as Marijn noted.
> 
>  - I agree with Sebastian that tail *recursion* is not the compelling
>    case of tail calls at all; that's nice for textbooks but the bigger
>    use-case is state machines. However: we have early returns and
>    mutable alias arguments; it's not really clear we need them nearly
>    as much as (say) a pure-expression language. They're really just an
>    optimization, to avoid the cost of doing a switch on a first class
>    value (current state gets encoded into the PC directly, rather than
>    a state variable). It's really not clear to me that this case is
>    a sufficiently important one to bend the rest of the language for.
> 
> Any champions for 'em? I have stood up for them many times in the past but 
> they continue to be a sticky cost we pay on many design choices, I'd be ok 
> ceasing to pay that.
> 
> -Graydon
> _______________________________________________
> Rust-dev mailing list
> Rust-dev@mozilla.org
> https://mail.mozilla.org/listinfo/rust-dev

_______________________________________________
Rust-dev mailing list
Rust-dev@mozilla.org
https://mail.mozilla.org/listinfo/rust-dev

Reply via email to