New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

'fn lifetime ascription #1847

Closed
wants to merge 9 commits into
base: master
from

Conversation

Projects
@llogiq
Contributor

llogiq commented Jan 7, 2017

This is a much reduced version of lifetime ascription that gives us none of the great teachability of full lifetime ascription, but rather extends the power of the lifetime system by allowing to ascribe a 'fn lifetime.

(rendered)

@llogiq llogiq referenced this pull request Jan 7, 2017

Closed

Alloca for Rust #1808

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

In llogiq#1 added and unresolved question for break 'fn.

Contributor

Ericson2314 commented Jan 7, 2017

In llogiq#1 added and unresolved question for break 'fn.

@comex

This comment has been minimized.

Show comment
Hide comment
@comex

comex Jan 7, 2017

  • In your example, you have 'fn in a struct field. How would this work if values of that type were passed to or returned from functions? It seems to me that 'fn would have to refer to a different lifetime per function, so it would have to be passed to the struct as a generic parameter.

  • What syntax would be used to give a value 'fn lifetime? Would it ever be inferred? As written, your example is clearly a type error as Some(head) is an Option<Node>, not Option<&'fn Node>.

  • What kind of code should the compiler generate if types with destructors are allocaed?

  • Would this provide any way to allocate dynamically sized arrays on the stack?

comex commented Jan 7, 2017

  • In your example, you have 'fn in a struct field. How would this work if values of that type were passed to or returned from functions? It seems to me that 'fn would have to refer to a different lifetime per function, so it would have to be passed to the struct as a generic parameter.

  • What syntax would be used to give a value 'fn lifetime? Would it ever be inferred? As written, your example is clearly a type error as Some(head) is an Option<Node>, not Option<&'fn Node>.

  • What kind of code should the compiler generate if types with destructors are allocaed?

  • Would this provide any way to allocate dynamically sized arrays on the stack?

@whitequark

This comment has been minimized.

Show comment
Hide comment
@whitequark

whitequark Jan 7, 2017

In your example, you have 'fn in a struct field. How would this work if values of that type were passed to or returned from functions? It seems to me that 'fn would have to refer to a different lifetime per function, so it would have to be passed to the struct as a generic parameter.

'fn is an implicitly bound lifetime that is equivalent, borrow checker wise, to the following code in today's Rust:

fn foo<'fn>() {
  ...
}

No changes from the behavior of the code above with respect to borrow checker are needed.

What kind of code should the compiler generate if types with destructors are allocaed?

Destroyed before the function returns, just as if the respective let bindings were hoisted to the very first line of the function.

Would this provide any way to allocate dynamically sized arrays on the stack?

Not without #1808.

whitequark commented Jan 7, 2017

In your example, you have 'fn in a struct field. How would this work if values of that type were passed to or returned from functions? It seems to me that 'fn would have to refer to a different lifetime per function, so it would have to be passed to the struct as a generic parameter.

'fn is an implicitly bound lifetime that is equivalent, borrow checker wise, to the following code in today's Rust:

fn foo<'fn>() {
  ...
}

No changes from the behavior of the code above with respect to borrow checker are needed.

What kind of code should the compiler generate if types with destructors are allocaed?

Destroyed before the function returns, just as if the respective let bindings were hoisted to the very first line of the function.

Would this provide any way to allocate dynamically sized arrays on the stack?

Not without #1808.

Merge pull request #1 from Ericson2314/fn-lifetime
Add unresolved question of `break 'fn ..`
@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

Also a nit on terminology. With type ascription, we constrain the type of an expression with an annotation, but here we are binding new lifetime identifier. I'd think that actual lifetime ascription would be using an explicit (already bound) lifetime with the & operator. We should pick a different term like "explicit named lexical lifetimes"

Contributor

Ericson2314 commented Jan 7, 2017

Also a nit on terminology. With type ascription, we constrain the type of an expression with an annotation, but here we are binding new lifetime identifier. I'd think that actual lifetime ascription would be using an explicit (already bound) lifetime with the & operator. We should pick a different term like "explicit named lexical lifetimes"

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

@comex the example makes sense if it is supposed to be all within a function body. @llogiq maybe make the function explicit syntax types defined within a function are somewhat exotic?

Contributor

Ericson2314 commented Jan 7, 2017

@comex the example makes sense if it is supposed to be all within a function body. @llogiq maybe make the function explicit syntax types defined within a function are somewhat exotic?

@comex

This comment has been minimized.

Show comment
Hide comment
@comex

comex Jan 7, 2017

@Ericson2314 Having function-local bindings (in this case lifetimes) apply to nested items would be a significant change, albeit one that I'd like to see.

@whitequark Yes, but how is that implemented? Shall there be an implicit linked list of allocaed values to call destructors on? ...Actually, scratch that; this doesn't even make sense for values with destructors because there's no way to translate the strictly-outlives rule. I don't see how you'd prevent a situation where two structs with Drop impls have 'fn references pointing to each other.

comex commented Jan 7, 2017

@Ericson2314 Having function-local bindings (in this case lifetimes) apply to nested items would be a significant change, albeit one that I'd like to see.

@whitequark Yes, but how is that implemented? Shall there be an implicit linked list of allocaed values to call destructors on? ...Actually, scratch that; this doesn't even make sense for values with destructors because there's no way to translate the strictly-outlives rule. I don't see how you'd prevent a situation where two structs with Drop impls have 'fn references pointing to each other.

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

@comex excellent points. I might argue however that the latter is a prexisting problem we just duck by not allowing the user to ask for specific lifetimes.

Contributor

Ericson2314 commented Jan 7, 2017

@comex excellent points. I might argue however that the latter is a prexisting problem we just duck by not allowing the user to ask for specific lifetimes.

Ericson2314 added some commits Jan 7, 2017

Put example in function body to make clear 'fn is bound
Also fix type error with missing & operator
One sentance per line
This helps make diffs more readable because there is no longer
manual rewrapping every time.

I propose this as a general policy in #1811, but absent one right
now I think its fine to do this already.
@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

Hmm. So currently @whitequark's desugaring doesn't work very well: https://is.gd/7vWrMK. But according my formalization in https://internals.rust-lang.org/t/a-stateful-mir-for-rust/3596 or (if you squint) @nikomatsakis's outlives-at relation (where I got the idea), it's OK to borrow for an already-entered lifetime. This would make that example valid.

But this is some thorny stuff to figure out for our type system (actual axioms for lifetimes, not just a magic borrow checking algorithm we trust!), so perhaps it is easier to start with full named lexical lifetimes.

Contributor

Ericson2314 commented Jan 7, 2017

Hmm. So currently @whitequark's desugaring doesn't work very well: https://is.gd/7vWrMK. But according my formalization in https://internals.rust-lang.org/t/a-stateful-mir-for-rust/3596 or (if you squint) @nikomatsakis's outlives-at relation (where I got the idea), it's OK to borrow for an already-entered lifetime. This would make that example valid.

But this is some thorny stuff to figure out for our type system (actual axioms for lifetimes, not just a magic borrow checking algorithm we trust!), so perhaps it is easier to start with full named lexical lifetimes.

@camlorn

This comment has been minimized.

Show comment
Hide comment
@camlorn

camlorn Jan 7, 2017

Why not just move to full lifetime ascription?

It seems to me that we could have an RFC for it that says we'll implement some parts before others as opposed to this and presumably an RFC for that in future.

I'm kind of assuming that something about this proposal is easy to implement.

What about compatibility concerns with 'fn already being used by user code? Is 'fn already forbidden because fn is a keyword?

camlorn commented Jan 7, 2017

Why not just move to full lifetime ascription?

It seems to me that we could have an RFC for it that says we'll implement some parts before others as opposed to this and presumably an RFC for that in future.

I'm kind of assuming that something about this proposal is easy to implement.

What about compatibility concerns with 'fn already being used by user code? Is 'fn already forbidden because fn is a keyword?

@comex

This comment has been minimized.

Show comment
Hide comment
@comex

comex Jan 7, 2017

@Ericson2314 Hrm, can you clarify "OK to borrow for an already-entered lifetime"? Normally of course if you have an &'a Foo (for a lifetime parameter 'a) you can send it to the current function's caller by returning it, storing it in a reference, etc., so it wouldn't make sense to give a stack variable that type. I read @whitequark as assuming that 'a is unique and not referenced by anything else in the signature, in which case it works out, but that doesn't seem to match up with what you're saying.

comex commented Jan 7, 2017

@Ericson2314 Hrm, can you clarify "OK to borrow for an already-entered lifetime"? Normally of course if you have an &'a Foo (for a lifetime parameter 'a) you can send it to the current function's caller by returning it, storing it in a reference, etc., so it wouldn't make sense to give a stack variable that type. I read @whitequark as assuming that 'a is unique and not referenced by anything else in the signature, in which case it works out, but that doesn't seem to match up with what you're saying.

@llogiq

This comment has been minimized.

Show comment
Hide comment
@llogiq

llogiq Jan 7, 2017

Contributor

@camlorn that is the long-term plan, but the 'fn lifetime will give us more bang/buck short-term and works quite well as an extension even if we move to fully ascribed lifetimes, because function block labels look weird.

Contributor

llogiq commented Jan 7, 2017

@camlorn that is the long-term plan, but the 'fn lifetime will give us more bang/buck short-term and works quite well as an extension even if we move to fully ascribed lifetimes, because function block labels look weird.

@camlorn

This comment has been minimized.

Show comment
Hide comment
@camlorn

camlorn Jan 7, 2017

@llogiq
I agree that this is forward compatible, but the following doesn't seem odd to me:

fn foo() { 'fn
...
}

It's consistent in that it's the same, at least supposing the syntax is { 'lifetime. I don't see why the top level should be different.

camlorn commented Jan 7, 2017

@llogiq
I agree that this is forward compatible, but the following doesn't seem odd to me:

fn foo() { 'fn
...
}

It's consistent in that it's the same, at least supposing the syntax is { 'lifetime. I don't see why the top level should be different.

@llogiq

This comment has been minimized.

Show comment
Hide comment
@llogiq

llogiq Jan 7, 2017

Contributor

@camlorn the syntax that labels use (and we don't want to change it) is 'lifetime: { .. }. The text even has an example of this.

Contributor

llogiq commented Jan 7, 2017

@camlorn the syntax that labels use (and we don't want to change it) is 'lifetime: { .. }. The text even has an example of this.

@llogiq

This comment has been minimized.

Show comment
Hide comment
@llogiq

llogiq Jan 7, 2017

Contributor

Also, yes, fn is a keyword.

Contributor

llogiq commented Jan 7, 2017

Also, yes, fn is a keyword.

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

@comex so

let b = ..;
'a: {
  let x: &'a _ = &b;
}

is for sure OK, but we want to effectively do

'a: {
  let b = ..;
  let x: &'a _ = &b;
}

where the lifetime of b only properly outlives 'a if we exclude everything that happens before the borrow.

Contributor

Ericson2314 commented Jan 7, 2017

@comex so

let b = ..;
'a: {
  let x: &'a _ = &b;
}

is for sure OK, but we want to effectively do

'a: {
  let b = ..;
  let x: &'a _ = &b;
}

where the lifetime of b only properly outlives 'a if we exclude everything that happens before the borrow.

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

@comex hmm this may still be irredeemable because I think we ought to treat the destruction of a as happening before the function body ends. [That is the approach I adopted in https://internals.rust-lang.org/t/a-stateful-mir-for-rust/3596 as part of making drop glue explicit in safe stateful-MIR.]

Contributor

Ericson2314 commented Jan 7, 2017

@comex hmm this may still be irredeemable because I think we ought to treat the destruction of a as happening before the function body ends. [That is the approach I adopted in https://internals.rust-lang.org/t/a-stateful-mir-for-rust/3596 as part of making drop glue explicit in safe stateful-MIR.]

Show outdated Hide outdated text/0000-fn-lifetime.md Outdated
@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 7, 2017

Contributor

@llogiq btw if you didn't see it, llogiq#2 more commits for you to merge/cherry-pick/steal-from/whatever.

Contributor

Ericson2314 commented Jan 7, 2017

@llogiq btw if you didn't see it, llogiq#2 more commits for you to merge/cherry-pick/steal-from/whatever.

@eddyb

This comment has been minimized.

Show comment
Hide comment
@eddyb

eddyb Jan 8, 2017

Member

(moved from diff comment)

@Ericson2314 If we had nested generics (which we don't), the former requires injecting an extra parameter, which is supplied by uses in the surrounding function, which is my second point.
There is no need to allow it in this form, and I don't think @whitequark was thinking of doing anything about type declarations (I sure wasn't), only borrowing expressions.

That is, &'fn Node { ... } to allocate one in the current stack frame, dynamically.
Oh btw you can't infer this allocation thing from the type, it has to syntactically be in the borrow expression for it to be usable to place it in the right scope accordingly.
Which leads to... drops. How would one even drop such a thing? A linked list of dynamic allocations and their associated drop glue? This might actually require something that goes with placement-in to allocate the raw space on the stack, and to be used with custom-allocator-enabled containers.

Member

eddyb commented Jan 8, 2017

(moved from diff comment)

@Ericson2314 If we had nested generics (which we don't), the former requires injecting an extra parameter, which is supplied by uses in the surrounding function, which is my second point.
There is no need to allow it in this form, and I don't think @whitequark was thinking of doing anything about type declarations (I sure wasn't), only borrowing expressions.

That is, &'fn Node { ... } to allocate one in the current stack frame, dynamically.
Oh btw you can't infer this allocation thing from the type, it has to syntactically be in the borrow expression for it to be usable to place it in the right scope accordingly.
Which leads to... drops. How would one even drop such a thing? A linked list of dynamic allocations and their associated drop glue? This might actually require something that goes with placement-in to allocate the raw space on the stack, and to be used with custom-allocator-enabled containers.

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 Jan 8, 2017

Contributor

@eddyb Makes sense. Here a and b I assume would be the same, but the point is with 'fn one can dynamically allocate?

fn foo<'a>() {
    let x;
    {
        x = Box::new(1u32);
        let a = Box::new(&x);
    }   
}

fn bar<'a>() {
    {
        let b = Box::new(&'fn Box::new(1u32));
    }
}

@llogiq sorry I should have thought more about the motivations for this coming from the alloca RFC.

Contributor

Ericson2314 commented Jan 8, 2017

@eddyb Makes sense. Here a and b I assume would be the same, but the point is with 'fn one can dynamically allocate?

fn foo<'a>() {
    let x;
    {
        x = Box::new(1u32);
        let a = Box::new(&x);
    }   
}

fn bar<'a>() {
    {
        let b = Box::new(&'fn Box::new(1u32));
    }
}

@llogiq sorry I should have thought more about the motivations for this coming from the alloca RFC.

@eddyb

This comment has been minimized.

Show comment
Hide comment
@eddyb

eddyb Jan 8, 2017

Member

@Ericson2314 That looks about right, and if you decide to go with a dynamic per-stack-frame "drop list" (which I believe is what Go has w/ defer? @pcwalton keeps mentioning it), it would presumably work.

Member

eddyb commented Jan 8, 2017

@Ericson2314 That looks about right, and if you decide to go with a dynamic per-stack-frame "drop list" (which I believe is what Go has w/ defer? @pcwalton keeps mentioning it), it would presumably work.

@llogiq llogiq referenced this pull request Feb 21, 2017

Merged

Unsized Rvalues #1909

@arielb1

This comment has been minimized.

Show comment
Hide comment
@arielb1

arielb1 Feb 24, 2017

Contributor

With the current semantics of Rust, forcing borrows to some lifetime won't help you - lifetimes don't affect the destruction order of locals.

What you do want is to create locals without a corresponding drop (I don't think we can't make destructors run without having a compiler-generated linked list, including the drop flags, per local, which I don't think is a particularly smart thing to do), so they are "leaked" on the next reinitialization. That's why I think the syntax should be on the local. For example,

fn foo() {
    // here we ascribe the `'fn` lifetime to `next`
    let leak start = Node { data: 0, None };
    let mut head = &start;
    for i in iter {
        let leak cur = Node { data: i, Some(head) };
        head = &cur;
    }
}
Contributor

arielb1 commented Feb 24, 2017

With the current semantics of Rust, forcing borrows to some lifetime won't help you - lifetimes don't affect the destruction order of locals.

What you do want is to create locals without a corresponding drop (I don't think we can't make destructors run without having a compiler-generated linked list, including the drop flags, per local, which I don't think is a particularly smart thing to do), so they are "leaked" on the next reinitialization. That's why I think the syntax should be on the local. For example,

fn foo() {
    // here we ascribe the `'fn` lifetime to `next`
    let leak start = Node { data: 0, None };
    let mut head = &start;
    for i in iter {
        let leak cur = Node { data: i, Some(head) };
        head = &cur;
    }
}
@arielb1

This comment has been minimized.

Show comment
Hide comment
@arielb1

arielb1 Feb 24, 2017

Contributor

@whitequark

Looking at your alloca versions, the only borrow checker change needed would be to have it ignore borrows on "previous" instantiations of a local when looking at borrows for the current instantiation - and the only reason you care about borrows of "previous" instantiations is for destructors, which I'm not sure we want.

Basically the "dropless" version is equivalent to supporting:

let mut x0 = 0;
let mut x1 = 1;
let mut x_ = &mut x0;
let z = &mut *x_;
x_ = &mut x1;
use(z);

Adding 'fn and block lifetimes to Rust should not be that hard - we already have the scopes available, we just need to wire up the syntax.

Contributor

arielb1 commented Feb 24, 2017

@whitequark

Looking at your alloca versions, the only borrow checker change needed would be to have it ignore borrows on "previous" instantiations of a local when looking at borrows for the current instantiation - and the only reason you care about borrows of "previous" instantiations is for destructors, which I'm not sure we want.

Basically the "dropless" version is equivalent to supporting:

let mut x0 = 0;
let mut x1 = 1;
let mut x_ = &mut x0;
let z = &mut *x_;
x_ = &mut x1;
use(z);

Adding 'fn and block lifetimes to Rust should not be that hard - we already have the scopes available, we just need to wire up the syntax.

@whitequark

This comment has been minimized.

Show comment
Hide comment
@whitequark

whitequark Feb 24, 2017

@arielb1 I have some doubts the "dropless" version will be accepted, seeing as it's quite non-orthogonal.

whitequark commented Feb 24, 2017

@arielb1 I have some doubts the "dropless" version will be accepted, seeing as it's quite non-orthogonal.

@llogiq

This comment has been minimized.

Show comment
Hide comment
@llogiq

llogiq Feb 24, 2017

Contributor

Sorry, @whitequark, but I ran out of steam before completing the lifetime ascription RFC. There are a few interactions we may want to think about (for example ascription should be able to extend, but not restrict the lifetime).

Contributor

llogiq commented Feb 24, 2017

Sorry, @whitequark, but I ran out of steam before completing the lifetime ascription RFC. There are a few interactions we may want to think about (for example ascription should be able to extend, but not restrict the lifetime).

@eddyb

This comment has been minimized.

Show comment
Hide comment
@eddyb

eddyb Feb 24, 2017

Member

@arielb1 My intention with &'a rvalue is not to only hint a lifetime, but force allocation in an 'a scope.
If there are any loops between the 'a scope and &'a rvalue, you have to either ban it, force dropless or have a linked list of destructors dynamically alloca'd at the same time as the data itself.

EDIT: This is also why I don't use the syntax &rvalue: &'a T because that shouldn't affect drop scopes.

Member

eddyb commented Feb 24, 2017

@arielb1 My intention with &'a rvalue is not to only hint a lifetime, but force allocation in an 'a scope.
If there are any loops between the 'a scope and &'a rvalue, you have to either ban it, force dropless or have a linked list of destructors dynamically alloca'd at the same time as the data itself.

EDIT: This is also why I don't use the syntax &rvalue: &'a T because that shouldn't affect drop scopes.

@eddyb

This comment has been minimized.

Show comment
Hide comment
@eddyb

eddyb Feb 24, 2017

Member

Another suggestion is roughly Stack::<'a> <- rvalue, which would be a fancier version of &move.

Member

eddyb commented Feb 24, 2017

Another suggestion is roughly Stack::<'a> <- rvalue, which would be a fancier version of &move.

@arielb1

This comment has been minimized.

Show comment
Hide comment
@arielb1

arielb1 Feb 24, 2017

Contributor

Forbidding types with destructors seems like a smarter choice then leaking, indeed.

Contributor

arielb1 commented Feb 24, 2017

Forbidding types with destructors seems like a smarter choice then leaking, indeed.

@carols10cents carols10cents added this to Merge proposed in Tracker Apr 26, 2017

@aturon

This comment has been minimized.

Show comment
Hide comment
@aturon

aturon Apr 29, 2017

Member

This RFC has gone quiet, without much clear conclusion. @whitequark, what's your current thinking here? How do we make progress on this front?

Member

aturon commented Apr 29, 2017

This RFC has gone quiet, without much clear conclusion. @whitequark, what's your current thinking here? How do we make progress on this front?

@whitequark

This comment has been minimized.

Show comment
Hide comment
@whitequark

whitequark Apr 29, 2017

@aturon It seems like this is the result of:

  • the RFC really being four RFCs in a trenchcoat, with a bunch of fine detail in each;
  • a lack of clear understanding of whether this four-RFC plan is even a right direction (no one objected, but I'm not sure how many people paid attention);
  • requiring a significant amount of grunt work and re-work, which exhausted @llogiq, who I believe did most of it.

I'd like to hear from other @rust-lang/lang team members whether the overall set of parts that ought to eventually fit together seems acceptable. If it is... personally I won't have time to get an RFC through in at least 1-2 months, perhaps @llogiq could take another stab. I am still quite interested in the features and going to participate in the design process, of course.

whitequark commented Apr 29, 2017

@aturon It seems like this is the result of:

  • the RFC really being four RFCs in a trenchcoat, with a bunch of fine detail in each;
  • a lack of clear understanding of whether this four-RFC plan is even a right direction (no one objected, but I'm not sure how many people paid attention);
  • requiring a significant amount of grunt work and re-work, which exhausted @llogiq, who I believe did most of it.

I'd like to hear from other @rust-lang/lang team members whether the overall set of parts that ought to eventually fit together seems acceptable. If it is... personally I won't have time to get an RFC through in at least 1-2 months, perhaps @llogiq could take another stab. I am still quite interested in the features and going to participate in the design process, of course.

@aturon

This comment has been minimized.

Show comment
Hide comment
@aturon

aturon Apr 29, 2017

Member

@whitequark Thanks much!

I propose that we hold a dedicated meeting with various interested stakeholders, and try to hammer out some of these questions at high bandwidth. (Either as a lang team meeting or a separate ad hoc one.)

Anyone who would like to be included in such a meeting, please let me know.

Member

aturon commented Apr 29, 2017

@whitequark Thanks much!

I propose that we hold a dedicated meeting with various interested stakeholders, and try to hammer out some of these questions at high bandwidth. (Either as a lang team meeting or a separate ad hoc one.)

Anyone who would like to be included in such a meeting, please let me know.

@whitequark

This comment has been minimized.

Show comment
Hide comment
@whitequark

whitequark commented Apr 29, 2017

@aturon Sounds good!

@aturon

This comment has been minimized.

Show comment
Hide comment
@aturon

aturon May 3, 2017

Member

@whitequark @nikomatsakis @eddyb any pointers on the stakeholders to include? I believe this was discussed at the compiler sprint?

Member

aturon commented May 3, 2017

@whitequark @nikomatsakis @eddyb any pointers on the stakeholders to include? I believe this was discussed at the compiler sprint?

@nikomatsakis

This comment has been minimized.

Show comment
Hide comment
@nikomatsakis

nikomatsakis May 5, 2017

Contributor

Well, we discussed primarily the "unsized rvalues" RFC (#1909), which is certainly a way to support alloca, though it is somewhat orthogonal from this RFC I believe.

I think that what I personally want out of this RFC is not necessarily the same as what @Ericson2314 wanted. I am primarily interested in a better way to teach Rust and to teach lifetimes in particular. To that end, I think that having explicit syntax can be a great way to expose the mechanics. So I'd like to be able to give names to blocks and so forth (e.g., 'a: {...}) and then refer to those names from borrows or other expressions &'a foo. This would let you illustrate the rules in a very explicit way. I had not originally envisioned any special 'fn lifetime, but that seems like it could be a handy addition.

So, I suppose in terms of "stakeholders", I could see two groups. If we're talking about allocas, then I would include @arielb1, who put a lot of effort into #1909, and naturally @eddyb.

If we're talking about teaching lifetimes, I might include other people (@wycats, perhaps).

Contributor

nikomatsakis commented May 5, 2017

Well, we discussed primarily the "unsized rvalues" RFC (#1909), which is certainly a way to support alloca, though it is somewhat orthogonal from this RFC I believe.

I think that what I personally want out of this RFC is not necessarily the same as what @Ericson2314 wanted. I am primarily interested in a better way to teach Rust and to teach lifetimes in particular. To that end, I think that having explicit syntax can be a great way to expose the mechanics. So I'd like to be able to give names to blocks and so forth (e.g., 'a: {...}) and then refer to those names from borrows or other expressions &'a foo. This would let you illustrate the rules in a very explicit way. I had not originally envisioned any special 'fn lifetime, but that seems like it could be a handy addition.

So, I suppose in terms of "stakeholders", I could see two groups. If we're talking about allocas, then I would include @arielb1, who put a lot of effort into #1909, and naturally @eddyb.

If we're talking about teaching lifetimes, I might include other people (@wycats, perhaps).

@ubsan

This comment has been minimized.

Show comment
Hide comment
@ubsan

ubsan May 5, 2017

Contributor

I'm interested in better ways of teaching lifetimes.

Contributor

ubsan commented May 5, 2017

I'm interested in better ways of teaching lifetimes.

@Ericson2314

This comment has been minimized.

Show comment
Hide comment
@Ericson2314

Ericson2314 May 11, 2017

Contributor

@nikomatsakis I think our interests are closer than you might imagine :).

If nothing else, my desire for move and out pointers leads me to be wary of the sublety of unsized rvalues and friends without them. I think the teaching portions of all of this (and IRC I originally thought this RFC was sidestepping the allocation stuff) are wanted by everyone, so let's factor them out and expedite them. I absolutely agree with @whitequark's division of labor—I'd just rearrange the teaching ones first.

I do like breaking out of all blocks, and break 'fn as a synonym for return. Maybe this is my battle alone :), but semantically I see it simpler than any alloca, and good for teaching too as it unifies previously disparate concepts. In any event, that would become a 5th RFC, whose fate is divorced from the rest.

Contributor

Ericson2314 commented May 11, 2017

@nikomatsakis I think our interests are closer than you might imagine :).

If nothing else, my desire for move and out pointers leads me to be wary of the sublety of unsized rvalues and friends without them. I think the teaching portions of all of this (and IRC I originally thought this RFC was sidestepping the allocation stuff) are wanted by everyone, so let's factor them out and expedite them. I absolutely agree with @whitequark's division of labor—I'd just rearrange the teaching ones first.

I do like breaking out of all blocks, and break 'fn as a synonym for return. Maybe this is my battle alone :), but semantically I see it simpler than any alloca, and good for teaching too as it unifies previously disparate concepts. In any event, that would become a 5th RFC, whose fate is divorced from the rest.

@joshtriplett

This comment has been minimized.

Show comment
Hide comment
@joshtriplett

joshtriplett Sep 3, 2017

Member

In #2137 , @canndrew mentions that this would help for defining the right lifetime for a VaList type. The mechanism for non-movable types might also help for that, in some circumstances.

Member

joshtriplett commented Sep 3, 2017

In #2137 , @canndrew mentions that this would help for defining the right lifetime for a VaList type. The mechanism for non-movable types might also help for that, in some circumstances.

@aturon

This comment has been minimized.

Show comment
Hide comment
@aturon

aturon Sep 6, 2017

Member

I'm going to propose we postpone this RFC; we don't have bandwidth to convene the full stakeholders ahead of the impl period, and should revisit this area in 2018.

@rfcbot fcp postpone

Member

aturon commented Sep 6, 2017

I'm going to propose we postpone this RFC; we don't have bandwidth to convene the full stakeholders ahead of the impl period, and should revisit this area in 2018.

@rfcbot fcp postpone

@rfcbot

This comment has been minimized.

Show comment
Hide comment
@rfcbot

rfcbot Sep 6, 2017

Team member @aturon has proposed to postpone this. The next step is review by the rest of the tagged teams:

No concerns currently listed.

Once these reviewers reach consensus, this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up!

See this document for info about what commands tagged team members can give me.

rfcbot commented Sep 6, 2017

Team member @aturon has proposed to postpone this. The next step is review by the rest of the tagged teams:

No concerns currently listed.

Once these reviewers reach consensus, this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up!

See this document for info about what commands tagged team members can give me.

@llogiq

This comment has been minimized.

Show comment
Hide comment
@llogiq

llogiq Sep 6, 2017

Contributor

For the record, I'm fine with this, hopefully I have the energy to revisit it next year.

Contributor

llogiq commented Sep 6, 2017

For the record, I'm fine with this, hopefully I have the energy to revisit it next year.

@rfcbot

This comment has been minimized.

Show comment
Hide comment
@rfcbot

rfcbot Sep 19, 2017

🔔 This is now entering its final comment period, as per the review above. 🔔

rfcbot commented Sep 19, 2017

🔔 This is now entering its final comment period, as per the review above. 🔔

1 similar comment
@rfcbot

This comment has been minimized.

Show comment
Hide comment
@rfcbot

rfcbot Sep 19, 2017

🔔 This is now entering its final comment period, as per the review above. 🔔

rfcbot commented Sep 19, 2017

🔔 This is now entering its final comment period, as per the review above. 🔔

@aturon

This comment has been minimized.

Show comment
Hide comment
@aturon

aturon Sep 29, 2017

Member

I'm going to close this RFC as postponed for the time being, as per previous comments; we hope to revisit after various other dust has settled! Thanks @llogiq!

Member

aturon commented Sep 29, 2017

I'm going to close this RFC as postponed for the time being, as per previous comments; we hope to revisit after various other dust has settled! Thanks @llogiq!

@aturon aturon closed this Sep 29, 2017

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment