Skip to content

Grammar: Paths #431

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 6 commits into from
Oct 6, 2018
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
19 changes: 12 additions & 7 deletions src/attributes.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,15 +11,16 @@
>    `#[` MetaItem `]`
>
> _MetaItem_ :\
>       IDENTIFIER\
>    | IDENTIFIER `=` LITERAL\
>    | IDENTIFIER `(` _MetaSeq_ `)`
>       [_SimplePath_]\
> &nbsp;&nbsp; | [_SimplePath_] `=` [_LiteralExpression_]<sub>_without suffix_</sub>\
> &nbsp;&nbsp; | [_SimplePath_] `(` _MetaSeq_<sup>?</sup> `)`
>
> _MetaSeq_ :\
> &nbsp;&nbsp; &nbsp;&nbsp; EMPTY\
> &nbsp;&nbsp; | _MetaItem_\
> &nbsp;&nbsp; | LITERAL\
> &nbsp;&nbsp; | _MetaItem_ `,` _MetaSeq_
> &nbsp;&nbsp; _MetaItemInner_ ( `,` MetaItemInner )<sup>\*</sup> `,`<sup>?</sup>
>
> _MetaItemInner_ :\
> &nbsp;&nbsp; &nbsp;&nbsp; _MetaItem_\
> &nbsp;&nbsp; | [_LiteralExpression_]<sub>_without suffix_</sub>

An _attribute_ is a general, free-form metadatum that is interpreted according
to name, convention, and language and compiler version. Attributes are modeled
Expand All @@ -33,6 +34,8 @@ Attributes may appear as any of:
* An identifier followed by a parenthesized list of sub-attribute arguments
which include literals

Literal values must not include integer or float type suffixes.

_Inner attributes_, written with a bang ("!") after the hash ("#"), apply to the
item that the attribute is declared within. _Outer attributes_, written without
the bang after the hash, apply to the thing that follows the attribute.
Expand Down Expand Up @@ -522,6 +525,8 @@ impl<T: PartialEq> PartialEq for Foo<T> {

You can implement `derive` for your own traits through [procedural macros].

[_LiteralExpression_]: expressions/literal-expr.html
[_SimplePath_]: paths.html#simple-paths
[Doc comments]: comments.html#doc-comments
[The Rustdoc Book]: ../rustdoc/the-doc-attribute.html
[procedural macros]: procedural-macros.html
Expand Down
10 changes: 8 additions & 2 deletions src/expressions/method-call-expr.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
# Method-call expressions

> **<sup>Syntax</sup>**\
> _MethodCallExpression_ :\
> &nbsp;&nbsp; [_Expression_] `.` [_PathExprSegment_] `(`[_CallParams_]<sup>?</sup> `)`

A _method call_ consists of an expression (the *receiver*) followed by a single
dot, an [identifier], and a parenthesized expression-list. Method calls are
dot, an expression path segment, and a parenthesized expression-list. Method calls are
resolved to associated [methods] on specific traits, either statically
dispatching to a method if the exact `self`-type of the left-hand-side is known,
or dynamically dispatching if the left-hand-side expression is an indirect
Expand Down Expand Up @@ -93,7 +97,9 @@ method and you'll be fine.

</div>

[IDENTIFIER]: identifiers.html
[_CallParams_]: expressions/call-expr.html
[_Expression_]: expressions.html
[_PathExprSegment_]: paths.html#paths-in-expressions
[visible]: visibility-and-privacy.html
[array]: types.html#array-and-slice-types
[trait objects]: types.html#trait-objects
Expand Down
4 changes: 2 additions & 2 deletions src/expressions/operator-expr.md
Original file line number Diff line number Diff line change
Expand Up @@ -312,7 +312,7 @@ let y = false && panic!(); // false, doesn't evaluate `panic!()`

> **<sup>Syntax</sup>**\
> _TypeCastExpression_ :\
> &nbsp;&nbsp; [_Expression_] `as` [_PathInExpression_]
> &nbsp;&nbsp; [_Expression_] `as` [_TypeNoBounds_]

A type cast expression is denoted with the binary operator `as`.

Expand Down Expand Up @@ -460,4 +460,4 @@ assert_eq!(x, 14);
[_CompoundAssignmentExpression_]: #compound-assignment-expressions

[_Expression_]: expressions.html
[_PathInExpression_]: paths.html
[_TypeNoBounds_]: types.html
9 changes: 8 additions & 1 deletion src/expressions/path-expr.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
# Path expressions

> **<sup>Syntax</sup>**\
> _PathExpression_ :\
> &nbsp;&nbsp; &nbsp;&nbsp; [_PathInExpression_]\
> &nbsp;&nbsp; | [_QualifiedPathInExpression_]

A [path] used as an expression context denotes either a local
variable or an item. Path expressions that resolve to local or static variables
are [place expressions], other paths are [value expressions]. Using a
Expand All @@ -19,8 +24,10 @@ let push_integer = Vec::<i32>::push;
let slice_reverse = <[i32]>::reverse;
```

[_PathInExpression_]: paths.html#paths-in-expressions
[_QualifiedPathInExpression_]: paths.html#qualified-paths
[place expressions]: expressions.html#place-expressions-and-value-expressions
[value expressions]: expressions.html#place-expressions-and-value-expressions
[path]: paths.html
[`static mut`]: items/static-items.html#mutable-statics
[`unsafe` block]: expressions/block-expr.html#unsafe-blocks
[`unsafe` block]: expressions/block-expr.html#unsafe-blocks
4 changes: 2 additions & 2 deletions src/items/structs.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,15 +25,15 @@
>
> _StructField_ :\
> &nbsp;&nbsp; [_OuterAttribute_]<sup>\*</sup>\
> &nbsp;&nbsp; [_Visibility_]
> &nbsp;&nbsp; [_Visibility_]<sup>?</sup>\
> &nbsp;&nbsp; [IDENTIFIER] `:` [_Type_]
>
> _TupleFields_ :\
> &nbsp;&nbsp; _TupleField_ (`,` _TupleField_)<sup>\*</sup> `,`<sup>?</sup>
>
> _TupleField_ :\
> &nbsp;&nbsp; [_OuterAttribute_]<sup>\*</sup>\
> &nbsp;&nbsp; [_Visibility_]
> &nbsp;&nbsp; [_Visibility_]<sup>?</sup>\
> &nbsp;&nbsp; [_Type_]

A _struct_ is a nominal [struct type] defined with the keyword `struct`.
Expand Down
59 changes: 44 additions & 15 deletions src/items/use-declarations.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

> **<sup>Syntax:</sup>**\
> _UseDeclaration_ :\
> &nbsp;&nbsp; ([_Visibility_])<sup>?</sup> `use` _UseTree_ `;`
> &nbsp;&nbsp; [_Visibility_]<sup>?</sup> `use` _UseTree_ `;`
>
> _UseTree_ :\
> &nbsp;&nbsp; &nbsp;&nbsp; ([_SimplePath_]<sup>?</sup> `::`)<sup>?</sup> `*`\
Expand Down Expand Up @@ -57,6 +57,8 @@ fn main() {
}
```

## `use` Visibility

Like items, `use` declarations are private to the containing module, by
default. Also like items, a `use` declaration can be public, if qualified by
the `pub` keyword. Such a `use` declaration serves to _re-export_ a name. A
Expand All @@ -82,32 +84,32 @@ mod quux {
In this example, the module `quux` re-exports two public names defined in
`foo`.

Also note that the paths contained in `use` items are relative to the crate
root. So, in the previous example, the `use` refers to `quux::foo::{bar, baz}`,
and not simply to `foo::{bar, baz}`. This also means that top-level module
declarations should be at the crate root if direct usage of the declared
modules within `use` items is desired. It is also possible to use `self` and
`super` at the beginning of a `use` item to refer to the current and direct
parent modules respectively. All rules regarding accessing declared modules in
`use` declarations apply to both module declarations and `extern crate`
declarations.
## `use` Paths

Paths in `use` items must start with a crate name or one of the [path
qualifiers] `crate`, `self`, `super`, or `::`. `crate` refers to the current
crate. `self` refers to the current module. `super` refers to the parent
module. `::` can be used to explicitly refer to a crate, requiring an extern
crate name to follow.

An example of what will and will not work for `use` items:
<!-- Note: This example works as-is in either 2015 or 2018. -->

```rust
# #![allow(unused_imports)]
use foo::baz::foobaz; // good: foo is at the root of the crate
use std::path::{self, Path, PathBuf}; // good: std is a crate name
use crate::foo::baz::foobaz; // good: foo is at the root of the crate

mod foo {

mod example {
pub mod iter {}
}

use foo::example::iter; // good: foo is at crate root
// use example::iter; // bad: example is not at the crate root
use crate::foo::example::iter; // good: foo is at crate root
// use example::iter; // bad: relative paths are not allowed without `self`
use self::baz::foobaz; // good: self refers to module 'foo'
use foo::bar::foobar; // good: foo is at crate root
use crate::foo::bar::foobar; // good: foo is at crate root

pub mod bar {
pub fn foobar() { }
Expand All @@ -122,6 +124,33 @@ mod foo {
fn main() {}
```

> **Edition Differences**: In the 2015 Edition, `use` paths also allow
> accessing items in the crate root. Using the example above, the following
> `use` paths work in 2015 but not 2018:
>
> ```rust,ignore
> use foo::example::iter;
> use ::foo::baz::foobaz;
> ```
>
> In the 2018 Edition, if an in-scope item has the same name as an external
> crate, then `use` of that crate name requires a leading `::` to
> unambiguously select the crate name. This is to retain compatibility with
> potential future changes. <!-- uniform_paths future-proofing -->
>
> ```rust,edition2018
> // use std::fs; // Error, this is ambiguous.
> use ::std::fs; // Imports from the `std` crate, not the module below.
> use self::std::fs as self_fs; // Imports the module below.
>
> mod std {
> pub mod fs {}
> }
> # fn main() {}
> ```


[IDENTIFIER]: identifiers.html
[_SimplePath_]: paths.html
[_SimplePath_]: paths.html#simple-paths
[_Visibility_]: visibility-and-privacy.html
[path qualifiers]: paths.html#path-qualifiers
Loading