mago_syntax/walker/
mod.rs

1#![allow(unused_variables)]
2
3use crate::ast::Program;
4use crate::ast::ast::*;
5
6/// Macro for generating a walker trait and associated functions for traversing an AST.
7///
8/// For each node type provided to the macro, this trait generates three methods:
9///
10/// - `walk_in_<node>`: Called before walking the children of the node.
11///   Override this to perform actions before traversing the node's children.
12/// - `walk_<node>`: Orchestrates the traversal of the node by calling `walk_in_<node>`,
13///   then walking its children, and finally calling `walk_out_<node>`.
14///   **It is not recommended to override this method directly.**
15/// - `walk_out_<node>`: Called after walking the children of the node.
16///   Override this to perform actions after traversing the node's children.
17///
18/// Additionally, for each node type, a standalone `walk_<node>` function is generated.
19/// This function performs the default traversal behavior and can be used within an
20/// overridden `walk_<node>` method to retain the default traversal logic.
21macro_rules! generate_ast_walker {
22    (
23        using($walker:ident, $context:ident):
24
25        $(
26            $node_type:ty as $var_name:ident => $code:block
27        )*
28    ) => {
29        /// A trait that defines a mutable walker to traverse AST nodes.
30        ///
31        /// Each method can be overridden to customize how a node is entered, walked, and exited.
32        pub trait MutWalker<C>: Sync + Send
33        {
34            $(
35                paste::paste! {
36                    #[inline]
37                    fn [<walk_in_ $var_name>](&mut self, $var_name: &$node_type, context: &mut C) {
38                        // Do nothing by default
39                    }
40
41                    #[inline]
42                    fn [<walk_ $var_name>](&mut self, $var_name: &$node_type, $context: &mut C) {
43                        let $walker = self;
44
45                        $walker.[<walk_in_ $var_name>]($var_name, $context);
46                        $code
47                        $walker.[<walk_out_ $var_name>]($var_name, $context);
48                    }
49
50                    #[inline]
51                    fn [<walk_out_ $var_name>](&mut self, $var_name: &$node_type, context: &mut C) {
52                        // Do nothing by default
53                    }
54                }
55            )*
56        }
57
58        /// A trait that defines a walker to traverse AST nodes.
59        ///
60        /// Each method can be overridden to customize how a node is entered, walked, and exited.
61        pub trait Walker<C>: Sync + Send
62        {
63            $(
64                paste::paste! {
65                    #[inline]
66                    fn [<walk_in_ $var_name>](&self, $var_name: &$node_type, context: &mut C) {
67                        // Do nothing by default
68                    }
69
70                    #[inline]
71                    fn [<walk_ $var_name>](&self, $var_name: &$node_type, $context: &mut C) {
72                        let $walker = self;
73
74                        $walker.[<walk_in_ $var_name>]($var_name, $context);
75                        $code
76                        $walker.[<walk_out_ $var_name>]($var_name, $context);
77                    }
78
79                    #[inline]
80                    fn [<walk_out_ $var_name>](&self, $var_name: &$node_type, context: &mut C) {
81                        // Do nothing by default
82                    }
83                }
84            )*
85        }
86
87        $(
88            paste::paste! {
89                #[inline]
90                pub fn [<walk_ $var_name _mut>]<W, C>($walker: &mut W, $var_name: &$node_type, $context: &mut C)
91                    where
92                        W: MutWalker<C>
93                {
94                    $walker.[<walk_in_ $var_name>]($var_name, $context);
95                    $code
96                    $walker.[<walk_out_ $var_name>]($var_name, $context);
97                }
98
99
100                #[inline]
101                pub fn [<walk_ $var_name>]<W, C>($walker: &W, $var_name: &$node_type, $context: &mut C)
102                    where
103                        W: Walker<C>
104                {
105                    $walker.[<walk_in_ $var_name>]($var_name, $context);
106                    $code
107                    $walker.[<walk_out_ $var_name>]($var_name, $context);
108                }
109            }
110        )*
111    }
112}
113
114generate_ast_walker! {
115    using(walker, context):
116
117    Program as program => {
118        for statement in program.statements.iter() {
119            walker.walk_statement(statement, context);
120        }
121    }
122
123    Statement as statement => {
124        match &statement {
125            Statement::OpeningTag(opening_tag) => walker.walk_opening_tag(opening_tag, context),
126            Statement::ClosingTag(closing_tag) => walker.walk_closing_tag(closing_tag, context),
127            Statement::Inline(inline) => walker.walk_inline(inline, context),
128            Statement::Namespace(namespace) => walker.walk_namespace(namespace, context),
129            Statement::Use(r#use) => walker.walk_use(r#use, context),
130            Statement::Class(class) => walker.walk_class(class, context),
131            Statement::Interface(interface) => walker.walk_interface(interface, context),
132            Statement::Trait(r#trait) => walker.walk_trait(r#trait, context),
133            Statement::Enum(r#enum) => walker.walk_enum(r#enum, context),
134            Statement::Block(block) => walker.walk_block(block, context),
135            Statement::Constant(constant) => walker.walk_constant(constant, context),
136            Statement::Function(function) => walker.walk_function(function, context),
137            Statement::Declare(declare) => walker.walk_declare(declare, context),
138            Statement::Goto(goto) => walker.walk_goto(goto, context),
139            Statement::Label(label) => walker.walk_label(label, context),
140            Statement::Try(r#try) => walker.walk_try(r#try, context),
141            Statement::Foreach(foreach) => walker.walk_foreach(foreach, context),
142            Statement::For(r#for) => walker.walk_for(r#for, context),
143            Statement::While(r#while) => walker.walk_while(r#while, context),
144            Statement::DoWhile(do_while) => walker.walk_do_while(do_while, context),
145            Statement::Continue(r#continue) => walker.walk_continue(r#continue, context),
146            Statement::Break(r#break) => walker.walk_break(r#break, context),
147            Statement::Switch(switch) => walker.walk_switch(switch, context),
148            Statement::If(r#if) => walker.walk_if(r#if, context),
149            Statement::Return(r#return) => walker.walk_return(r#return, context),
150            Statement::Expression(expression) => walker.walk_statement_expression(expression, context),
151            Statement::Echo(echo) => walker.walk_echo(echo, context),
152            Statement::Global(global) => walker.walk_global(global, context),
153            Statement::Static(r#static) => walker.walk_static(r#static, context),
154            Statement::HaltCompiler(halt_compiler) => walker.walk_halt_compiler(halt_compiler, context),
155            Statement::Unset(unset) => walker.walk_unset(unset, context),
156            Statement::Noop(_) => {
157                // Do nothing by default
158            },
159        }
160    }
161
162    OpeningTag as opening_tag => {
163        match opening_tag {
164            OpeningTag::Full(full_opening_tag) => walker.walk_full_opening_tag(full_opening_tag, context),
165            OpeningTag::Short(short_opening_tag) => walker.walk_short_opening_tag(short_opening_tag, context),
166            OpeningTag::Echo(echo_opening_tag) => walker.walk_echo_opening_tag(echo_opening_tag, context),
167        }
168    }
169
170    FullOpeningTag as full_opening_tag => {
171        // Do nothing by default
172    }
173
174    ShortOpeningTag as short_opening_tag => {
175        // Do nothing by default
176    }
177
178    EchoOpeningTag as echo_opening_tag => {
179        // Do nothing by default
180    }
181
182    ClosingTag as closing_tag => {
183        // Do nothing by default
184    }
185
186    Inline as inline => {
187        // Do nothing by default
188    }
189
190    Namespace as namespace => {
191        walker.walk_keyword(&namespace.namespace, context);
192        if let Some(name) = &namespace.name {
193            walker.walk_identifier(name, context);
194        }
195
196        walker.walk_namespace_body(&namespace.body, context);
197    }
198
199    NamespaceBody as namespace_body => {
200        match namespace_body {
201            NamespaceBody::Implicit(namespace_implicit_body) => walker.walk_namespace_implicit_body(namespace_implicit_body, context),
202            NamespaceBody::BraceDelimited(block) => walker.walk_block(block, context),
203        }
204    }
205
206    NamespaceImplicitBody as namespace_implicit_body => {
207        walker.walk_terminator(&namespace_implicit_body.terminator, context);
208
209        for statement in namespace_implicit_body.statements.iter() {
210            walker.walk_statement(statement, context);
211        }
212    }
213
214    Terminator as terminator => {
215        match terminator {
216            Terminator::Semicolon(_) => {
217                // Do nothing by default
218            }
219            Terminator::ClosingTag(closing_tag) => {
220                walker.walk_closing_tag(closing_tag, context);
221            }
222            Terminator::TagPair(closing_tag, opening_tag) => {
223                walker.walk_closing_tag(closing_tag, context);
224                walker.walk_opening_tag(opening_tag, context);
225            }
226        }
227    }
228
229    Use as r#use => {
230        walker.walk_keyword(&r#use.r#use, context);
231
232        walker.walk_use_items(&r#use.items, context);
233
234        walker.walk_terminator(&r#use.terminator, context);
235    }
236
237    UseItems as use_items => {
238        match use_items {
239            UseItems::Sequence(use_item_sequence) => {
240                walker.walk_use_item_sequence(use_item_sequence, context);
241            }
242            UseItems::TypedSequence(typed_use_item_sequence) => {
243                walker.walk_typed_use_item_sequence(typed_use_item_sequence, context);
244            }
245            UseItems::TypedList(typed_use_item_list) => {
246                walker.walk_typed_use_item_list(typed_use_item_list, context);
247            }
248            UseItems::MixedList(mixed_use_item_list) => {
249                walker.walk_mixed_use_item_list(mixed_use_item_list, context);
250            }
251        }
252    }
253
254    UseItemSequence as use_item_sequence => {
255        for use_item in use_item_sequence.items.iter() {
256            walker.walk_use_item(use_item, context);
257        }
258    }
259
260    UseItem as use_item => {
261        walker.walk_identifier(&use_item.name, context);
262
263        if let Some(alias) = &use_item.alias {
264            walker.walk_use_item_alias(alias, context);
265        }
266    }
267
268    UseItemAlias as use_item_alias => {
269        walker.walk_keyword(&use_item_alias.r#as, context);
270        walker.walk_local_identifier(&use_item_alias.identifier, context);
271    }
272
273    TypedUseItemSequence as typed_use_item_sequence => {
274        walker.walk_use_type(&typed_use_item_sequence.r#type, context);
275
276        for use_item in typed_use_item_sequence.items.iter() {
277            walker.walk_use_item(use_item, context);
278        }
279    }
280
281    UseType as use_type => {
282        match &use_type {
283            UseType::Function(keyword) => walker.walk_keyword(keyword, context),
284            UseType::Const(keyword) => walker.walk_keyword(keyword, context),
285        }
286    }
287
288    TypedUseItemList as typed_use_item_list => {
289        walker.walk_use_type(&typed_use_item_list.r#type, context);
290        walker.walk_identifier(&typed_use_item_list.namespace, context);
291
292        for use_item in typed_use_item_list.items.iter() {
293            walker.walk_use_item(use_item, context);
294        }
295    }
296
297    MixedUseItemList as mixed_use_item_list => {
298        walker.walk_identifier(&mixed_use_item_list.namespace, context);
299
300        for maybe_typed_use_item in mixed_use_item_list.items.iter() {
301            walker.walk_maybe_typed_use_item(maybe_typed_use_item, context);
302        }
303    }
304
305    MaybeTypedUseItem as maybe_typed_use_item => {
306        if let Some(use_type) = &maybe_typed_use_item.r#type {
307            walker.walk_use_type(use_type, context);
308        }
309
310        walker.walk_use_item(&maybe_typed_use_item.item, context);
311    }
312
313    AttributeList as attribute_list => {
314        for attribute in attribute_list.attributes.iter() {
315            walker.walk_attribute(attribute, context);
316        }
317    }
318
319    Attribute as attribute => {
320        walker.walk_identifier(&attribute.name, context);
321
322        if let Some(argument_list) = &attribute.argument_list {
323            walker.walk_argument_list(argument_list, context);
324        }
325    }
326
327    ArgumentList as argument_list => {
328        for argument in argument_list.arguments.iter() {
329            walker.walk_argument(argument, context);
330        }
331    }
332
333    Argument as argument => {
334        match &argument {
335            Argument::Positional(positional_argument) => {
336                walker.walk_positional_argument(positional_argument, context);
337            }
338            Argument::Named(named_argument) => {
339                walker.walk_named_argument(named_argument, context);
340            }
341        }
342    }
343
344    PositionalArgument as positional_argument => {
345        walker.walk_expression(&positional_argument.value, context);
346    }
347
348    NamedArgument as named_argument => {
349        walker.walk_local_identifier(&named_argument.name, context);
350        walker.walk_expression(&named_argument.value, context);
351    }
352
353    Modifier as modifier => {
354        walker.walk_keyword(modifier.get_keyword(), context);
355    }
356
357    Extends as extends => {
358        walker.walk_keyword(&extends.extends, context);
359
360        for ty in extends.types.iter() {
361            walker.walk_identifier(ty, context);
362        }
363    }
364
365    Implements as implements => {
366        walker.walk_keyword(&implements.implements, context);
367
368        for ty in implements.types.iter() {
369            walker.walk_identifier(ty, context);
370        }
371    }
372
373    Class as class => {
374        for attribute_list in class.attribute_lists.iter() {
375            walker.walk_attribute_list(attribute_list, context);
376        }
377
378        for modifier in class.modifiers.iter() {
379            walker.walk_modifier(modifier, context);
380        }
381
382        walker.walk_keyword(&class.class, context);
383        walker.walk_local_identifier(&class.name, context);
384        if let Some(extends) = &class.extends {
385            walker.walk_extends(extends, context);
386        }
387
388        if let Some(implements) = &class.implements {
389            walker.walk_implements(implements, context);
390        }
391
392        for class_member in class.members.iter() {
393            walker.walk_class_like_member(class_member, context);
394        }
395    }
396
397    Interface as interface => {
398        for attribute_list in interface.attribute_lists.iter() {
399            walker.walk_attribute_list(attribute_list, context);
400        }
401
402        walker.walk_keyword(&interface.interface, context);
403        walker.walk_local_identifier(&interface.name, context);
404
405        if let Some(extends) = &interface.extends {
406            walker.walk_extends(extends, context);
407        }
408
409        for class_member in interface.members.iter() {
410            walker.walk_class_like_member(class_member, context);
411        }
412    }
413
414    Trait as r#trait => {
415        for attribute_list in r#trait.attribute_lists.iter() {
416            walker.walk_attribute_list(attribute_list, context);
417        }
418
419        walker.walk_keyword(&r#trait.r#trait, context);
420        walker.walk_local_identifier(&r#trait.name, context);
421
422        for class_member in r#trait.members.iter() {
423            walker.walk_class_like_member(class_member, context);
424        }
425    }
426
427    Enum as r#enum => {
428        for attribute_list in r#enum.attribute_lists.iter() {
429            walker.walk_attribute_list(attribute_list, context);
430        }
431
432        walker.walk_keyword(&r#enum.r#enum, context);
433        walker.walk_local_identifier(&r#enum.name, context);
434
435        if let Some(backing_type_hint) = &r#enum.backing_type_hint {
436            walker.walk_enum_backing_type_hint(backing_type_hint, context);
437        }
438
439        if let Some(implements) = &r#enum.implements {
440            walker.walk_implements(implements, context);
441        }
442
443        for class_member in r#enum.members.iter() {
444            walker.walk_class_like_member(class_member, context);
445        }
446    }
447
448    EnumBackingTypeHint as enum_backing_type_hint => {
449        walker.walk_hint(&enum_backing_type_hint.hint, context);
450    }
451
452    ClassLikeMember as class_like_member => {
453        match class_like_member {
454            ClassLikeMember::TraitUse(trait_use) => {
455                walker.walk_trait_use(trait_use, context);
456            }
457            ClassLikeMember::Constant(class_like_constant) => {
458                walker.walk_class_like_constant(class_like_constant, context);
459            }
460            ClassLikeMember::Property(property) => {
461                walker.walk_property(property, context);
462            }
463            ClassLikeMember::EnumCase(enum_case) => {
464                walker.walk_enum_case(enum_case, context);
465            }
466            ClassLikeMember::Method(method) => {
467                walker.walk_method(method, context);
468            }
469        }
470    }
471
472    TraitUse as trait_use => {
473        walker.walk_keyword(&trait_use.r#use, context);
474
475        for trait_name in trait_use.trait_names.iter() {
476            walker.walk_identifier(trait_name, context);
477        }
478
479        walker.walk_trait_use_specification(&trait_use.specification, context);
480    }
481
482    TraitUseSpecification as trait_use_specification => {
483        match trait_use_specification {
484            TraitUseSpecification::Abstract(trait_use_abstract_specification) => {
485                walker.walk_trait_use_abstract_specification(trait_use_abstract_specification, context);
486            }
487            TraitUseSpecification::Concrete(trait_use_concrete_specification) => {
488                walker.walk_trait_use_concrete_specification(trait_use_concrete_specification, context);
489            }
490        }
491    }
492
493    TraitUseAbstractSpecification as trait_use_abstract_specification => {
494        walker.walk_terminator(&trait_use_abstract_specification.0, context);
495    }
496
497    TraitUseConcreteSpecification as trait_use_concrete_specification => {
498        for adaptation in trait_use_concrete_specification.adaptations.iter() {
499            walker.walk_trait_use_adaptation(
500                adaptation,
501
502                context,
503            );
504        }
505    }
506
507    TraitUseAdaptation as trait_use_adaptation => {
508        match trait_use_adaptation {
509            TraitUseAdaptation::Precedence(trait_use_precedence_adaptation) => {
510                walker.walk_trait_use_precedence_adaptation(trait_use_precedence_adaptation, context);
511            },
512            TraitUseAdaptation::Alias(trait_use_alias_adaptation) => {
513                walker.walk_trait_use_alias_adaptation(trait_use_alias_adaptation, context);
514            },
515        }
516    }
517
518    TraitUsePrecedenceAdaptation as trait_use_precedence_adaptation => {
519        walker.walk_trait_use_absolute_method_reference(
520            &trait_use_precedence_adaptation.method_reference,
521
522            context,
523        );
524
525        walker.walk_keyword(&trait_use_precedence_adaptation.insteadof, context);
526
527        for trait_name in trait_use_precedence_adaptation.trait_names.iter() {
528            walker.walk_identifier(trait_name, context);
529        }
530
531        walker.walk_terminator(&trait_use_precedence_adaptation.terminator, context);
532    }
533
534    TraitUseAbsoluteMethodReference as trait_use_absolute_method_reference => {
535        walker.walk_identifier(&trait_use_absolute_method_reference.trait_name, context);
536        walker.walk_local_identifier(&trait_use_absolute_method_reference.method_name, context);
537    }
538
539    TraitUseAliasAdaptation as trait_use_alias_adaptation => {
540        walker.walk_trait_use_method_reference(
541            &trait_use_alias_adaptation.method_reference,
542
543            context,
544        );
545
546        walker.walk_keyword(&trait_use_alias_adaptation.r#as, context);
547
548        if let Some(modifier) = &trait_use_alias_adaptation.visibility {
549            walker.walk_modifier(modifier, context);
550        }
551
552        if let Some(alias) = &trait_use_alias_adaptation.alias {
553            walker.walk_local_identifier(alias, context);
554        }
555
556        walker.walk_terminator(&trait_use_alias_adaptation.terminator, context);
557    }
558
559    TraitUseMethodReference as trait_use_method_reference => {
560        match trait_use_method_reference {
561            TraitUseMethodReference::Identifier(local_identifier) => {
562                walker.walk_local_identifier(local_identifier, context);
563            },
564            TraitUseMethodReference::Absolute(absolute) => {
565                walker.walk_trait_use_absolute_method_reference(absolute, context);
566            },
567        }
568    }
569
570    ClassLikeConstant as class_like_constant => {
571        for attribute_list in class_like_constant.attribute_lists.iter() {
572            walker.walk_attribute_list(attribute_list, context);
573        }
574
575        for modifier in class_like_constant.modifiers.iter() {
576            walker.walk_modifier(modifier, context);
577        }
578
579        walker.walk_keyword(&class_like_constant.r#const, context);
580
581        if let Some(hint) = &class_like_constant.hint {
582            walker.walk_hint(hint, context);
583        }
584
585        for item in class_like_constant.items.iter() {
586            walker.walk_class_like_constant_item(item, context);
587        }
588
589        walker.walk_terminator(&class_like_constant.terminator, context);
590    }
591
592    ClassLikeConstantItem as class_like_constant_item => {
593        walker.walk_local_identifier(&class_like_constant_item.name, context);
594        walker.walk_expression(&class_like_constant_item.value, context);
595    }
596
597    Property as property => {
598        match property {
599            Property::Plain(plain_property) => {
600                walker.walk_plain_property(plain_property, context);
601            }
602            Property::Hooked(hooked_property) => {
603                walker.walk_hooked_property(hooked_property, context);
604            }
605        }
606    }
607
608    PlainProperty as plain_property => {
609        for attribute_list in plain_property.attribute_lists.iter() {
610            walker.walk_attribute_list(attribute_list, context);
611        }
612
613        for modifier in plain_property.modifiers.iter() {
614            walker.walk_modifier(modifier, context);
615        }
616
617        if let Some(var) = &plain_property.var {
618            walker.walk_keyword(var, context);
619        }
620
621        if let Some(hint) = &plain_property.hint {
622            walker.walk_hint(hint, context);
623        }
624
625        for item in plain_property.items.iter() {
626            walker.walk_property_item(item, context);
627        }
628
629        walker.walk_terminator(&plain_property.terminator, context);
630    }
631
632    PropertyItem as property_item => {
633        match property_item {
634            PropertyItem::Abstract(property_abstract_item) => {
635                walker.walk_property_abstract_item(property_abstract_item, context);
636            }
637            PropertyItem::Concrete(property_concrete_item) => {
638                walker.walk_property_concrete_item(property_concrete_item, context);
639            }
640        }
641    }
642
643    PropertyAbstractItem as property_abstract_item => {
644        walker.walk_direct_variable(&property_abstract_item.variable, context);
645    }
646
647    PropertyConcreteItem as property_concrete_item => {
648        walker.walk_direct_variable(&property_concrete_item.variable, context);
649        walker.walk_expression(&property_concrete_item.value, context);
650    }
651
652    HookedProperty as hooked_property => {
653        for attribute_list in hooked_property.attribute_lists.iter() {
654            walker.walk_attribute_list(attribute_list, context);
655        }
656
657        for modifier in hooked_property.modifiers.iter() {
658            walker.walk_modifier(modifier, context);
659        }
660
661        if let Some(var) = &hooked_property.var {
662            walker.walk_keyword(var, context);
663        }
664
665        if let Some(hint) = &hooked_property.hint {
666            walker.walk_hint(hint, context);
667        }
668
669        walker.walk_property_item(&hooked_property.item, context);
670        walker.walk_property_hook_list(&hooked_property.hooks, context);
671    }
672
673    PropertyHookList as property_hook_list => {
674        for hook in property_hook_list.hooks.iter() {
675            walker.walk_property_hook(hook, context);
676        }
677    }
678
679    PropertyHook as property_hook => {
680        for attribute_list in property_hook.attribute_lists.iter() {
681            walker.walk_attribute_list(attribute_list, context);
682        }
683
684        for modifier in property_hook.modifiers.iter() {
685            walker.walk_modifier(modifier, context);
686        }
687
688        walker.walk_local_identifier(&property_hook.name, context);
689        if let Some(parameters) = &property_hook.parameters {
690            walker.walk_function_like_parameter_list(parameters, context);
691        }
692
693        walker.walk_property_hook_body(&property_hook.body, context);
694    }
695
696    PropertyHookBody as property_hook_body => {
697        match property_hook_body {
698            PropertyHookBody::Abstract(property_hook_abstract_body) => {
699                walker.walk_property_hook_abstract_body(property_hook_abstract_body, context);
700            }
701            PropertyHookBody::Concrete(property_hook_concrete_body) => {
702                walker.walk_property_hook_concrete_body(property_hook_concrete_body, context);
703            }
704        }
705    }
706
707    PropertyHookAbstractBody as property_hook_abstract_body => {
708        // Do nothing by default
709    }
710
711    PropertyHookConcreteBody as property_hook_concrete_body => {
712        match property_hook_concrete_body {
713            PropertyHookConcreteBody::Block(block) => {
714                walker.walk_block(block, context);
715            }
716            PropertyHookConcreteBody::Expression(property_hook_concrete_expression_body) => {
717                walker.walk_property_hook_concrete_expression_body(property_hook_concrete_expression_body, context);
718            }
719        }
720    }
721
722    PropertyHookConcreteExpressionBody as property_hook_concrete_expression_body => {
723        walker.walk_expression(&property_hook_concrete_expression_body.expression, context);
724    }
725
726    FunctionLikeParameterList as function_like_parameter_list => {
727        for parameter in function_like_parameter_list.parameters.iter() {
728            walker.walk_function_like_parameter(parameter, context);
729        }
730    }
731
732    FunctionLikeParameter as function_like_parameter => {
733        for attribute_list in function_like_parameter.attribute_lists.iter() {
734            walker.walk_attribute_list(attribute_list, context);
735        }
736
737        for modifier in function_like_parameter.modifiers.iter() {
738            walker.walk_modifier(modifier, context);
739        }
740
741        if let Some(hint) = &function_like_parameter.hint {
742            walker.walk_hint(hint, context);
743        }
744
745        walker.walk_direct_variable(&function_like_parameter.variable, context);
746        if let Some(default_value) = &function_like_parameter.default_value {
747            walker.walk_function_like_parameter_default_value(default_value, context);
748        }
749
750        if let Some(hooks) = &function_like_parameter.hooks {
751            walker.walk_property_hook_list(hooks, context);
752        }
753    }
754
755    FunctionLikeParameterDefaultValue as function_like_parameter_default_value => {
756        walker.walk_expression(&function_like_parameter_default_value.value, context);
757    }
758
759    EnumCase as enum_case => {
760        for attribute_list in enum_case.attribute_lists.iter() {
761            walker.walk_attribute_list(attribute_list, context);
762        }
763
764        walker.walk_keyword(&enum_case.case, context);
765        walker.walk_enum_case_item(&enum_case.item, context);
766        walker.walk_terminator(&enum_case.terminator, context);
767    }
768
769    EnumCaseItem as enum_case_item => {
770        match enum_case_item {
771            EnumCaseItem::Unit(enum_case_unit_item) => {
772                walker.walk_enum_case_unit_item(enum_case_unit_item, context);
773            }
774            EnumCaseItem::Backed(enum_case_backed_item) => {
775                walker.walk_enum_case_backed_item(enum_case_backed_item, context);
776            }
777        }
778    }
779
780    EnumCaseUnitItem as enum_case_unit_item => {
781        walker.walk_local_identifier(&enum_case_unit_item.name, context);
782    }
783
784    EnumCaseBackedItem as enum_case_backed_item => {
785        walker.walk_local_identifier(&enum_case_backed_item.name, context);
786        walker.walk_expression(&enum_case_backed_item.value, context);
787    }
788
789    Method as method => {
790        for attribute_list in method.attribute_lists.iter() {
791            walker.walk_attribute_list(attribute_list, context);
792        }
793
794        for modifier in method.modifiers.iter() {
795            walker.walk_modifier(modifier, context);
796        }
797
798        walker.walk_keyword(&method.function, context);
799        walker.walk_local_identifier(&method.name, context);
800        walker.walk_function_like_parameter_list(&method.parameter_list, context);
801        if let Some(hint) = &method.return_type_hint {
802            walker.walk_function_like_return_type_hint(hint, context);
803        }
804
805        walker.walk_method_body(&method.body, context);
806    }
807
808    MethodBody as method_body => {
809        match method_body {
810            MethodBody::Abstract(method_abstract_body) => {
811                walker.walk_method_abstract_body(method_abstract_body, context);
812            }
813            MethodBody::Concrete(method_concrete_body) => {
814                walker.walk_block(method_concrete_body, context);
815            }
816        }
817    }
818
819    MethodAbstractBody as method_abstract_body => {
820        // Do nothing by default
821    }
822
823    FunctionLikeReturnTypeHint as function_like_return_type_hint => {
824        walker.walk_hint(&function_like_return_type_hint.hint, context);
825    }
826
827    Block as block => {
828        for statement in block.statements.iter() {
829            walker.walk_statement(statement, context);
830        }
831    }
832
833    Constant as constant => {
834        for attribute_list in constant.attribute_lists.iter() {
835            walker.walk_attribute_list(attribute_list, context);
836        }
837
838        walker.walk_keyword(&constant.r#const, context);
839        for item in constant.items.iter() {
840            walker.walk_constant_item(item, context);
841        }
842
843        walker.walk_terminator(&constant.terminator, context);
844    }
845
846    ConstantItem as constant_item => {
847        walker.walk_local_identifier(&constant_item.name, context);
848        walker.walk_expression(&constant_item.value, context);
849    }
850
851    Function as function => {
852        for attribute_list in function.attribute_lists.iter() {
853            walker.walk_attribute_list(attribute_list, context);
854        }
855
856        walker.walk_keyword(&function.function, context);
857        walker.walk_local_identifier(&function.name, context);
858        walker.walk_function_like_parameter_list(&function.parameter_list, context);
859        if let Some(hint) = &function.return_type_hint {
860            walker.walk_function_like_return_type_hint(hint, context);
861        }
862
863        walker.walk_block(&function.body, context);
864    }
865
866    Declare as declare => {
867        walker.walk_keyword(&declare.declare, context);
868        for item in declare.items.iter() {
869            walker.walk_declare_item(item, context);
870        }
871
872        walker.walk_declare_body(&declare.body, context);
873    }
874
875    DeclareItem as declare_item => {
876        walker.walk_local_identifier(&declare_item.name, context);
877        walker.walk_expression(&declare_item.value, context);
878    }
879
880    DeclareBody as declare_body => {
881        match declare_body {
882            DeclareBody::Statement(statement) => {
883                walker.walk_statement(statement, context);
884            }
885            DeclareBody::ColonDelimited(declare_colon_delimited_body) => {
886                walker.walk_declare_colon_delimited_body(declare_colon_delimited_body, context);
887            }
888        }
889    }
890
891    DeclareColonDelimitedBody as declare_colon_delimited_body => {
892        for statement in declare_colon_delimited_body.statements.iter() {
893            walker.walk_statement(statement, context);
894        }
895
896        walker.walk_terminator(&declare_colon_delimited_body.terminator, context);
897    }
898
899    Goto as goto => {
900        walker.walk_keyword(&goto.goto, context);
901        walker.walk_local_identifier(&goto.label, context);
902        walker.walk_terminator(&goto.terminator, context);
903    }
904
905    Label as label => {
906        walker.walk_local_identifier(&label.name, context);
907    }
908
909    Try as r#try => {
910        walker.walk_keyword(&r#try.r#try, context);
911        walker.walk_block(&r#try.block, context);
912        for catch in r#try.catch_clauses.iter() {
913            walker.walk_try_catch_clause(catch, context);
914        }
915
916        if let Some(finally) = &r#try.finally_clause {
917            walker.walk_try_finally_clause(finally, context);
918        }
919    }
920
921    TryCatchClause as try_catch_clause => {
922        walker.walk_keyword(&try_catch_clause.catch, context);
923        walker.walk_hint(&try_catch_clause.hint, context);
924        if let Some(variable) = &try_catch_clause.variable {
925            walker.walk_direct_variable(variable, context);
926        }
927
928        walker.walk_block(&try_catch_clause.block, context);
929    }
930
931    TryFinallyClause as try_finally_clause => {
932        walker.walk_keyword(&try_finally_clause.finally, context);
933        walker.walk_block(&try_finally_clause.block, context);
934    }
935
936    Foreach as foreach => {
937        walker.walk_keyword(&foreach.foreach, context);
938        walker.walk_expression(&foreach.expression, context);
939        walker.walk_keyword(&foreach.r#as, context);
940        walker.walk_foreach_target(&foreach.target, context);
941        walker.walk_foreach_body(&foreach.body, context);
942    }
943
944    ForeachTarget as foreach_target => {
945        match foreach_target {
946            ForeachTarget::Value(foreach_value_target) => {
947                walker.walk_foreach_value_target(foreach_value_target, context);
948            }
949            ForeachTarget::KeyValue(foreach_key_value_target) => {
950                walker.walk_foreach_key_value_target(foreach_key_value_target, context);
951            }
952        }
953    }
954
955    ForeachValueTarget as foreach_value_target => {
956        walker.walk_expression(&foreach_value_target.value, context);
957    }
958
959    ForeachKeyValueTarget as foreach_key_value_target => {
960        walker.walk_expression(&foreach_key_value_target.key, context);
961        walker.walk_expression(&foreach_key_value_target.value, context);
962    }
963
964    ForeachBody as foreach_body => {
965        match foreach_body {
966            ForeachBody::Statement(statement) => {
967                walker.walk_statement(statement, context);
968            }
969            ForeachBody::ColonDelimited(foreach_colon_delimited_body) => {
970                walker.walk_foreach_colon_delimited_body(foreach_colon_delimited_body, context);
971            }
972        }
973    }
974
975    ForeachColonDelimitedBody as foreach_colon_delimited_body => {
976        for statement in foreach_colon_delimited_body.statements.iter() {
977            walker.walk_statement(statement, context);
978        }
979
980        walker.walk_keyword(&foreach_colon_delimited_body.end_foreach, context);
981        walker.walk_terminator(&foreach_colon_delimited_body.terminator, context);
982    }
983
984    For as r#for => {
985        walker.walk_keyword(&r#for.r#for, context);
986
987        for initialization in r#for.initializations.iter() {
988            walker.walk_expression(initialization, context);
989        }
990
991        for condition in r#for.conditions.iter() {
992            walker.walk_expression(condition, context);
993        }
994
995        for increment in r#for.increments.iter() {
996            walker.walk_expression(increment, context);
997        }
998
999        walker.walk_for_body(&r#for.body, context);
1000    }
1001
1002    ForBody as for_body => {
1003        match for_body {
1004            ForBody::Statement(statement) => {
1005                walker.walk_statement(statement, context);
1006            }
1007            ForBody::ColonDelimited(for_colon_delimited_body) => {
1008                walker.walk_for_colon_delimited_body(for_colon_delimited_body, context);
1009            }
1010        }
1011    }
1012
1013    ForColonDelimitedBody as for_colon_delimited_body => {
1014        for statement in for_colon_delimited_body.statements.iter() {
1015            walker.walk_statement(statement, context);
1016        }
1017
1018        walker.walk_keyword(&for_colon_delimited_body.end_for, context);
1019        walker.walk_terminator(&for_colon_delimited_body.terminator, context);
1020    }
1021
1022    While as r#while => {
1023        walker.walk_keyword(&r#while.r#while, context);
1024        walker.walk_expression(&r#while.condition, context);
1025        walker.walk_while_body(&r#while.body, context);
1026    }
1027
1028    WhileBody as while_body => {
1029        match while_body {
1030            WhileBody::Statement(statement) => {
1031                walker.walk_statement(statement, context);
1032            }
1033            WhileBody::ColonDelimited(while_colon_delimited_body) => {
1034                walker.walk_while_colon_delimited_body(while_colon_delimited_body, context);
1035            }
1036        }
1037    }
1038
1039    WhileColonDelimitedBody as while_colon_delimited_body => {
1040        for statement in while_colon_delimited_body.statements.iter() {
1041            walker.walk_statement(statement, context);
1042        }
1043
1044        walker.walk_keyword(&while_colon_delimited_body.end_while, context);
1045        walker.walk_terminator(&while_colon_delimited_body.terminator, context);
1046    }
1047
1048    DoWhile as do_while => {
1049        walker.walk_keyword(&do_while.r#do, context);
1050        walker.walk_statement(&do_while.statement, context);
1051        walker.walk_keyword(&do_while.r#while, context);
1052        walker.walk_expression(&do_while.condition, context);
1053        walker.walk_terminator(&do_while.terminator, context);
1054    }
1055
1056    Continue as r#continue => {
1057        walker.walk_keyword(&r#continue.r#continue, context);
1058        if let Some(level) = &r#continue.level {
1059            walker.walk_expression(level, context);
1060        }
1061
1062        walker.walk_terminator(&r#continue.terminator, context);
1063    }
1064
1065    Break as r#break => {
1066        walker.walk_keyword(&r#break.r#break, context);
1067        if let Some(level) = &r#break.level {
1068            walker.walk_expression(level, context);
1069        }
1070
1071        walker.walk_terminator(&r#break.terminator, context);
1072    }
1073
1074    Switch as switch => {
1075        walker.walk_keyword(&switch.r#switch, context);
1076        walker.walk_expression(&switch.expression, context);
1077        walker.walk_switch_body(&switch.body, context);
1078    }
1079
1080    SwitchBody as switch_body => {
1081        match switch_body {
1082            SwitchBody::BraceDelimited(switch_brace_delimited_body) => {
1083                walker.walk_switch_brace_delimited_body(switch_brace_delimited_body, context);
1084            }
1085            SwitchBody::ColonDelimited(switch_colon_delimited_body) => {
1086                walker.walk_switch_colon_delimited_body(switch_colon_delimited_body, context);
1087            }
1088        }
1089    }
1090
1091    SwitchBraceDelimitedBody as switch_brace_delimited_body => {
1092        if let Some(terminator) = &switch_brace_delimited_body.optional_terminator {
1093            walker.walk_terminator(terminator, context);
1094        }
1095
1096        for case in switch_brace_delimited_body.cases.iter() {
1097            walker.walk_switch_case(case, context);
1098        }
1099    }
1100
1101    SwitchColonDelimitedBody as switch_colon_delimited_body => {
1102        if let Some(terminator) = &switch_colon_delimited_body.optional_terminator {
1103            walker.walk_terminator(terminator, context);
1104        }
1105
1106        for case in switch_colon_delimited_body.cases.iter() {
1107            walker.walk_switch_case(case, context);
1108        }
1109
1110        walker.walk_keyword(&switch_colon_delimited_body.end_switch, context);
1111        walker.walk_terminator(&switch_colon_delimited_body.terminator, context);
1112    }
1113
1114    SwitchCase as switch_case => {
1115        match switch_case {
1116            SwitchCase::Expression(switch_expression_case) => {
1117                walker.walk_switch_expression_case(switch_expression_case, context);
1118            }
1119            SwitchCase::Default(switch_default_case) => {
1120                walker.walk_switch_default_case(switch_default_case, context);
1121            }
1122        }
1123    }
1124
1125    SwitchExpressionCase as switch_expression_case => {
1126        walker.walk_keyword(&switch_expression_case.r#case, context);
1127        walker.walk_expression(&switch_expression_case.expression, context);
1128        walker.walk_switch_case_separator(&switch_expression_case.separator, context);
1129        for statement in switch_expression_case.statements.iter() {
1130            walker.walk_statement(statement, context);
1131        }
1132    }
1133
1134    SwitchDefaultCase as switch_default_case => {
1135        walker.walk_keyword(&switch_default_case.r#default, context);
1136        walker.walk_switch_case_separator(&switch_default_case.separator, context);
1137        for statement in switch_default_case.statements.iter() {
1138            walker.walk_statement(statement, context);
1139        }
1140    }
1141
1142    SwitchCaseSeparator as switch_case_separator => {
1143        // Do nothing by default
1144    }
1145
1146    If as r#if => {
1147        walker.walk_keyword(&r#if.r#if, context);
1148        walker.walk_expression(&r#if.condition, context);
1149        walker.walk_if_body(&r#if.body, context);
1150    }
1151
1152    IfBody as if_body => {
1153        match if_body {
1154            IfBody::Statement(statement) => {
1155                walker.walk_if_statement_body(statement, context);
1156            }
1157            IfBody::ColonDelimited(if_colon_delimited_body) => {
1158                walker.walk_if_colon_delimited_body(if_colon_delimited_body, context);
1159            }
1160        }
1161    }
1162
1163    IfStatementBody as if_statement_body => {
1164        walker.walk_statement(&if_statement_body.statement, context);
1165
1166        for else_if_clause in if_statement_body.else_if_clauses.iter() {
1167            walker.walk_if_statement_body_else_if_clause(else_if_clause, context);
1168        }
1169
1170        if let Some(else_clause) = &if_statement_body.else_clause {
1171            walker.walk_if_statement_body_else_clause(else_clause, context);
1172        }
1173    }
1174
1175    IfStatementBodyElseIfClause as if_statement_body_else_if_clause => {
1176        walker.walk_keyword(&if_statement_body_else_if_clause.r#elseif, context);
1177        walker.walk_expression(&if_statement_body_else_if_clause.condition, context);
1178        walker.walk_statement(&if_statement_body_else_if_clause.statement, context);
1179    }
1180
1181    IfStatementBodyElseClause as if_statement_body_else_clause => {
1182        walker.walk_keyword(&if_statement_body_else_clause.r#else, context);
1183        walker.walk_statement(&if_statement_body_else_clause.statement, context);
1184    }
1185
1186    IfColonDelimitedBody as if_colon_delimited_body => {
1187        for statement in if_colon_delimited_body.statements.iter() {
1188            walker.walk_statement(statement, context);
1189        }
1190
1191        for else_if_clause in if_colon_delimited_body.else_if_clauses.iter() {
1192            walker.walk_if_colon_delimited_body_else_if_clause(else_if_clause, context);
1193        }
1194
1195        if let Some(else_clause) = &if_colon_delimited_body.else_clause {
1196            walker.walk_if_colon_delimited_body_else_clause(else_clause, context);
1197        }
1198
1199        walker.walk_keyword(&if_colon_delimited_body.endif, context);
1200        walker.walk_terminator(&if_colon_delimited_body.terminator, context);
1201    }
1202
1203    IfColonDelimitedBodyElseIfClause as if_colon_delimited_body_else_if_clause => {
1204        walker.walk_keyword(&if_colon_delimited_body_else_if_clause.r#elseif, context);
1205        walker.walk_expression(&if_colon_delimited_body_else_if_clause.condition, context);
1206        for statement in if_colon_delimited_body_else_if_clause.statements.iter() {
1207            walker.walk_statement(statement, context);
1208        }
1209    }
1210
1211    IfColonDelimitedBodyElseClause as if_colon_delimited_body_else_clause => {
1212        walker.walk_keyword(&if_colon_delimited_body_else_clause.r#else, context);
1213        for statement in if_colon_delimited_body_else_clause.statements.iter() {
1214            walker.walk_statement(statement, context);
1215        }
1216    }
1217
1218    Return as r#return => {
1219        walker.walk_keyword(&r#return.r#return, context);
1220        if let Some(expression) = &r#return.value {
1221            walker.walk_expression(expression, context);
1222        }
1223
1224        walker.walk_terminator(&r#return.terminator, context);
1225    }
1226
1227    ExpressionStatement as statement_expression => {
1228        walker.walk_expression(&statement_expression.expression, context);
1229        walker.walk_terminator(&statement_expression.terminator, context);
1230    }
1231
1232    Echo as echo => {
1233        walker.walk_keyword(&echo.echo, context);
1234        for expression in echo.values.iter() {
1235            walker.walk_expression(expression, context);
1236        }
1237
1238        walker.walk_terminator(&echo.terminator, context);
1239    }
1240
1241    Global as global => {
1242        walker.walk_keyword(&global.global, context);
1243        for variable in global.variables.iter() {
1244            walker.walk_variable(variable, context);
1245        }
1246
1247        walker.walk_terminator(&global.terminator, context);
1248    }
1249
1250    Static as r#static => {
1251        walker.walk_keyword(&r#static.r#static, context);
1252        for item in r#static.items.iter() {
1253            walker.walk_static_item(item, context);
1254        }
1255
1256        walker.walk_terminator(&r#static.terminator, context);
1257    }
1258
1259    StaticItem as static_item => {
1260        match static_item {
1261            StaticItem::Abstract(static_abstract_item) => {
1262                walker.walk_static_abstract_item(static_abstract_item, context);
1263            }
1264            StaticItem::Concrete(static_concrete_item) => {
1265                walker.walk_static_concrete_item(static_concrete_item, context);
1266            }
1267        }
1268    }
1269
1270    StaticAbstractItem as static_abstract_item => {
1271        walker.walk_direct_variable(&static_abstract_item.variable, context);
1272    }
1273
1274    StaticConcreteItem as static_concrete_item => {
1275        walker.walk_direct_variable(&static_concrete_item.variable, context);
1276        walker.walk_expression(&static_concrete_item.value, context);
1277    }
1278
1279    HaltCompiler as halt_compiler => {
1280        walker.walk_keyword(&halt_compiler.halt_compiler, context);
1281    }
1282
1283    Unset as unset => {
1284        walker.walk_keyword(&unset.unset, context);
1285        for value in unset.values.iter() {
1286            walker.walk_expression(value, context);
1287        }
1288
1289        walker.walk_terminator(&unset.terminator, context);
1290    }
1291
1292    Expression as expression => {
1293        match &expression {
1294            Expression::Parenthesized(parenthesized) => walker.walk_parenthesized(parenthesized, context),
1295            Expression::Binary(expr) => walker.walk_binary(expr, context),
1296            Expression::UnaryPrefix(operation) => walker.walk_unary_prefix(operation, context),
1297            Expression::UnaryPostfix(operation) => walker.walk_unary_postfix(operation, context),
1298            Expression::Literal(literal) => walker.walk_literal_expression(literal, context),
1299            Expression::CompositeString(string) => walker.walk_composite_string(string, context),
1300            Expression::Assignment(assignment) => {
1301                walker.walk_assignment(assignment, context)
1302            }
1303            Expression::Conditional(conditional) => {
1304                walker.walk_conditional(conditional, context)
1305            }
1306            Expression::Array(array) => walker.walk_array(array, context),
1307            Expression::LegacyArray(legacy_array) => walker.walk_legacy_array(legacy_array, context),
1308            Expression::List(list) => walker.walk_list(list, context),
1309            Expression::ArrayAccess(array_access) => walker.walk_array_access(array_access, context),
1310            Expression::ArrayAppend(array_append) => walker.walk_array_append(array_append, context),
1311            Expression::AnonymousClass(anonymous_class) => {
1312                walker.walk_anonymous_class(anonymous_class, context)
1313            }
1314            Expression::Closure(closure) => walker.walk_closure(closure, context),
1315            Expression::ArrowFunction(arrow_function) => walker.walk_arrow_function(arrow_function, context),
1316            Expression::Variable(variable) => walker.walk_variable(variable, context),
1317            Expression::Identifier(identifier) => walker.walk_identifier(identifier, context),
1318            Expression::Match(r#match) => walker.walk_match(r#match, context),
1319            Expression::Yield(r#yield) => walker.walk_yield(r#yield, context),
1320            Expression::Construct(construct) => walker.walk_construct(construct, context),
1321            Expression::Throw(throw) => walker.walk_throw(throw, context),
1322            Expression::Clone(clone) => walker.walk_clone(clone, context),
1323            Expression::Call(call) => walker.walk_call(call, context),
1324            Expression::Access(access) => walker.walk_access(access, context),
1325            Expression::ConstantAccess(expr) => walker.walk_constant_access(expr, context),
1326            Expression::ClosureCreation(closure_creation) => {
1327                walker.walk_closure_creation(closure_creation, context)
1328            }
1329            Expression::Parent(keyword) => walker.walk_parent_keyword(keyword, context),
1330            Expression::Static(keyword) => walker.walk_static_keyword(keyword, context),
1331            Expression::Self_(keyword) => walker.walk_self_keyword(keyword, context),
1332            Expression::Instantiation(instantiation) => walker.walk_instantiation(instantiation, context),
1333            Expression::MagicConstant(magic_constant) => walker.walk_magic_constant(magic_constant, context),
1334            Expression::Pipe(pipe) => walker.walk_pipe(pipe, context),
1335        }
1336    }
1337
1338    Binary as binary => {
1339        walker.walk_expression(&binary.lhs, context);
1340        walker.walk_binary_operator(&binary.operator, context);
1341        walker.walk_expression(&binary.rhs, context);
1342    }
1343
1344    BinaryOperator as binary_operator => {
1345        match binary_operator {
1346            BinaryOperator::Instanceof(keyword)
1347            | BinaryOperator::LowAnd(keyword)
1348            | BinaryOperator::LowOr(keyword)
1349            | BinaryOperator::LowXor(keyword) => {
1350                walker.walk_keyword(keyword, context);
1351            }
1352            _ => {}
1353        }
1354    }
1355
1356    UnaryPrefix as unary_prefix => {
1357        walker.walk_unary_prefix_operator(&unary_prefix.operator, context);
1358        walker.walk_expression(&unary_prefix.operand, context);
1359    }
1360
1361    UnaryPrefixOperator as unary_prefix_operator => {
1362        // Do nothing
1363    }
1364
1365    UnaryPostfix as unary_postfix => {
1366        walker.walk_expression(&unary_postfix.operand, context);
1367        walker.walk_unary_postfix_operator(&unary_postfix.operator, context);
1368    }
1369
1370    UnaryPostfixOperator as unary_postfix_operator => {
1371        // Do nothing
1372    }
1373
1374    Parenthesized as parenthesized => {
1375        walker.walk_expression(&parenthesized.expression, context)
1376    }
1377
1378    Literal as literal_expression => {
1379        match literal_expression {
1380            Literal::String(string) => walker.walk_literal_string(string, context),
1381            Literal::Integer(integer) => walker.walk_literal_integer(integer, context),
1382            Literal::Float(float) => walker.walk_literal_float(float, context),
1383            Literal::True(keyword) => walker.walk_true_keyword(keyword, context),
1384            Literal::False(keyword) => walker.walk_false_keyword(keyword, context),
1385            Literal::Null(keyword) => walker.walk_null_keyword(keyword, context),
1386        }
1387    }
1388
1389    LiteralString as literal_string => {
1390        // Do nothing by default
1391    }
1392
1393    LiteralInteger as literal_integer => {
1394        // Do nothing by default
1395    }
1396
1397    LiteralFloat as literal_float => {
1398        // Do nothing by default
1399    }
1400
1401    Keyword as true_keyword => {
1402        // Do nothing by default
1403    }
1404
1405    Keyword as false_keyword => {
1406        // Do nothing by default
1407    }
1408
1409    Keyword as null_keyword => {
1410        // Do nothing by default
1411    }
1412
1413    CompositeString as composite_string => {
1414        match composite_string {
1415            CompositeString::ShellExecute(str) => walker.walk_shell_execute_string(str, context),
1416            CompositeString::Interpolated(str) => walker.walk_interpolated_string(str, context),
1417            CompositeString::Document(str) => walker.walk_document_string(str, context),
1418        }
1419    }
1420
1421    ShellExecuteString as shell_execute_string => {
1422        for part in shell_execute_string.parts.iter() {
1423            walker.walk_string_part(part, context);
1424        }
1425    }
1426
1427    InterpolatedString as interpolated_string => {
1428        for part in interpolated_string.parts.iter() {
1429            walker.walk_string_part(part, context);
1430        }
1431    }
1432
1433    DocumentString as document_string => {
1434        for part in document_string.parts.iter() {
1435            walker.walk_string_part(part, context);
1436        }
1437    }
1438
1439    StringPart as string_part => {
1440        match string_part {
1441            StringPart::Literal(literal) => walker.walk_literal_string_part(literal, context),
1442            StringPart::Expression(expression) => walker.walk_expression(expression, context),
1443            StringPart::BracedExpression(braced_expression_string_part) => {
1444                walker.walk_braced_expression_string_part(braced_expression_string_part, context)
1445            }
1446        };
1447    }
1448
1449    LiteralStringPart as literal_string_part => {
1450        // Do nothing
1451    }
1452
1453    BracedExpressionStringPart as braced_expression_string_part => {
1454        walker.walk_expression(&braced_expression_string_part.expression, context);
1455    }
1456
1457    Assignment as assignment => {
1458        walker.walk_expression(&assignment.lhs, context);
1459        walker.walk_assignment_operator(&assignment.operator, context);
1460        walker.walk_expression(&assignment.rhs, context);
1461    }
1462
1463    AssignmentOperator as assignment_operator => {
1464        // Do nothing
1465    }
1466
1467    Conditional as conditional => {
1468        walker.walk_expression(&conditional.condition, context);
1469        if let Some(then) = &conditional.then {
1470            walker.walk_expression(then, context);
1471        }
1472
1473        walker.walk_expression(&conditional.r#else, context);
1474    }
1475
1476    Array as array => {
1477        for element in array.elements.iter() {
1478            walker.walk_array_element(element, context);
1479        }
1480    }
1481
1482    ArrayElement as array_element => {
1483        match array_element {
1484            ArrayElement::KeyValue(key_value_array_element) => {
1485                walker.walk_key_value_array_element(key_value_array_element, context);
1486            }
1487            ArrayElement::Value(value_array_element) => {
1488                walker.walk_value_array_element(value_array_element, context);
1489            }
1490            ArrayElement::Variadic(variadic_array_element) => {
1491                walker.walk_variadic_array_element(variadic_array_element, context);
1492            }
1493            ArrayElement::Missing(missing_array_element) => {
1494                walker.walk_missing_array_element(missing_array_element, context);
1495            }
1496        }
1497    }
1498
1499    KeyValueArrayElement as key_value_array_element => {
1500        walker.walk_expression(&key_value_array_element.key, context);
1501        walker.walk_expression(&key_value_array_element.value, context);
1502    }
1503
1504    ValueArrayElement as value_array_element => {
1505        walker.walk_expression(&value_array_element.value, context);
1506    }
1507
1508    VariadicArrayElement as variadic_array_element => {
1509        walker.walk_expression(&variadic_array_element.value, context);
1510    }
1511
1512    MissingArrayElement as missing_array_element => {
1513        // Do nothing
1514    }
1515
1516    LegacyArray as legacy_array => {
1517        walker.walk_keyword(&legacy_array.array, context);
1518        for element in legacy_array.elements.iter() {
1519            walker.walk_array_element(element, context);
1520        }
1521    }
1522
1523    List as list => {
1524        walker.walk_keyword(&list.list, context);
1525
1526        for element in list.elements.iter() {
1527            walker.walk_array_element(element, context);
1528        }
1529    }
1530
1531    ArrayAccess as array_access => {
1532        walker.walk_expression(&array_access.array, context);
1533        walker.walk_expression(&array_access.index, context);
1534    }
1535
1536    ArrayAppend as array_append => {
1537        walker.walk_expression(&array_append.array, context);
1538    }
1539
1540    AnonymousClass as anonymous_class => {
1541        for attribute_list in anonymous_class.attribute_lists.iter() {
1542            walker.walk_attribute_list(attribute_list, context);
1543        }
1544
1545        for modifier in anonymous_class.modifiers.iter() {
1546            walker.walk_modifier(modifier, context);
1547        }
1548
1549        walker.walk_keyword(&anonymous_class.new, context);
1550        walker.walk_keyword(&anonymous_class.class, context);
1551        if let Some(argument_list) = &anonymous_class.argument_list {
1552            walker.walk_argument_list(argument_list, context);
1553        }
1554
1555        if let Some(extends) = &anonymous_class.extends {
1556            walker.walk_extends(extends, context);
1557        }
1558
1559        if let Some(implements) = &anonymous_class.implements {
1560            walker.walk_implements(implements, context);
1561        }
1562
1563        for class_member in anonymous_class.members.iter() {
1564            walker.walk_class_like_member(class_member, context);
1565        }
1566    }
1567
1568    Closure as closure => {
1569        for attribute_list in closure.attribute_lists.iter() {
1570                walker.walk_attribute_list(attribute_list, context);
1571            }
1572
1573        if let Some(keyword) = &closure.r#static {
1574            walker.walk_keyword(keyword, context);
1575        }
1576
1577        walker.walk_keyword(&closure.function, context);
1578        walker.walk_function_like_parameter_list(&closure.parameter_list, context);
1579        if let Some(use_clause) = &closure.use_clause {
1580            walker.walk_closure_use_clause(use_clause, context);
1581        }
1582
1583        if let Some(return_type_hint) = &closure.return_type_hint {
1584            walker.walk_function_like_return_type_hint(return_type_hint, context);
1585        }
1586
1587        walker.walk_block(&closure.body, context);
1588    }
1589
1590    ClosureUseClause as closure_use_clause => {
1591        for variable in closure_use_clause.variables.iter() {
1592            walker.walk_closure_use_clause_variable(variable, context);
1593        }
1594    }
1595
1596    ClosureUseClauseVariable as closure_use_clause_variable => {
1597        walker.walk_direct_variable(&closure_use_clause_variable.variable, context);
1598    }
1599
1600    ArrowFunction as arrow_function => {
1601        for attribute_list in arrow_function.attribute_lists.iter() {
1602            walker.walk_attribute_list(attribute_list, context);
1603        }
1604
1605        if let Some(keyword) = &arrow_function.r#static {
1606            walker.walk_keyword(keyword, context);
1607        }
1608
1609        walker.walk_keyword(&arrow_function.r#fn, context);
1610        walker.walk_function_like_parameter_list(&arrow_function.parameter_list, context);
1611
1612        if let Some(return_type_hint) = &arrow_function.return_type_hint {
1613            walker.walk_function_like_return_type_hint(return_type_hint, context);
1614        }
1615
1616        walker.walk_expression(&arrow_function.expression, context);
1617    }
1618
1619    Variable as variable => {
1620        match variable {
1621            Variable::Direct(direct_variable) => {
1622                walker.walk_direct_variable(direct_variable, context);
1623            }
1624            Variable::Indirect(indirect_variable) => {
1625                walker.walk_indirect_variable(indirect_variable, context);
1626            }
1627            Variable::Nested(nested_variable) => {
1628                walker.walk_nested_variable(nested_variable, context);
1629            }
1630        }
1631    }
1632
1633    DirectVariable as direct_variable => {
1634        // Do nothing by default
1635    }
1636
1637    IndirectVariable as indirect_variable => {
1638        walker.walk_expression(&indirect_variable.expression, context);
1639    }
1640
1641    NestedVariable as nested_variable => {
1642        walker.walk_variable(nested_variable.variable.as_ref(), context);
1643    }
1644
1645    Identifier as identifier => {
1646        match identifier {
1647            Identifier::Local(local_identifier) => walker.walk_local_identifier(local_identifier, context),
1648            Identifier::Qualified(qualified_identifier) => walker.walk_qualified_identifier(qualified_identifier, context),
1649            Identifier::FullyQualified(fully_qualified_identifier) => walker.walk_fully_qualified_identifier(fully_qualified_identifier, context),
1650        };
1651    }
1652
1653    LocalIdentifier as local_identifier => {
1654        // Do nothing by default
1655    }
1656
1657    QualifiedIdentifier as qualified_identifier => {
1658        // Do nothing by default
1659    }
1660
1661    FullyQualifiedIdentifier as fully_qualified_identifier => {
1662        // Do nothing by default
1663    }
1664
1665    Match as r#match => {
1666        walker.walk_keyword(&r#match.r#match, context);
1667        walker.walk_expression(&r#match.expression, context);
1668        for arm in r#match.arms.iter() {
1669            walker.walk_match_arm(arm, context);
1670        }
1671    }
1672
1673    MatchArm as match_arm => {
1674        match match_arm {
1675            MatchArm::Expression(expression_match_arm) => {
1676                walker.walk_match_expression_arm(expression_match_arm, context);
1677            }
1678            MatchArm::Default(default_match_arm) => {
1679                walker.walk_match_default_arm(default_match_arm, context);
1680            }
1681        }
1682    }
1683
1684    MatchExpressionArm as match_expression_arm => {
1685        for condition in match_expression_arm.conditions.iter() {
1686            walker.walk_expression(condition, context);
1687        }
1688
1689        walker.walk_expression(&match_expression_arm.expression, context);
1690    }
1691
1692    MatchDefaultArm as match_default_arm => {
1693        walker.walk_keyword(&match_default_arm.r#default, context);
1694        walker.walk_expression(&match_default_arm.expression, context);
1695    }
1696
1697    Yield as r#yield => {
1698        match r#yield {
1699            Yield::Value(yield_value) => {
1700                walker.walk_yield_value(yield_value, context);
1701            }
1702            Yield::Pair(yield_pair) => {
1703                walker.walk_yield_pair(yield_pair, context);
1704            }
1705            Yield::From(yield_from) => {
1706                walker.walk_yield_from(yield_from, context);
1707            }
1708        }
1709    }
1710
1711    YieldValue as yield_value => {
1712        walker.walk_keyword(&yield_value.r#yield, context);
1713
1714        if let Some(value) = &yield_value.value {
1715            walker.walk_expression(value, context);
1716        }
1717    }
1718
1719    YieldPair as yield_pair => {
1720        walker.walk_keyword(&yield_pair.r#yield, context);
1721        walker.walk_expression(&yield_pair.key, context);
1722        walker.walk_expression(&yield_pair.value, context);
1723    }
1724
1725    YieldFrom as yield_from => {
1726        walker.walk_keyword(&yield_from.r#yield, context);
1727        walker.walk_keyword(&yield_from.from, context);
1728        walker.walk_expression(&yield_from.iterator, context);
1729    }
1730
1731    Construct as construct => {
1732        match construct {
1733            Construct::Isset(isset_construct) => {
1734                walker.walk_isset_construct(isset_construct, context);
1735            }
1736            Construct::Empty(empty_construct) => {
1737                walker.walk_empty_construct(empty_construct, context);
1738            }
1739            Construct::Eval(eval_construct) => {
1740                walker.walk_eval_construct(eval_construct, context);
1741            }
1742            Construct::Include(include_construct) => {
1743                walker.walk_include_construct(include_construct, context);
1744            }
1745            Construct::IncludeOnce(include_once_construct) => {
1746                walker.walk_include_once_construct(include_once_construct, context);
1747            }
1748            Construct::Require(require_construct) => {
1749                walker.walk_require_construct(require_construct, context);
1750            }
1751            Construct::RequireOnce(require_once_construct) => {
1752                walker.walk_require_once_construct(require_once_construct, context);
1753            }
1754            Construct::Print(print_construct) => {
1755                walker.walk_print_construct(print_construct, context);
1756            }
1757            Construct::Exit(exit_construct) => {
1758                walker.walk_exit_construct(exit_construct, context);
1759            }
1760            Construct::Die(die_construct) => {
1761                walker.walk_die_construct(die_construct, context);
1762            }
1763        }
1764    }
1765
1766    IssetConstruct as isset_construct => {
1767        walker.walk_keyword(&isset_construct.isset, context);
1768        for value in isset_construct.values.iter() {
1769            walker.walk_expression(value, context);
1770        }
1771    }
1772
1773    EmptyConstruct as empty_construct => {
1774        walker.walk_keyword(&empty_construct.empty, context);
1775        walker.walk_expression(&empty_construct.value, context);
1776    }
1777
1778    EvalConstruct as eval_construct => {
1779        walker.walk_keyword(&eval_construct.eval, context);
1780        walker.walk_expression(&eval_construct.value, context);
1781    }
1782
1783    IncludeConstruct as include_construct => {
1784        walker.walk_keyword(&include_construct.include, context);
1785        walker.walk_expression(&include_construct.value, context);
1786    }
1787
1788    IncludeOnceConstruct as include_once_construct => {
1789        walker.walk_keyword(&include_once_construct.include_once, context);
1790        walker.walk_expression(&include_once_construct.value, context);
1791    }
1792
1793    RequireConstruct as require_construct => {
1794        walker.walk_keyword(&require_construct.require, context);
1795        walker.walk_expression(&require_construct.value, context);
1796    }
1797
1798    RequireOnceConstruct as require_once_construct => {
1799        walker.walk_keyword(&require_once_construct.require_once, context);
1800        walker.walk_expression(&require_once_construct.value, context);
1801    }
1802
1803    PrintConstruct as print_construct => {
1804        walker.walk_keyword(&print_construct.print, context);
1805        walker.walk_expression(&print_construct.value, context);
1806    }
1807
1808    ExitConstruct as exit_construct => {
1809        walker.walk_keyword(&exit_construct.exit, context);
1810        if let Some(arguments) = &exit_construct.arguments {
1811            walker.walk_argument_list(arguments, context);
1812        }
1813    }
1814
1815    DieConstruct as die_construct => {
1816        walker.walk_keyword(&die_construct.die, context);
1817        if let Some(arguments) = &die_construct.arguments {
1818            walker.walk_argument_list(arguments, context);
1819        }
1820    }
1821
1822    Throw as r#throw => {
1823        walker.walk_keyword(&r#throw.r#throw, context);
1824        walker.walk_expression(&r#throw.exception, context);
1825    }
1826
1827    Clone as clone => {
1828        walker.walk_keyword(&clone.clone, context);
1829        walker.walk_expression(&clone.object, context);
1830    }
1831
1832    Call as call => {
1833        match call {
1834            Call::Function(function_call) => {
1835                walker.walk_function_call(function_call, context);
1836            }
1837            Call::Method(method_call) => {
1838                walker.walk_method_call(method_call, context);
1839            }
1840            Call::NullSafeMethod(null_safe_method_call) => {
1841                walker.walk_null_safe_method_call(null_safe_method_call, context);
1842            }
1843            Call::StaticMethod(static_method_call) => {
1844                walker.walk_static_method_call(static_method_call, context);
1845            }
1846        }
1847    }
1848
1849    FunctionCall as function_call => {
1850        walker.walk_expression(&function_call.function, context);
1851        walker.walk_argument_list(&function_call.argument_list, context);
1852    }
1853
1854    MethodCall as method_call => {
1855        walker.walk_expression(&method_call.object, context);
1856        walker.walk_class_like_member_selector(&method_call.method, context);
1857        walker.walk_argument_list(&method_call.argument_list, context);
1858    }
1859
1860    NullSafeMethodCall as null_safe_method_call => {
1861        walker.walk_expression(&null_safe_method_call.object, context);
1862        walker.walk_class_like_member_selector(&null_safe_method_call.method, context);
1863        walker.walk_argument_list(&null_safe_method_call.argument_list, context);
1864    }
1865
1866    StaticMethodCall as static_method_call => {
1867        walker.walk_expression(&static_method_call.class, context);
1868        walker.walk_class_like_member_selector(&static_method_call.method, context);
1869        walker.walk_argument_list(&static_method_call.argument_list, context);
1870    }
1871
1872    ClassLikeMemberSelector as class_like_member_selector => {
1873        match class_like_member_selector {
1874            ClassLikeMemberSelector::Identifier(local_identifier) => {
1875                walker.walk_local_identifier(local_identifier, context);
1876            }
1877            ClassLikeMemberSelector::Variable(variable) => {
1878                walker.walk_variable(variable, context);
1879            }
1880            ClassLikeMemberSelector::Expression(class_like_member_expression_selector) => {
1881                walker.walk_class_like_member_expression_selector(
1882                    class_like_member_expression_selector,
1883
1884                    context,
1885                );
1886            }
1887        }
1888    }
1889
1890    ClassLikeMemberExpressionSelector as class_like_member_expression_selector => {
1891        walker.walk_expression(&class_like_member_expression_selector.expression, context);
1892    }
1893
1894    ConstantAccess as constant_access => {
1895        walker.walk_identifier(&constant_access.name, context);
1896    }
1897
1898    Access as access => {
1899        match access {
1900            Access::Property(property_access) => {
1901                walker.walk_property_access(property_access, context);
1902            }
1903            Access::NullSafeProperty(null_safe_property_access) => {
1904                walker.walk_null_safe_property_access(null_safe_property_access, context);
1905            }
1906            Access::StaticProperty(static_property_access) => {
1907                walker.walk_static_property_access(static_property_access, context);
1908            }
1909            Access::ClassConstant(class_constant_access) => {
1910                walker.walk_class_constant_access(class_constant_access, context);
1911            }
1912        }
1913    }
1914
1915    PropertyAccess as property_access => {
1916        walker.walk_expression(&property_access.object, context);
1917        walker.walk_class_like_member_selector(&property_access.property, context);
1918    }
1919
1920    NullSafePropertyAccess as null_safe_property_access => {
1921        walker.walk_expression(&null_safe_property_access.object, context);
1922        walker.walk_class_like_member_selector(&null_safe_property_access.property, context);
1923    }
1924
1925    StaticPropertyAccess as static_property_access => {
1926        walker.walk_expression(&static_property_access.class, context);
1927        walker.walk_variable(&static_property_access.property, context);
1928    }
1929
1930    ClassConstantAccess as class_constant_access => {
1931        walker.walk_expression(&class_constant_access.class, context);
1932        walker.walk_class_like_constant_selector(&class_constant_access.constant, context);
1933    }
1934
1935    ClassLikeConstantSelector as class_like_constant_selector => {
1936        match class_like_constant_selector {
1937            ClassLikeConstantSelector::Identifier(local_identifier) => {
1938                walker.walk_local_identifier(local_identifier, context);
1939            }
1940            ClassLikeConstantSelector::Expression(class_like_constant_expression_selector) => {
1941                walker.walk_class_like_member_expression_selector(
1942                    class_like_constant_expression_selector,
1943
1944                    context,
1945                );
1946            }
1947        }
1948    }
1949
1950    ClosureCreation as closure_creation => {
1951        match closure_creation {
1952            ClosureCreation::Function(function_closure_creation) => {
1953                walker.walk_function_closure_creation(function_closure_creation, context);
1954            }
1955            ClosureCreation::Method(method_closure_creation) => {
1956                walker.walk_method_closure_creation(method_closure_creation, context);
1957            }
1958            ClosureCreation::StaticMethod(static_method_closure_creation) => {
1959                walker.walk_static_method_closure_creation(static_method_closure_creation, context);
1960            }
1961        }
1962    }
1963
1964    FunctionClosureCreation as function_closure_creation => {
1965        walker.walk_expression(&function_closure_creation.function, context);
1966    }
1967
1968    MethodClosureCreation as method_closure_creation => {
1969        walker.walk_expression(&method_closure_creation.object, context);
1970        walker.walk_class_like_member_selector(&method_closure_creation.method, context);
1971    }
1972
1973    StaticMethodClosureCreation as static_method_closure_creation => {
1974        walker.walk_expression(&static_method_closure_creation.class, context);
1975        walker.walk_class_like_member_selector(&static_method_closure_creation.method, context);
1976    }
1977
1978    Keyword as parent_keyword => {
1979        // Do nothing by default
1980    }
1981
1982    Keyword as static_keyword => {
1983        // Do nothing by default
1984    }
1985
1986    Keyword as self_keyword => {
1987        // Do nothing by default
1988    }
1989
1990    Instantiation as instantiation => {
1991        walker.walk_keyword(&instantiation.new, context);
1992        walker.walk_expression(&instantiation.class, context);
1993        if let Some(argument_list) = &instantiation.argument_list {
1994            walker.walk_argument_list(argument_list, context);
1995        }
1996    }
1997
1998    MagicConstant as magic_constant => {
1999        walker.walk_local_identifier(magic_constant.value(), context);
2000    }
2001
2002    Pipe as pipe => {
2003        walker.walk_expression(&pipe.input, context);
2004        walker.walk_expression(&pipe.callable, context);
2005    }
2006
2007    Hint as hint => {
2008        match hint {
2009            Hint::Identifier(identifier) => {
2010                walker.walk_identifier(identifier, context);
2011            }
2012            Hint::Parenthesized(parenthesized_hint) => {
2013                walker.walk_parenthesized_hint(parenthesized_hint, context);
2014            }
2015            Hint::Nullable(nullable_hint) => {
2016                walker.walk_nullable_hint(nullable_hint, context);
2017            }
2018            Hint::Union(union_hint) => {
2019                walker.walk_union_hint(union_hint, context);
2020            }
2021            Hint::Intersection(intersection_hint) => {
2022                walker.walk_intersection_hint(intersection_hint, context);
2023            }
2024            Hint::Null(keyword) |
2025            Hint::True(keyword) |
2026            Hint::False(keyword) |
2027            Hint::Array(keyword) |
2028            Hint::Callable(keyword) |
2029            Hint::Static(keyword) |
2030            Hint::Self_(keyword) |
2031            Hint::Parent(keyword) => {
2032                walker.walk_keyword(keyword, context);
2033            }
2034            Hint::Void(local_identifier) |
2035            Hint::Never(local_identifier) |
2036            Hint::Float(local_identifier) |
2037            Hint::Bool(local_identifier) |
2038            Hint::Integer(local_identifier) |
2039            Hint::String(local_identifier) |
2040            Hint::Object(local_identifier) |
2041            Hint::Mixed(local_identifier) |
2042            Hint::Iterable(local_identifier) => {
2043                walker.walk_local_identifier(local_identifier, context);
2044            }
2045        }
2046    }
2047
2048    ParenthesizedHint as parenthesized_hint => {
2049        walker.walk_hint(&parenthesized_hint.hint, context);
2050    }
2051
2052    NullableHint as nullable_hint => {
2053        walker.walk_hint(&nullable_hint.hint, context);
2054    }
2055
2056    UnionHint as union_hint => {
2057        walker.walk_hint(&union_hint.left, context);
2058        walker.walk_hint(&union_hint.right, context);
2059    }
2060
2061    IntersectionHint as intersection_hint => {
2062        walker.walk_hint(&intersection_hint.left, context);
2063        walker.walk_hint(&intersection_hint.right, context);
2064    }
2065
2066    Keyword as keyword => {
2067        // Do nothing by default
2068    }
2069}