Skip to content

Add macros in extern blocks and new proc-macro support. #691

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Oct 3, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 6 additions & 4 deletions src/items/external-blocks.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,10 @@
>    `}`
>
> _ExternalItem_ :\
> &nbsp;&nbsp; [_OuterAttribute_]<sup>\*</sup>\
> &nbsp;&nbsp; [_Visibility_]<sup>?</sup>\
> &nbsp;&nbsp; ( _ExternalStaticItem_ | _ExternalFunctionItem_ )
> &nbsp;&nbsp; [_OuterAttribute_]<sup>\*</sup> (\
> &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; [_MacroInvocationSemi_]\
> &nbsp;&nbsp; &nbsp;&nbsp; | ( [_Visibility_]<sup>?</sup> ( _ExternalStaticItem_ | _ExternalFunctionItem_ ) )\
> &nbsp;&nbsp; )
>
> _ExternalStaticItem_ :\
> &nbsp;&nbsp; `static` `mut`<sup>?</sup> [IDENTIFIER] `:` [_Type_] `;`
Expand All @@ -31,7 +32,7 @@

External blocks provide _declarations_ of items that are not _defined_ in the
current crate and are the basis of Rust's foreign function interface. These are
akin to unchecked imports.
akin to unchecked imports.

Two kind of item _declarations_ are allowed in external blocks: [functions] and
[statics]. Calling functions or accessing statics that are declared in external
Expand Down Expand Up @@ -170,6 +171,7 @@ extern {
[_FunctionReturnType_]: functions.md
[_Generics_]: generics.md
[_InnerAttribute_]: ../attributes.md
[_MacroInvocationSemi_]: ../macros.md#macro-invocation
[_MetaListNameValueStr_]: ../attributes.md#meta-item-attribute-syntax
[_MetaNameValueStr_]: ../attributes.md#meta-item-attribute-syntax
[_OuterAttribute_]: ../attributes.md
Expand Down
2 changes: 2 additions & 0 deletions src/macros.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ following situations:
* [Types]
* [Items] including [associated items]
* [`macro_rules`] transcribers
* [External blocks]

When used as an item or a statement, the _MacroInvocationSemi_ form is used
where a semicolon is required at the end when not using curly braces.
Expand Down Expand Up @@ -99,3 +100,4 @@ example!();
[statements]: statements.md
[types]: types.md
[visibility qualifiers]: visibility-and-privacy.md
[External blocks]: items/external-blocks.md
42 changes: 25 additions & 17 deletions src/procedural-macros.md
Original file line number Diff line number Diff line change
Expand Up @@ -75,9 +75,7 @@ the macro invocation operator (`!`).
These macros are defined by a [public]&#32;[function] with the `proc_macro`
[attribute] and a signature of `(TokenStream) -> TokenStream`. The input
[`TokenStream`] is what is inside the delimiters of the macro invocation and the
output [`TokenStream`] replaces the entire macro invocation. It may contain an
arbitrary number of [items]. These macros cannot expand to syntax that defines
new `macro_rules` style macros.
output [`TokenStream`] replaces the entire macro invocation.

For example, the following macro definition ignores its input and outputs a
function `answer` into its scope.
Expand Down Expand Up @@ -105,11 +103,12 @@ fn main() {
}
```

These macros are only invokable in [modules]. They cannot even be invoked to
create [item declaration statements]. Furthermore, they must either be invoked
with curly braces and no semicolon or a different delimiter followed by a
semicolon. For example, `make_answer` from the previous example can be invoked
as `make_answer!{}`, `make_answer!();` or `make_answer![];`.
Function-like procedural macros may expand to a [type] or any number of
[items]. They may be invoked in a [type expression], [item] position (except
as a [statement]), including items in [`extern` blocks], inherent and trait
[implementations], and [trait definitions]. They cannot be used in a
[statement], [expression], or [pattern]. These macros cannot expand to syntax
that defines new [`macro_rules`] style macros.

### Derive macros

Expand Down Expand Up @@ -192,7 +191,9 @@ struct Struct {

### Attribute macros

*Attribute macros* define new [attributes] which can be attached to [items].
*Attribute macros* define new [outer attributes][attributes] which can be
attached to [items], including items in [`extern` blocks], inherent and trait
[implementations], and [trait definitions].

Attribute macros are defined by a [public]&#32;[function] with the
`proc_macro_attribute` [attribute] that has a signature of `(TokenStream,
Expand All @@ -202,7 +203,7 @@ the attribute is written as a bare attribute name, the attribute
[`TokenStream`] is empty. The second [`TokenStream`] is the rest of the [item]
including other [attributes] on the [item]. The returned [`TokenStream`]
replaces the [item] with an arbitrary number of [items]. These macros cannot
expand to syntax that defines new `macro_rules` style macros.
expand to syntax that defines new [`macro_rules`] style macros.

For example, this attribute macro takes the input stream and returns it as is,
effectively being the no-op of attributes.
Expand Down Expand Up @@ -266,28 +267,35 @@ fn invoke4() {}
// out: item: "fn invoke4() {}"
```

[Attribute macros]: #attribute-macros
[Cargo's build scripts]: ../cargo/reference/build-scripts.html
[Derive macros]: #derive-macros
[Function-like macros]: #function-like-procedural-macros
[`TokenStream`]: ../proc_macro/struct.TokenStream.html
[`TokenStream`s]: ../proc_macro/struct.TokenStream.html
[`compile_error`]: ../std/macro.compile_error.html
[`derive` attribute]: attributes/derive.md
[`extern` blocks]: items/external-blocks.md
[`macro_rules`]: macros-by-example.md
[`proc_macro` crate]: ../proc_macro/index.html
[Cargo's build scripts]: ../cargo/reference/build-scripts.html
[Derive macros]: #derive-macros
[Attribute macros]: #attribute-macros
[Function-like macros]: #function-like-procedural-macros
[attribute]: attributes.md
[attributes]: attributes.md
[block]: expressions/block-expr.md
[crate type]: linkage.md
[derive macro helper attributes]: #derive-macro-helper-attributes
[enum]: items/enumerations.md
[expression]: expressions.md
[function]: items/functions.md
[implementations]: items/implementations.md
[inert]: attributes.md#active-and-inert-attributes
[item]: items.md
[item declaration statements]: statements.md#item-declarations
[items]: items.md
[function]: items/functions.md
[module]: items/modules.md
[modules]: items/modules.md
[pattern]: patterns.md
[public]: visibility-and-privacy.md
[statement]: statements.md
[struct]: items/structs.md
[trait definitions]: items/traits.md
[type expression]: types.md#type-expressions
[type]: types.md
[union]: items/unions.md