diff options
| author | Dario Nieuwenhuis <[email protected]> | 2021-02-02 05:14:52 +0100 |
|---|---|---|
| committer | Dario Nieuwenhuis <[email protected]> | 2021-02-02 05:20:41 +0100 |
| commit | aeaa34d7a163b327643c08e299e1b40bb497c01c (patch) | |
| tree | 6054344c8a7d990b910416a1002aded9ad4d10eb /embassy-macros/src | |
| parent | d098952077b8fdc8426754151bb8064214a046fa (diff) | |
Executor API V2.
- It's no longer possible to call run() reentrantly from within a task (soundness issue)
- it's now possible to spawn Send tasks across threads (SendSpawner, #37)
Diffstat (limited to 'embassy-macros/src')
| -rw-r--r-- | embassy-macros/src/lib.rs | 20 |
1 files changed, 15 insertions, 5 deletions
diff --git a/embassy-macros/src/lib.rs b/embassy-macros/src/lib.rs index cb16f65aa..23f1cda99 100644 --- a/embassy-macros/src/lib.rs +++ b/embassy-macros/src/lib.rs | |||
| @@ -11,21 +11,23 @@ use syn::spanned::Spanned; | |||
| 11 | struct MacroArgs { | 11 | struct MacroArgs { |
| 12 | #[darling(default)] | 12 | #[darling(default)] |
| 13 | pool_size: Option<usize>, | 13 | pool_size: Option<usize>, |
| 14 | #[darling(default)] | ||
| 15 | send: bool, | ||
| 14 | } | 16 | } |
| 15 | 17 | ||
| 16 | #[proc_macro_attribute] | 18 | #[proc_macro_attribute] |
| 17 | pub fn task(args: TokenStream, item: TokenStream) -> TokenStream { | 19 | pub fn task(args: TokenStream, item: TokenStream) -> TokenStream { |
| 18 | let args = syn::parse_macro_input!(args as syn::AttributeArgs); | 20 | let macro_args = syn::parse_macro_input!(args as syn::AttributeArgs); |
| 19 | let mut task_fn = syn::parse_macro_input!(item as syn::ItemFn); | 21 | let mut task_fn = syn::parse_macro_input!(item as syn::ItemFn); |
| 20 | 22 | ||
| 21 | let args = match MacroArgs::from_list(&args) { | 23 | let macro_args = match MacroArgs::from_list(¯o_args) { |
| 22 | Ok(v) => v, | 24 | Ok(v) => v, |
| 23 | Err(e) => { | 25 | Err(e) => { |
| 24 | return TokenStream::from(e.write_errors()); | 26 | return TokenStream::from(e.write_errors()); |
| 25 | } | 27 | } |
| 26 | }; | 28 | }; |
| 27 | 29 | ||
| 28 | let pool_size: usize = args.pool_size.unwrap_or(1); | 30 | let pool_size: usize = macro_args.pool_size.unwrap_or(1); |
| 29 | 31 | ||
| 30 | let mut fail = false; | 32 | let mut fail = false; |
| 31 | if task_fn.sig.asyncness.is_none() { | 33 | if task_fn.sig.asyncness.is_none() { |
| @@ -90,11 +92,16 @@ pub fn task(args: TokenStream, item: TokenStream) -> TokenStream { | |||
| 90 | 92 | ||
| 91 | let visibility = &task_fn.vis; | 93 | let visibility = &task_fn.vis; |
| 92 | task_fn.sig.ident = format_ident!("task"); | 94 | task_fn.sig.ident = format_ident!("task"); |
| 95 | let impl_ty = if macro_args.send { | ||
| 96 | quote!(impl ::core::future::Future + Send + 'static) | ||
| 97 | } else { | ||
| 98 | quote!(impl ::core::future::Future + 'static) | ||
| 99 | }; | ||
| 93 | 100 | ||
| 94 | let result = quote! { | 101 | let result = quote! { |
| 95 | #visibility fn #name(#args) -> ::embassy::executor::SpawnToken { | 102 | #visibility fn #name(#args) -> ::embassy::executor::SpawnToken<#impl_ty> { |
| 96 | #task_fn | 103 | #task_fn |
| 97 | type F = impl ::core::future::Future + 'static; | 104 | type F = #impl_ty; |
| 98 | static POOL: [::embassy::executor::Task<F>; #pool_size] = [::embassy::executor::Task::new(); #pool_size]; | 105 | static POOL: [::embassy::executor::Task<F>; #pool_size] = [::embassy::executor::Task::new(); #pool_size]; |
| 99 | unsafe { ::embassy::executor::Task::spawn(&POOL, move || task(#arg_names)) } | 106 | unsafe { ::embassy::executor::Task::spawn(&POOL, move || task(#arg_names)) } |
| 100 | } | 107 | } |
| @@ -119,6 +126,9 @@ pub fn interrupt_declare(item: TokenStream) -> TokenStream { | |||
| 119 | let irq = Interrupt::#name; | 126 | let irq = Interrupt::#name; |
| 120 | irq.nr() as u8 | 127 | irq.nr() as u8 |
| 121 | } | 128 | } |
| 129 | unsafe fn steal() -> Self { | ||
| 130 | Self(()) | ||
| 131 | } | ||
| 122 | unsafe fn __handler(&self) -> &'static ::embassy::interrupt::Handler { | 132 | unsafe fn __handler(&self) -> &'static ::embassy::interrupt::Handler { |
| 123 | #[export_name = #name_handler] | 133 | #[export_name = #name_handler] |
| 124 | static HANDLER: ::embassy::interrupt::Handler = ::embassy::interrupt::Handler::new(); | 134 | static HANDLER: ::embassy::interrupt::Handler = ::embassy::interrupt::Handler::new(); |
