Commit Graph

11083 Commits

Author SHA1 Message Date
bors
393fdc1048 Auto merge of #94021 - tmiasko:inline, r=nagisa
Inline a few trivial conversion functions
2022-02-15 23:48:43 +00:00
bors
09cb29c64c Auto merge of #93439 - abrown:cf-protection, r=nagisa
Add support for control-flow protection

This change adds a flag for configuring control-flow protection in the LLVM backend. In Clang, this flag is exposed as `-fcf-protection` with options `none|branch|return|full`. This convention is followed for `rustc`, though as a codegen option: `rustc -Z cf-protection=<none|branch|return|full>`. Tracking issue for future work is #93754.
2022-02-15 21:20:49 +00:00
bors
bfb2856f27 Auto merge of #93820 - compiler-errors:gat-wfcheck, r=jackh726
Rework GAT `where` clause check

rework the GAT where check to use a fixed-point algorithm, and check all GATs in a trait at once

fixes #93278

r? `@jackh726`
cc `@nikomatsakis`
2022-02-15 19:03:38 +00:00
Tomasz Miąsko
ea71420761 Inline LocalExpnId::from_raw and LocalExpnId::as_raw 2022-02-15 19:08:12 +01:00
Tomasz Miąsko
81f12eb7ef Inline Target::deref 2022-02-15 19:08:12 +01:00
Tomasz Miąsko
d04677750b Inline GenericArg conversion functions 2022-02-15 19:08:08 +01:00
Tomasz Miąsko
cd37638c14 Inline UnifyKey::index and UnifyKey::from_index 2022-02-15 19:07:06 +01:00
Michael Goulet
f045b214ea Add removed comments back in self-outlives-lint 2022-02-15 09:17:09 -08:00
Michael Goulet
ce16189d46 add some more comments to GAT where clause check 2022-02-15 09:17:09 -08:00
Michael Goulet
477459795d make the gat wfcheck algorithm a loop 2022-02-15 09:17:09 -08:00
Michael Goulet
852a851712 check associated types too 2022-02-15 09:17:09 -08:00
Michael Goulet
453d2dbbd4 check all GATs at once 2022-02-15 09:17:09 -08:00
Michael Goulet
764839320c rename some variables in gat wfcheck 2022-02-15 09:17:09 -08:00
Michael Goulet
5b2291cfa6 introduce gather_gat_bounds 2022-02-15 09:17:07 -08:00
Matthias Krüger
a87be980d8
Rollup merge of #94001 - durin42:llvm-15-uwtable, r=nikic
llvm: migrate to new parameter-bearing uwtable attr

In https://reviews.llvm.org/D114543 the uwtable attribute gained a flag
so that we can ask for sync uwtables instead of async, as the former are
much cheaper. The default is async, so that's what I've done here, but I
left a TODO that we might be able to do better.

While in here I went ahead and dropped support for removing uwtable
attributes in rustc: we never did it, so I didn't write the extra C++
bridge code to make it work. Maybe I should have done the same thing
with the `sync|async` parameter but we'll see.
2022-02-15 16:02:37 +01:00
Matthias Krüger
c6b27db876
Rollup merge of #93999 - barzamin:suggest-raw-strings, r=jackh726
suggest using raw strings when invalid escapes appear in literals

i'd guess about 70% of "bad escape" cases occur when someone meant to use a raw string literal because they're passing it directly to `Regex::new()`.
this emits an advisory (`Applicability::MaybeIncorrect`) `help:` suggestion to the user that they use an `r""` string, on top of the normal notes about looking at the string literal documentation/spec.
2022-02-15 16:02:35 +01:00
bors
5569757491 Auto merge of #93148 - nnethercote:Uniq, r=fee1-dead
Overhaul interning.

A number of types are interned and `eq` and `hash` are implemented on
the pointer rather than the contents. But this is not well enforced
within the type system like you might expect.

This PR introduces a new type `Interned` which encapsulates this concept
more rigorously, and uses it to convert a couple of the less common
interned types.

r? `@fee1-dead`
2022-02-15 11:59:37 +00:00
bors
6421a499a5 Auto merge of #93176 - danielhenrymantilla:stack-pinning-macro, r=m-ou-se
Add a stack-`pin!`-ning macro to `core::pin`.

  - https://github.com/rust-lang/rust/issues/93178

`pin!` allows pinning a value to the stack. Thanks to being implemented in the stdlib, which gives access to `macro` macros, and to the private `.pointer` field of the `Pin` wrapper, [it was recently discovered](https://rust-lang.zulipchat.com/#narrow/stream/187312-wg-async-foundations/topic/pin!.20.E2.80.94.20the.20.22definitive.22.20edition.20.28a.20rhs-compatible.20pin-nin.2E.2E.2E/near/268731241) ([archive link](https://zulip-archive.rust-lang.org/stream/187312-wg-async-foundations/topic/A.20rhs-compatible.20pin-ning.20macro.html#268731241)), contrary to popular belief, that it is actually possible to implement and feature such a macro:

```rust
let foo: Pin<&mut PhantomPinned> = pin!(PhantomPinned);
stuff(foo);
```
or, directly:

```rust
stuff(pin!(PhantomPinned));
```

  - For context, historically, this used to require one of the two following syntaxes:

      - ```rust
        let foo = PhantomPinned;
        pin!(foo);
        stuff(foo);
        ```

      -  ```rust
         pin! {
             let foo = PhantomPinned;
         }
         stuff(foo);
         ```

This macro thus allows, for instance, doing things like:

```diff
fn block_on<T>(fut: impl Future<Output = T>) -> T {
    // Pin the future so it can be polled.
-   let mut fut = Box::pin(fut);
+   let mut fut = pin!(fut);

    // Create a new context to be passed to the future.
    let t = thread::current();
    let waker = Arc::new(ThreadWaker(t)).into();
    let mut cx = Context::from_waker(&waker);

    // Run the future to completion.
    loop {
        match fut.as_mut().poll(&mut cx) {
            Poll::Ready(res) => return res,
            Poll::Pending => thread::park(),
        }
    }
}
```

  - _c.f._, https://doc.rust-lang.org/1.58.1/alloc/task/trait.Wake.html

And so on, and so forth.

I don't think such an API can get better than that, barring full featured language support (`&pin` references or something), so I see no reason not to start experimenting with featuring this in the stdlib already 🙂

  - cc `@rust-lang/wg-async-foundations` \[EDIT: this doesn't seem to have pinged anybody 😩, thanks `@yoshuawuyts` for the real ping\]

r? `@joshtriplett`

___

# Docs preview

https://user-images.githubusercontent.com/9920355/150605731-1f45c2eb-c9b0-4ce3-b17f-2784fb75786e.mp4

___

# Implementation

The implementation ends up being dead simple (so much it's embarrassing):

```rust
pub macro pin($value:expr $(,)?) {
    Pin { pointer: &mut { $value } }
}
```

_and voilà_!

  - The key for it working lies in [the rules governing the scope of anonymous temporaries](https://doc.rust-lang.org/1.58.1/reference/destructors.html#temporary-lifetime-extension).

<details><summary>Comments and context</summary>

This is `Pin::new_unchecked(&mut { $value })`, so, for starters, let's
review such a hypothetical macro (that any user-code could define):
```rust
macro_rules! pin {( $value:expr ) => (
    match &mut { $value } { at_value => unsafe { // Do not wrap `$value` in an `unsafe` block.
        $crate::pin::Pin::<&mut _>::new_unchecked(at_value)
    }}
)}
```

Safety:
  - `type P = &mut _`. There are thus no pathological `Deref{,Mut}` impls that would break `Pin`'s invariants.
  - `{ $value }` is braced, making it a _block expression_, thus **moving** the given `$value`, and making it _become an **anonymous** temporary_.
    By virtue of being anonynomous, it can no longer be accessed, thus preventing any attemps to `mem::replace` it or `mem::forget` it, _etc._

This gives us a `pin!` definition that is sound, and which works, but only in certain scenarios:

  - If the `pin!(value)` expression is _directly_ fed to a function call:
    `let poll = pin!(fut).poll(cx);`

  - If the `pin!(value)` expression is part of a scrutinee:

    ```rust
    match pin!(fut) { pinned_fut => {
        pinned_fut.as_mut().poll(...);
        pinned_fut.as_mut().poll(...);
    }} // <- `fut` is dropped here.
    ```

Alas, it doesn't work for the more straight-forward use-case: `let` bindings.

```rust
let pinned_fut = pin!(fut); // <- temporary value is freed at the end of this statement
pinned_fut.poll(...) // error[E0716]: temporary value dropped while borrowed
                     // note: consider using a `let` binding to create a longer lived value
```

  - Issues such as this one are the ones motivating https://github.com/rust-lang/rfcs/pull/66

This makes such a macro incredibly unergonomic in practice, and the reason most macros out there had to take the path of being a statement/binding macro (_e.g._, `pin!(future);`) instead of featuring the more intuitive ergonomics of an expression macro.

Luckily, there is a way to avoid the problem. Indeed, the problem stems from the fact that a temporary is dropped at the end of its enclosing statement when it is part of the parameters given to function call, which has precisely been the case with our `Pin::new_unchecked()`!

For instance,

```rust
let p = Pin::new_unchecked(&mut <temporary>);
```

becomes:

```rust
let p = { let mut anon = <temporary>; &mut anon };
```

However, when using a literal braced struct to construct the value, references to temporaries can then be taken. This makes Rust change the lifespan of such temporaries so that they are, instead, dropped _at the end of the enscoping block_.

For instance,
```rust
let p = Pin { pointer: &mut <temporary> };
```

becomes:

```rust
let mut anon = <temporary>;
let p = Pin { pointer: &mut anon };
```

which is *exactly* what we want.

Finally, we don't hit problems _w.r.t._ the privacy of the `pointer` field, or the unqualified `Pin` name, thanks to `decl_macro`s being _fully_ hygienic (`def_site` hygiene).

</details>

___

# TODO

  - [x] Add compile-fail tests with attempts to break the `Pin` invariants thanks to the macro (_e.g._, try to access the private `.pointer` field, or see what happens if such a pin is used outside its enscoping scope (borrow error));
  - [ ] Follow-up stuff:
      - [ ] Try to experiment with adding `pin!` to the prelude: this may require to be handled with some extra care, as it may lead to issues reminiscent of those of `assert_matches!`: https://github.com/rust-lang/rust/issues/82913
      - [x] Create the tracking issue.
2022-02-15 09:32:03 +00:00
Nicholas Nethercote
80632de4a1 Address review comments. 2022-02-15 16:20:01 +11:00
Nicholas Nethercote
a95fb8b150 Overhaul Const.
Specifically, rename the `Const` struct as `ConstS` and re-introduce `Const` as
this:
```
pub struct Const<'tcx>(&'tcx Interned<ConstS>);
```
This now matches `Ty` and `Predicate` more closely, including using
pointer-based `eq` and `hash`.

Notable changes:
- `mk_const` now takes a `ConstS`.
- `Const` was copy, despite being 48 bytes. Now `ConstS` is not, so need a
  we need separate arena for it, because we can't use the `Dropless` one any
  more.
- Many `&'tcx Const<'tcx>`/`&Const<'tcx>` to `Const<'tcx>` changes
- Many `ct.ty` to `ct.ty()` and `ct.val` to `ct.val()` changes.
- Lots of tedious sigil fiddling.
2022-02-15 16:19:59 +11:00
Nicholas Nethercote
7eb15509ce Remove unnecessary RegionKind:: quals.
The variant names are exported, so we can use them directly (possibly
with a `ty::` qualifier). Lots of places already do this, this commit
just increases consistency.
2022-02-15 16:14:24 +11:00
Nicholas Nethercote
7024dc523a Overhaul RegionKind and Region.
Specifically, change `Region` from this:
```
pub type Region<'tcx> = &'tcx RegionKind;
```
to this:
```
pub struct Region<'tcx>(&'tcx Interned<RegionKind>);
```

This now matches `Ty` and `Predicate` more closely.

Things to note
- Regions have always been interned, but we haven't been using pointer-based
  `Eq` and `Hash`. This is now happening.
- I chose to impl `Deref` for `Region` because it makes pattern matching a lot
  nicer, and `Region` can be viewed as just a smart wrapper for `RegionKind`.
- Various methods are moved from `RegionKind` to `Region`.
- There is a lot of tedious sigil changes.
- A couple of types like `HighlightBuilder`, `RegionHighlightMode` now have a
  `'tcx` lifetime because they hold a `Ty<'tcx>`, so they can call `mk_region`.
- A couple of test outputs change slightly, I'm not sure why, but the new
  outputs are a little better.
2022-02-15 16:08:52 +11:00
Nicholas Nethercote
925ec0d3c7 Overhaul PredicateInner and Predicate.
Specifically, change `Ty` from this:
```
pub struct Predicate<'tcx> { inner: &'tcx PredicateInner<'tcx> }
```
to this:
```
pub struct Predicate<'tcx>(&'tcx Interned<PredicateS<'tcx>>)
```
where `PredicateInner` is renamed as `PredicateS`.

 This (plus a few other minor changes) makes the parallels with `Ty` and
`TyS` much clearer, and makes the uniqueness more explicit.
2022-02-15 16:03:26 +11:00
Nicholas Nethercote
e9a0c429c5 Overhaul TyS and Ty.
Specifically, change `Ty` from this:
```
pub type Ty<'tcx> = &'tcx TyS<'tcx>;
```
to this
```
pub struct Ty<'tcx>(Interned<'tcx, TyS<'tcx>>);
```
There are two benefits to this.
- It's now a first class type, so we can define methods on it. This
  means we can move a lot of methods away from `TyS`, leaving `TyS` as a
  barely-used type, which is appropriate given that it's not meant to
  be used directly.
- The uniqueness requirement is now explicit, via the `Interned` type.
  E.g. the pointer-based `Eq` and `Hash` comes from `Interned`, rather
  than via `TyS`, which wasn't obvious at all.

Much of this commit is boring churn. The interesting changes are in
these files:
- compiler/rustc_middle/src/arena.rs
- compiler/rustc_middle/src/mir/visit.rs
- compiler/rustc_middle/src/ty/context.rs
- compiler/rustc_middle/src/ty/mod.rs

Specifically:
- Most mentions of `TyS` are removed. It's very much a dumb struct now;
  `Ty` has all the smarts.
- `TyS` now has `crate` visibility instead of `pub`.
- `TyS::make_for_test` is removed in favour of the static `BOOL_TY`,
  which just works better with the new structure.
- The `Eq`/`Ord`/`Hash` impls are removed from `TyS`. `Interned`s impls
  of `Eq`/`Hash` now suffice. `Ord` is now partly on `Interned`
  (pointer-based, for the `Equal` case) and partly on `TyS`
  (contents-based, for the other cases).
- There are many tedious sigil adjustments, i.e. adding or removing `*`
  or `&`. They seem to be unavoidable.
2022-02-15 16:03:24 +11:00
Nicholas Nethercote
0c2ebbd412 Rename PtrKey as Interned and improve it.
In particular, there's now more protection against incorrect usage,
because you can only create one via `Interned::new_unchecked`, which
makes it more obvious that you must be careful.

There are also some tests.
2022-02-15 15:50:29 +11:00
Nicholas Nethercote
028e57ba1d Rename Interned as InternedInSet.
This will let us introduce a more widely-used `Interned` type in the
next commit.
2022-02-15 15:50:29 +11:00
bors
8d163e6621 Auto merge of #93863 - pierwill:fix-93676, r=Mark-Simulacrum
Update `sha1`, `sha2`, and `md-5` dependencies

This replaces the deprecated [`cpuid-bool`](https://crates.io/crates/cpuid-bool) dependency with [`cpufeatures`](https://crates.io/crates/cpufeatures), while adding [`crypto-common`](https://crates.io/crates/crypto-common) as a new dependency.

Closes #93676.
2022-02-15 04:39:37 +00:00
bors
0c3f0cddde Auto merge of #93752 - eholk:drop-tracking-break-continue, r=nikomatsakis
Generator drop tracking: improve break and continue handling

This PR fixes two related issues.

One, sometimes break or continue have a block target instead of an expression target. This seems to mainly happen with try blocks. Since the drop tracking analysis only works on expressions, if we see a block target for break or continue, we substitute the last expression of the block as the target instead.

Two, break and continue were incorrectly being treated as the same, so continue would also show up as an exit from the loop or block. This patch corrects the way continue is handled by keeping a stack of loop entry points and uses those to find the target of the continue.

Fixes #93197

r? `@nikomatsakis`
2022-02-15 02:27:37 +00:00
Augie Fackler
0958c8f4ca llvm: migrate to new parameter-bearing uwtable attr
In https://reviews.llvm.org/D114543 the uwtable attribute gained a flag
so that we can ask for sync uwtables instead of async, as the former are
much cheaper. The default is async, so that's what I've done here, but I
left a TODO that we might be able to do better.

While in here I went ahead and dropped support for removing uwtable
attributes in rustc: we never did it, so I didn't write the extra C++
bridge code to make it work. Maybe I should have done the same thing
with the `sync|async` parameter but we'll see.
2022-02-14 16:09:53 -05:00
Erin Petra Sofiya Moon
e59cda9ee1
suggest using raw string literals when invalid escapes appear
i'd guess about 70% of "bad escape" cases occur when someone meant to
use a raw string literal because they're passing it directly to
Regex::new(). this emits an advisory (Applicability::MaybeIncorrect)
help: suggestion to the user that they use an r"" string,
on top of the normal notes about looking at the
string literal documentation/spec.
2022-02-14 15:11:38 -05:00
Mara Bos
bf2a9dc375
Update unsafe_pin_internals unstable version. 2022-02-14 19:17:21 +00:00
bors
c5c610aad0 Auto merge of #93652 - spastorino:fix-negative-overlap-check-regions, r=nikomatsakis
Fix negative overlap check regions

r? `@nikomatsakis`
2022-02-14 18:28:04 +00:00
Andrew Brown
8d6c973c7f Add support for control-flow protection
This change adds a flag for configuring control-flow protection in the
LLVM backend. In Clang, this flag is exposed as `-fcf-protection` with
options `none|branch|return|full`. This convention is followed for
`rustc`, though as a codegen option: `rustc -Z
cf-protection=<none|branch|return|full>`.

Co-authored-by: BlackHoleFox <blackholefoxdev@gmail.com>
2022-02-14 08:31:24 -08:00
Daniel Henry-Mantilla
c93968aee8 Mark unsafe_pin_internals as incomplete.
This thus still makes it technically possible to enable the feature, and thus
to trigger UB without `unsafe`, but this is fine since incomplete features are
known to be potentially unsound (labelled "may not be safe").

This follows from the discussion at https://github.com/rust-lang/rust/pull/93176#discussion_r799413561
2022-02-14 17:27:37 +01:00
Santiago Pastorino
3c7fa0bcf3
reveal_defining_opaque_types field doesn't exist after rebase 2022-02-14 13:02:22 -03:00
Santiago Pastorino
8c4ffaaa7c
Inline loose_check fn on call site 2022-02-14 12:57:22 -03:00
Santiago Pastorino
45983fecff
Add comments about outlives_env 2022-02-14 12:57:22 -03:00
Santiago Pastorino
f4bb4500dd
Call the method fork instead of clone and add proper comments 2022-02-14 12:57:20 -03:00
Santiago Pastorino
3fd89a662a
Properly check regions on negative overlap check 2022-02-14 12:56:28 -03:00
Santiago Pastorino
b61e1bbf06
Add debug calls for negative impls in coherence 2022-02-14 12:56:28 -03:00
Santiago Pastorino
74c431866b
Move FIXME text to the right place 2022-02-14 12:56:28 -03:00
Santiago Pastorino
4e83924595
Remove extra negative_impl_exists check 2022-02-14 12:56:27 -03:00
bors
52dd59ed21 Auto merge of #93298 - lcnr:issue-92113, r=cjgillot
make `find_similar_impl_candidates` even fuzzier

continues the good work of `@BGR360` in #92223. I might have overshot a bit and we're now slightly too fuzzy 😅

with this we can now also simplify `simplify_type`, which is nice :3
2022-02-14 14:47:20 +00:00
bors
b321742c6c Auto merge of #93938 - BoxyUwU:fix_res_self_ty, r=lcnr
Make `Res::SelfTy` a struct variant and update docs

I found pattern matching on a `(Option<DefId>, Option<(DefId, bool)>)` to not be super readable, additionally the doc comments on the types in a tuple variant aren't visible anywhere at use sites as far as I can tell (using rust analyzer + vscode)

The docs incorrectly assumed that the `DefId` in `Option<(DefId, bool)>` would only ever be for an impl item and I also found the code examples to be somewhat unclear about which `DefId` was being talked about.

r? `@lcnr` since you reviewed the last PR changing these docs
2022-02-14 12:26:43 +00:00
lcnr
f2aea1ea6e further update fuzzy_match_tys 2022-02-14 07:37:15 +01:00
lcnr
0efc6c02cb fast_reject: remove StripReferences 2022-02-14 07:37:14 +01:00
lcnr
165142e993 fuzzify fuzzy_match_tys 2022-02-14 07:32:34 +01:00
Ben Reeves
002456a95a Make find_similar_impl_candidates a little fuzzier. 2022-02-14 07:32:34 +01:00
bors
902e59057e Auto merge of #93937 - bjorn3:simplifications3, r=cjgillot
Remove Config::stderr

1. It captured stdout and not stderr
2. It isn't used anywhere
3. All error messages should go to the DiagnosticOutput instead
4. It modifies thread local state

Marking as blocked as it will conflict a bit with https://github.com/rust-lang/rust/pull/93936.
2022-02-14 05:55:26 +00:00
pierwill
ef6dd124d6 Update sha1, sha2, and md5 dependencies
This removes the `cpuid-bool` dependency, which is deprecated,
while adding `crypto-common` as a new dependency.
2022-02-13 15:29:01 -06:00