@@ -29,18 +29,19 @@ A syntactical example of a generator is:
29
29
#![feature(generators, generator_trait)]
30
30
31
31
use std :: ops :: {Generator , GeneratorState };
32
+ use std :: pin :: Pin ;
32
33
33
34
fn main () {
34
35
let mut generator = || {
35
36
yield 1 ;
36
37
return " foo"
37
38
};
38
39
39
- match unsafe { generator . resume () } {
40
+ match Pin :: new ( & mut generator ) . resume () {
40
41
GeneratorState :: Yielded (1 ) => {}
41
42
_ => panic! (" unexpected value from resume" ),
42
43
}
43
- match unsafe { generator . resume () } {
44
+ match Pin :: new ( & mut generator ) . resume () {
44
45
GeneratorState :: Complete (" foo" ) => {}
45
46
_ => panic! (" unexpected value from resume" ),
46
47
}
@@ -60,6 +61,7 @@ prints all numbers in order:
60
61
#![feature(generators, generator_trait)]
61
62
62
63
use std :: ops :: Generator ;
64
+ use std :: pin :: Pin ;
63
65
64
66
fn main () {
65
67
let mut generator = || {
@@ -69,9 +71,9 @@ fn main() {
69
71
};
70
72
71
73
println! (" 1" );
72
- unsafe { generator . resume () } ;
74
+ Pin :: new ( & mut generator ) . resume ();
73
75
println! (" 3" );
74
- unsafe { generator . resume () } ;
76
+ Pin :: new ( & mut generator ) . resume ();
75
77
println! (" 5" );
76
78
}
77
79
```
@@ -86,13 +88,14 @@ Feedback on the design and usage is always appreciated!
86
88
The ` Generator ` trait in ` std::ops ` currently looks like:
87
89
88
90
```
89
- # #![feature(generator_trait)]
91
+ # #![feature(arbitrary_self_types, generator_trait)]
90
92
# use std::ops::GeneratorState;
93
+ # use std::pin::Pin;
91
94
92
95
pub trait Generator {
93
96
type Yield;
94
97
type Return;
95
- unsafe fn resume(&mut self ) -> GeneratorState<Self::Yield, Self::Return>;
98
+ fn resume(self: Pin< &mut Self> ) -> GeneratorState<Self::Yield, Self::Return>;
96
99
}
97
100
```
98
101
@@ -167,6 +170,7 @@ Let's take a look at an example to see what's going on here:
167
170
#![feature(generators, generator_trait)]
168
171
169
172
use std :: ops :: Generator ;
173
+ use std :: pin :: Pin ;
170
174
171
175
fn main () {
172
176
let ret = " foo" ;
@@ -175,17 +179,18 @@ fn main() {
175
179
return ret
176
180
};
177
181
178
- unsafe { generator . resume () } ;
179
- unsafe { generator . resume () } ;
182
+ Pin :: new ( & mut generator ) . resume ();
183
+ Pin :: new ( & mut generator ) . resume ();
180
184
}
181
185
```
182
186
183
187
This generator literal will compile down to something similar to:
184
188
185
189
``` rust
186
- #![feature(generators, generator_trait)]
190
+ #![feature(arbitrary_self_types, generators, generator_trait)]
187
191
188
192
use std :: ops :: {Generator , GeneratorState };
193
+ use std :: pin :: Pin ;
189
194
190
195
fn main () {
191
196
let ret = " foo" ;
@@ -200,9 +205,9 @@ fn main() {
200
205
type Yield = i32 ;
201
206
type Return = & 'static str ;
202
207
203
- unsafe fn resume (& mut self ) -> GeneratorState <i32 , & 'static str > {
208
+ fn resume (mut self : Pin < & mut Self > ) -> GeneratorState <i32 , & 'static str > {
204
209
use std :: mem;
205
- match mem :: replace (self , __Generator :: Done ) {
210
+ match mem :: replace (& mut * self , __Generator :: Done ) {
206
211
__Generator :: Start (s ) => {
207
212
* self = __Generator :: Yield1 (s );
208
213
GeneratorState :: Yielded (1 )
@@ -223,8 +228,8 @@ fn main() {
223
228
__Generator :: Start (ret )
224
229
};
225
230
226
- unsafe { generator . resume () } ;
227
- unsafe { generator . resume () } ;
231
+ Pin :: new ( & mut generator ) . resume ();
232
+ Pin :: new ( & mut generator ) . resume ();
228
233
}
229
234
```
230
235
0 commit comments