Using diagnostic items avoids having to update the paths if the guard
types ever get moved around for some reason. Additionally, it also greatly
simplifies the `is_sync_lock` check.
If the type has a trivial Drop implementation, then it is probably irrelevant
that the type was dropped immediately, since nothing important
happens on drop. Hence, we can bail out early instead of doing some
expensive checks.
This commit uses `span_suggestion_verbose` to add what specific code
changes can be done as suggested by the lint--in this case, either binding
the expression to an unused variable or using `std::mem::drop` to drop
the value explicitly.
These lints are very noisy and are allow-by-default in clippy anyways.
Hence, setting them to allow-by-default here makes more sense than
warning constantly on these cases.
Similar to `let_underscore_drop`, this lint checks for statements similar
to `let _ = foo`, where `foo` is a lock guard. These types of let
statements are especially problematic because the lock gets released
immediately, instead of at the end of the scope. This behavior is almost
always the wrong thing.
This lint checks for statements similar to `let _ = foo`, where `foo` is
a type that implements `Drop`. These types of let statements cause the
expression in them to be dropped immediately, instead of at the end of
the scope. Such behavior can be surprizing, especially if you are
relying on the value to be dropped at the end of the scope. Instead, the
binding should be an underscore prefixed name (like `_unused`) or the
value should explicitly be passed to `std::mem::drop()` if the value
really should be dropped immediately.
Use GRND_INSECURE instead of /dev/urandom when possible
From reading the source code, it appears like the desired semantic of
std::unix::rand is to always provide some bytes and never block. For
that reason GRND_NONBLOCK is checked before calling getrandom(0), so
that getrandom(0) won't block. If it would block, then the function
falls back to using /dev/urandom, which for the time being doesn't
block. There are some drawbacks to using /dev/urandom, however, and so
getrandom(GRND_INSECURE) was created as a replacement for this exact
circumstance.
getrandom(GRND_INSECURE) is the same as /dev/urandom, except:
- It won't leave a warning in dmesg if used at early boot time, which is
a common occurance (and the reason why I found this issue);
- It won't introduce a tiny delay at early boot on newer kernels when
/dev/urandom tries to opportunistically create jitter entropy;
- It only requires 1 syscall, rather than 3.
Other than that, it returns the same "quality" of randomness as
/dev/urandom, and never blocks.
It's only available on kernels ≥5.6, so we try to use it, cache the
result of that attempt, and fall back to to the previous code if it
didn't work.
From reading the source code, it appears like the desired semantic of
std::unix::rand is to always provide some bytes and never block. For
that reason GRND_NONBLOCK is checked before calling getrandom(0), so
that getrandom(0) won't block. If it would block, then the function
falls back to using /dev/urandom, which for the time being doesn't
block. There are some drawbacks to using /dev/urandom, however, and so
getrandom(GRND_INSECURE) was created as a replacement for this exact
circumstance.
getrandom(GRND_INSECURE) is the same as /dev/urandom, except:
- It won't leave a warning in dmesg if used at early boot time, which is
a common occurance (and the reason why I found this issue);
- It won't introduce a tiny delay at early boot on newer kernels when
/dev/urandom tries to opportunistically create jitter entropy;
- It only requires 1 syscall, rather than 3.
Other than that, it returns the same "quality" of randomness as
/dev/urandom, and never blocks.
It's only available on kernels ≥5.6, so we try to use it, cache the
result of that attempt, and fall back to to the previous code if it
didn't work.
Cache more queries on disk
One of the principles of incremental compilation is to allow saving results on disk to avoid recomputing them.
This PR investigates persisting a lot of queries whose result are to be saved into metadata.
Some of the queries are cheap reads from HIR, but we may also want to get rid of these reads for incremental lowering.
Add complexity estimation of iterating over HashSet and HashMap
It is not obvious (at least for me) that complexity of iteration over hash tables depends on capacity and not length. Especially comparing with other containers like Vec or String. I think, this behaviour is worth mentioning.
I run benchmark which tests iteration time for maps with length 50 and different capacities and get this results:
```
capacity - time
64 - 203.87 ns
256 - 351.78 ns
1024 - 607.87 ns
4096 - 965.82 ns
16384 - 3.1188 us
```
If you want to dig why it behaves such way, you can look current implementation in [hashbrown code](f3a9f211d0/src/raw/mod.rs (L1933)).
Benchmarks code would be presented in PR related to this commit.
Do not emit the lint `unused_attributes` for *inherent* `#[doc(hidden)]` associated items
Fixes#97205 (embarrassing oversight from #96008).
`@rustbot` label A-lint
Minor tweaks to rustc book summary formatting.
This includes a few minor tweaks to the summary/titles of chapters for the rustc book:
* Use a consistent chapter capitalization and hyphenation.
* Move "Codegen Options" underneath "Command-line Arguments". I feel like they are two closely related chapters, where codegen is just a subset of the total arguments.
* Move "Target Tier Policy" underneath "Platform Support". That chapter includes that policy for platform support, and thus I feel it is more closely related to that grouping.
Reverse condition in Vec::retain_mut doctest
I find that the doctest for `Vec::retain_mut` is easier to read and understand when the `if` block corresponds to the path that returns `true` and the `else` block returns `false`. Having the `if` block be the `false` path led me to stare at the example for somewhat longer than I probably had to.
It is not obvious (at least for me) that complexity of iteration over hash tables depends on capacity and not length. Especially comparing with other containers like Vec or String. I think, this behaviour is worth mentioning.
I run benchmark which tests iteration time for maps with length 50 and different capacities and get this results:
```
capacity - time
64 - 203.87 ns
256 - 351.78 ns
1024 - 607.87 ns
4096 - 965.82 ns
16384 - 3.1188 us
```
If you want to dig why it behaves such way, you can look current implementation in [hashbrown code](f3a9f211d0/src/raw/mod.rs (L1933)).
Benchmarks code would be presented in PR related to this commit.
Rollup of 6 pull requests
Successful merges:
- #96565 (rustdoc: show implementations on `#[fundamental]` wrappers)
- #97179 (Add new lint to enforce whitespace after keywords)
- #97185 (interpret/validity: separately control checking numbers for being init and non-ptr)
- #97188 (Remove unneeded null pointer asserts in ptr2int casts)
- #97189 (Update .mailmap)
- #97192 (Say "last" instead of "rightmost" in the documentation for `std::str:rfind`)
Failed merges:
r? `@ghost`
`@rustbot` modify labels: rollup
Say "last" instead of "rightmost" in the documentation for `std::str:rfind`
In the documentation comment for `std::str::rfind`, say "last" instead
of "rightmost" to describe the match that `rfind` finds. This follows the
spirit of #30459, for which `trim_left` and `trim_right` were replaced by
`trim_start` and `trim_end` to be more clear about how they work on
text which is displayed right-to-left.
Remove unneeded null pointer asserts in ptr2int casts
This removes an assert that a pointer with address 0 has no provenance. This change is needed to support permissive provenance work in Miri, and seems justified by `ptr.with_addr(0)` working and a discussion on Zulip regarding LLVM semantics.
r? `@RalfJung`
interpret/validity: separately control checking numbers for being init and non-ptr
This lets Miri control this in a more fine-grained way.
r? `@oli-obk`