Skip to content

Commit b226e46

Browse files
committed
add mir-opt test
1 parent fd5b624 commit b226e46

2 files changed

Lines changed: 369 additions & 0 deletions

File tree

Lines changed: 331 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,331 @@
1+
// MIR for `my_async_fn::{closure#0}` after StateTransform
2+
/* coroutine_layout = CoroutineLayout {
3+
field_tys: {
4+
_s0: CoroutineSavedTy {
5+
ty: std::pin::UnsafePinned<std::boxed::Box<i32, std::alloc::Global>>,
6+
source_info: SourceInfo {
7+
span: $DIR/async_self_referential_fields.rs:27:9: 27:10 (#0),
8+
scope: scope[0],
9+
},
10+
ignore_for_traits: false,
11+
},
12+
_s1: CoroutineSavedTy {
13+
ty: &'{erased} std::boxed::Box<i32, std::alloc::Global>,
14+
source_info: SourceInfo {
15+
span: $DIR/async_self_referential_fields.rs:28:9: 28:10 (#0),
16+
scope: scope[1],
17+
},
18+
ignore_for_traits: false,
19+
},
20+
_s2: CoroutineSavedTy {
21+
ty: Coroutine(
22+
DefId(0:15 ~ async_self_referential_fields[ea9b]::inner_async_fn::{closure#0}),
23+
[
24+
(),
25+
std::future::ResumeTy,
26+
(),
27+
(),
28+
(),
29+
],
30+
),
31+
source_info: SourceInfo {
32+
span: $DIR/async_self_referential_fields.rs:29:5: 29:27 (#10),
33+
scope: scope[2],
34+
},
35+
ignore_for_traits: false,
36+
},
37+
},
38+
variant_fields: {
39+
Unresumed(0): [],
40+
Returned (1): [],
41+
Panicked (2): [],
42+
Suspend0 (3): [_s0, _s1, _s2],
43+
},
44+
storage_conflicts: BitMatrix(3x3) {
45+
(_s0, _s0),
46+
(_s0, _s1),
47+
(_s0, _s2),
48+
(_s1, _s0),
49+
(_s1, _s1),
50+
(_s1, _s2),
51+
(_s2, _s0),
52+
(_s2, _s1),
53+
(_s2, _s2),
54+
},
55+
} */
56+
57+
fn my_async_fn::{closure#0}(_1: Pin<&mut {async fn body of my_async_fn()}>, _2: &mut std::task::Context<'_>) -> std::task::Poll<i32> {
58+
debug _task_context => _2;
59+
let mut _0: std::task::Poll<i32>;
60+
let _3: std::boxed::Box<i32>;
61+
let _5: ();
62+
let mut _6: {async fn body of inner_async_fn()};
63+
let mut _7: {async fn body of inner_async_fn()};
64+
let mut _9: ();
65+
let _10: ();
66+
let mut _11: std::task::Poll<()>;
67+
let mut _12: std::pin::Pin<&mut {async fn body of inner_async_fn()}>;
68+
let mut _13: &mut {async fn body of inner_async_fn()};
69+
let mut _14: &mut {async fn body of inner_async_fn()};
70+
let mut _15: &mut std::task::Context<'_>;
71+
let mut _16: &mut std::task::Context<'_>;
72+
let mut _17: &mut std::task::Context<'_>;
73+
let mut _18: isize;
74+
let mut _20: !;
75+
let mut _21: &mut std::task::Context<'_>;
76+
let mut _22: ();
77+
let _23: &std::boxed::Box<i32>;
78+
let mut _24: &std::boxed::Box<i32>;
79+
let mut _25: i32;
80+
let mut _26: *const i32;
81+
let mut _27: i32;
82+
let mut _28: u32;
83+
let mut _29: &mut {async fn body of my_async_fn()};
84+
scope 1 {
85+
debug x => (((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>);
86+
let _4: &std::boxed::Box<i32>;
87+
scope 2 {
88+
debug y => (((*_29) as variant#3).1: &std::boxed::Box<i32>);
89+
let mut _8: {async fn body of inner_async_fn()};
90+
scope 3 {
91+
debug __awaitee => (((*_29) as variant#3).2: {async fn body of inner_async_fn()});
92+
let _19: ();
93+
scope 4 {
94+
debug result => _19;
95+
}
96+
}
97+
}
98+
}
99+
100+
bb0: {
101+
_29 = copy (_1.0: &mut {async fn body of my_async_fn()});
102+
_28 = discriminant((*_29));
103+
switchInt(move _28) -> [0: bb1, 1: bb33, 2: bb32, 3: bb31, otherwise: bb9];
104+
}
105+
106+
bb1: {
107+
nop;
108+
(((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>) = Box::<i32>::new(const 5_i32) -> [return: bb2, unwind: bb27];
109+
}
110+
111+
bb2: {
112+
nop;
113+
(((*_29) as variant#3).1: &std::boxed::Box<i32>) = &(((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>);
114+
StorageLive(_5);
115+
StorageLive(_6);
116+
StorageLive(_7);
117+
_7 = inner_async_fn() -> [return: bb3, unwind: bb24];
118+
}
119+
120+
bb3: {
121+
_6 = <{async fn body of inner_async_fn()} as IntoFuture>::into_future(move _7) -> [return: bb4, unwind: bb23];
122+
}
123+
124+
bb4: {
125+
StorageDead(_7);
126+
PlaceMention(_6);
127+
nop;
128+
(((*_29) as variant#3).2: {async fn body of inner_async_fn()}) = move _6;
129+
goto -> bb5;
130+
}
131+
132+
bb5: {
133+
StorageLive(_10);
134+
StorageLive(_11);
135+
StorageLive(_12);
136+
StorageLive(_13);
137+
StorageLive(_14);
138+
_14 = &mut (((*_29) as variant#3).2: {async fn body of inner_async_fn()});
139+
_13 = &mut (*_14);
140+
_12 = Pin::<&mut {async fn body of inner_async_fn()}>::new_unchecked(move _13) -> [return: bb6, unwind: bb20];
141+
}
142+
143+
bb6: {
144+
StorageDead(_13);
145+
StorageLive(_15);
146+
StorageLive(_16);
147+
StorageLive(_17);
148+
_17 = copy _2;
149+
_16 = move _17;
150+
goto -> bb7;
151+
}
152+
153+
bb7: {
154+
_15 = &mut (*_16);
155+
StorageDead(_17);
156+
_11 = <{async fn body of inner_async_fn()} as Future>::poll(move _12, move _15) -> [return: bb8, unwind: bb19];
157+
}
158+
159+
bb8: {
160+
StorageDead(_15);
161+
StorageDead(_12);
162+
PlaceMention(_11);
163+
_18 = discriminant(_11);
164+
switchInt(move _18) -> [0: bb11, 1: bb10, otherwise: bb9];
165+
}
166+
167+
bb9: {
168+
unreachable;
169+
}
170+
171+
bb10: {
172+
_10 = const ();
173+
StorageDead(_16);
174+
StorageDead(_14);
175+
StorageDead(_11);
176+
StorageDead(_10);
177+
StorageLive(_21);
178+
StorageLive(_22);
179+
_22 = ();
180+
_0 = std::task::Poll::<i32>::Pending;
181+
StorageDead(_5);
182+
StorageDead(_6);
183+
StorageDead(_21);
184+
StorageDead(_22);
185+
discriminant((*_29)) = 3;
186+
return;
187+
}
188+
189+
bb11: {
190+
StorageLive(_19);
191+
_19 = copy ((_11 as Ready).0: ());
192+
_5 = copy _19;
193+
StorageDead(_19);
194+
StorageDead(_16);
195+
StorageDead(_14);
196+
StorageDead(_11);
197+
StorageDead(_10);
198+
drop((((*_29) as variant#3).2: {async fn body of inner_async_fn()})) -> [return: bb13, unwind: bb22];
199+
}
200+
201+
bb12: {
202+
StorageDead(_22);
203+
_2 = move _21;
204+
StorageDead(_21);
205+
_9 = const ();
206+
goto -> bb5;
207+
}
208+
209+
bb13: {
210+
nop;
211+
goto -> bb14;
212+
}
213+
214+
bb14: {
215+
StorageDead(_6);
216+
StorageDead(_5);
217+
StorageLive(_23);
218+
StorageLive(_24);
219+
_24 = copy (((*_29) as variant#3).1: &std::boxed::Box<i32>);
220+
_23 = std::hint::black_box::<&Box<i32>>(move _24) -> [return: bb15, unwind: bb18];
221+
}
222+
223+
bb15: {
224+
StorageDead(_24);
225+
StorageDead(_23);
226+
StorageLive(_25);
227+
_26 = copy (((((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>).0: std::ptr::Unique<i32>).0: std::ptr::NonNull<i32>) as *const i32 (Transmute);
228+
_25 = copy (*_26);
229+
_27 = Add(move _25, const 1_i32);
230+
StorageDead(_25);
231+
nop;
232+
drop((((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>)) -> [return: bb16, unwind: bb27];
233+
}
234+
235+
bb16: {
236+
nop;
237+
goto -> bb29;
238+
}
239+
240+
bb17: {
241+
_0 = std::task::Poll::<i32>::Ready(move _27);
242+
discriminant((*_29)) = 1;
243+
return;
244+
}
245+
246+
bb18 (cleanup): {
247+
StorageDead(_24);
248+
StorageDead(_23);
249+
goto -> bb26;
250+
}
251+
252+
bb19 (cleanup): {
253+
StorageDead(_15);
254+
StorageDead(_12);
255+
StorageDead(_16);
256+
goto -> bb21;
257+
}
258+
259+
bb20 (cleanup): {
260+
StorageDead(_13);
261+
StorageDead(_12);
262+
goto -> bb21;
263+
}
264+
265+
bb21 (cleanup): {
266+
StorageDead(_14);
267+
StorageDead(_11);
268+
StorageDead(_10);
269+
drop((((*_29) as variant#3).2: {async fn body of inner_async_fn()})) -> [return: bb22, unwind terminate(cleanup)];
270+
}
271+
272+
bb22 (cleanup): {
273+
nop;
274+
goto -> bb25;
275+
}
276+
277+
bb23 (cleanup): {
278+
goto -> bb24;
279+
}
280+
281+
bb24 (cleanup): {
282+
StorageDead(_7);
283+
goto -> bb25;
284+
}
285+
286+
bb25 (cleanup): {
287+
StorageDead(_6);
288+
StorageDead(_5);
289+
goto -> bb26;
290+
}
291+
292+
bb26 (cleanup): {
293+
nop;
294+
drop((((((*_29) as variant#3).0: std::pin::UnsafePinned<std::boxed::Box<i32>>).0: std::cell::UnsafeCell<std::boxed::Box<i32>>).0: std::boxed::Box<i32>)) -> [return: bb27, unwind terminate(cleanup)];
295+
}
296+
297+
bb27 (cleanup): {
298+
nop;
299+
goto -> bb28;
300+
}
301+
302+
bb28 (cleanup): {
303+
goto -> bb30;
304+
}
305+
306+
bb29: {
307+
goto -> bb17;
308+
}
309+
310+
bb30 (cleanup): {
311+
discriminant((*_29)) = 2;
312+
resume;
313+
}
314+
315+
bb31: {
316+
StorageLive(_5);
317+
StorageLive(_6);
318+
StorageLive(_21);
319+
StorageLive(_22);
320+
_21 = move _2;
321+
goto -> bb12;
322+
}
323+
324+
bb32: {
325+
assert(const false, "`async fn` resumed after panicking") -> [success: bb32, unwind continue];
326+
}
327+
328+
bb33: {
329+
assert(const false, "`async fn` resumed after completion") -> [success: bb33, unwind continue];
330+
}
331+
}
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
//@ edition:2021
2+
// skip-filecheck
3+
// EMIT_MIR async_self_referential_fields.my_async_fn-{closure#0}.StateTransform.after.mir
4+
5+
#![allow(unused)]
6+
7+
use std::future::Future;
8+
use std::ops::{AsyncFn, AsyncFnMut, AsyncFnOnce};
9+
use std::pin::pin;
10+
use std::task::*;
11+
12+
pub fn block_on<T>(fut: impl Future<Output = T>) -> T {
13+
let mut fut = pin!(fut);
14+
let ctx = &mut Context::from_waker(Waker::noop());
15+
16+
loop {
17+
match fut.as_mut().poll(ctx) {
18+
Poll::Pending => {}
19+
Poll::Ready(t) => break t,
20+
}
21+
}
22+
}
23+
24+
async fn inner_async_fn() {}
25+
26+
async fn my_async_fn() -> i32 {
27+
let x = Box::new(5);
28+
let y = &x;
29+
inner_async_fn().await;
30+
std::hint::black_box(y);
31+
*x + 1
32+
}
33+
34+
fn main() {
35+
block_on(async {
36+
my_async_fn().await;
37+
});
38+
}

0 commit comments

Comments
 (0)