#[doc(hidden)]
#[macro_export]
macro_rules! _private_events_unit {
($_t:tt) => {
()
};
}
#[doc(hidden)]
#[macro_export]
macro_rules! _private_define_events {
(
$(#[$enum_attr:meta])*
$vis:vis enum $name:ident in $module:ident {
$($body:tt)*
}
) => {
$crate::_private_define_events! {
@parse_body
ctx { [$(#[$enum_attr])*] [$vis] [$name] [$module] }
phase { kernels }
remaining { $($body)* }
events { }
}
};
(
@parse_body
ctx $ctx:tt
phase $phase:tt
remaining { }
events $events:tt
) => {
$crate::_private_define_events! {
@emit
ctx $ctx
events $events
}
};
(
@parse_body
ctx $ctx:tt
phase $phase:tt
remaining {
$gmod:ident { $($inner:tt)* }
$(, $($outer_rest:tt)*)?
}
events $events:tt
) => {
$crate::_private_define_events! {
@process_group_inner
ctx $ctx
group_module { $gmod }
inner { $($inner)* }
outer { $($($outer_rest)*)? }
events $events
}
};
(
@parse_body
ctx $ctx:tt
phase { groups }
remaining {
$(#[$($vattr:tt)*])*
$variant:ident
$(, $($rest:tt)*)?
}
events $events:tt
) => {
compile_error!(concat!(
"kernel event `",
stringify!($variant),
"` cannot appear after a module group. \
Move all kernel events above the first module group."
));
};
(
@parse_body
ctx $ctx:tt
phase { kernels }
remaining {
$(#[$($vattr:tt)*])*
$variant:ident,
$($rest:tt)*
}
events $events:tt
) => {
$crate::_private_split_reactor_attrs! {
peel: event
state: {
ctx $ctx
after_body { @parse_body ctx $ctx phase { kernels } remaining { $($rest)* } }
module { }
variant { $variant }
events $events
}
pass: { }
found: { }
attrs: { $(#[$($vattr)*])* }
}
};
(
@parse_body
ctx $ctx:tt
phase { kernels }
remaining {
$(#[$($vattr:tt)*])*
$variant:ident
}
events $events:tt
) => {
$crate::_private_split_reactor_attrs! {
peel: event
state: {
ctx $ctx
after_body { @parse_body ctx $ctx phase { kernels } remaining { } }
module { }
variant { $variant }
events $events
}
pass: { }
found: { }
attrs: { $(#[$($vattr)*])* }
}
};
(
@process_group_inner
ctx $ctx:tt
group_module { $gmod:ident }
inner { }
outer { $($outer:tt)* }
events $events:tt
) => {
$crate::_private_define_events! {
@parse_body
ctx $ctx
phase { groups }
remaining { $($outer)* }
events $events
}
};
(
@process_group_inner
ctx $ctx:tt
group_module { $gmod:ident }
inner {
$(#[$($vattr:tt)*])*
$variant:ident,
$($rest:tt)*
}
outer $outer:tt
events $events:tt
) => {
$crate::_private_split_reactor_attrs! {
peel: event
state: {
ctx $ctx
after_body { @process_group_inner ctx $ctx group_module { $gmod } inner { $($rest)* } outer $outer }
module { group $gmod }
variant { $variant }
events $events
}
pass: { }
found: { }
attrs: { $(#[$($vattr)*])* }
}
};
(
@process_group_inner
ctx $ctx:tt
group_module { $gmod:ident }
inner {
$(#[$($vattr:tt)*])*
$variant:ident
}
outer $outer:tt
events $events:tt
) => {
$crate::_private_split_reactor_attrs! {
peel: event
state: {
ctx $ctx
after_body { @process_group_inner ctx $ctx group_module { $gmod } inner { } outer $outer }
module { group $gmod }
variant { $variant }
events $events
}
pass: { }
found: { }
attrs: { $(#[$($vattr)*])* }
}
};
(
@after_split
state: {
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
}
pass: $pass:tt
found: { }
) => {
$crate::_private_define_events! {
@finish_event
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name { }
alias { [ ] }
optional { false }
}
};
(
@after_split
state: {
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
}
pass: $pass:tt
found: { $($eargs:tt)* }
) => {
$crate::_private_define_events! {
@parse_event_args
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name { }
alias { [ ] }
optional { false }
args { $($eargs)* }
}
};
(
@parse_event_args
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
pass $pass:tt
name $_old_name:tt
alias $alias:tt
optional $optional:tt
args { name = $name:literal $(, $($rest:tt)*)? }
) => {
$crate::_private_define_events! {
@parse_event_args
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name { $name }
alias $alias
optional $optional
args { $($($rest)*)? }
}
};
(
@parse_event_args
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
pass $pass:tt
name $name:tt
alias $_old_alias:tt
optional $optional:tt
args { alias = $alias:literal $(, $($rest:tt)*)? }
) => {
$crate::_private_define_events! {
@parse_event_args
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name $name
alias { [ $alias ] }
optional $optional
args { $($($rest)*)? }
}
};
(
@parse_event_args
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
pass $pass:tt
name $name:tt
alias $_old_alias:tt
optional $optional:tt
args { alias = [ $($alias:literal),* $(,)? ] $(, $($rest:tt)*)? }
) => {
$crate::_private_define_events! {
@parse_event_args
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name $name
alias { [ $($alias),* ] }
optional $optional
args { $($($rest)*)? }
}
};
(
@parse_event_args
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
pass $pass:tt
name $name:tt
alias $alias:tt
optional $_old_optional:tt
args { optional $(, $($rest:tt)*)? }
) => {
$crate::_private_define_events! {
@parse_event_args
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name $name
alias $alias
optional { true }
args { $($($rest)*)? }
}
};
(
@parse_event_args
ctx $ctx:tt
after_body $after:tt
module $module:tt
variant $variant:tt
events $events:tt
pass $pass:tt
name $name:tt
alias $alias:tt
optional $optional:tt
args { }
) => {
$crate::_private_define_events! {
@finish_event
ctx $ctx
after_body $after
module $module
variant $variant
events $events
pass $pass
name $name
alias $alias
optional $optional
}
};
(
@finish_event
ctx $ctx:tt
after_body { $($after:tt)* }
module $module:tt
variant { $variant:ident }
events { $($events:tt)* }
pass { $($pass:tt)* }
name $name:tt
alias $alias:tt
optional { $optional:tt }
) => {
$crate::_private_define_events! {
$($after)*
events {
$($events)*
{
variant: $variant,
pass: [$($pass)*],
module: $module,
name: $name,
alias: $alias,
optional: $optional,
}
}
}
};
(
@emit
ctx { [$($eattr:tt)*] [$vis:vis] [$name:ident] [$module:ident] }
events {
$(
{
variant: $variant:ident,
pass: [$($pass:tt)*],
module: $event_module:tt,
name: $event_name:tt,
alias: $event_alias:tt,
optional: $optional:tt,
}
)*
}
) => {
$($eattr)*
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
$vis enum $name {
$(
$($pass)*
$variant,
)*
}
impl $crate::reactor::ReactorEvent for $name {
type Module = $module;
const METADATA: &'static [$crate::reactor::EventMetadata<Self>] = &[
$(
$crate::reactor::EventMetadata {
name: $crate::_private_define_events!(
@event_name $event_name $variant
),
alias: $crate::_private_define_events!(
@event_alias $event_alias
),
module: $crate::_private_define_events!(
@event_module $event_module $module
),
event: Self::$variant,
optional: $optional,
},
)*
];
}
};
(@event_name { } $variant:ident) => {
stringify!($variant)
};
(@event_name { $literal:literal } $variant:ident) => {
$literal
};
(@event_alias { [ $($alias:literal),* $(,)? ] }) => {
&[ $($alias),* ]
};
(@event_module { } $module:ident) => {
None
};
(@event_module { group $gmod:ident } $module:ident) => {
Some($module::$gmod)
};
}