Macro hygiene prevents identifiers created or referenced during a macro expansion from accidentally colliding with names in surrounding Rust code. This safeguard is especially important for declarative macros, whose generated code receives the language's compile-time checks. section 1.3 section 2.2.7
Generated names stay separate
Suppose generate_x!() expands to `let x = 0`. Code outside the macro cannot then increment that binding with `x += 1`; Rust treats the macro's `x` and the surrounding `x` as different identifiers and reports that the outside name is unresolved. To affect an external identifier, pass it into the macro as an argument. section 2.2.7
Hygiene has two practical consequences:
- Protects surrounding code from accidental capture when a macro creates ordinary names for calculations or temporary data. section 1.3 section 2.2.7
- Requires deliberate inputs when generated code must affect surrounding code, such as an implementation block or a caller-provided identifier. section 2.2.7
- Makes unresolved or unknown names near macro code a useful signal to inspect identifier scope and expansion behavior. section 2.2.7

