108 Commits

Author SHA1 Message Date
Deadbeef
06a1c14d52
Switch all libraries to the 2021 edition 2021-12-23 19:03:47 +08:00
Scott McMurray
a0b96902e4 Do array-slice equality via arrays, rather than always via slices
This'll still go via slices eventually for large arrays, but this way slice comparisons to short arrays can use the same memcmp-avoidance tricks.

Added some tests for all the combinations to make sure I didn't accidentally infinitely-recurse something.
2021-12-14 13:15:15 -08:00
bors
83b32f27fc Auto merge of #91766 - scottmcm:more-array-raw-eq, r=yaahc
Allow `memcmp` for more array comparisons

This way comparing `[NonZeroU8; 8]` is just as fast as comparing `[u8; 8]`.
2021-12-14 08:22:31 +00:00
Matthias Krüger
42f8d4833f
Rollup merge of #91086 - rhysd:issue-91085, r=m-ou-se
Implement `TryFrom<&'_ mut [T]>` for `[T; N]`

Fixes #91085.
2021-12-13 00:20:06 +01:00
Matthias Krüger
40482bb539
Rollup merge of #90270 - woppopo:const_borrow_trait, r=dtolnay
Make `Borrow` and `BorrowMut` impls `const`

Tracking issue: #91522
2021-12-11 17:35:24 +01:00
Scott McMurray
24affba02e Allow memcmp for more array comparisons
This way comparing `[NonZeroU8; 8]` is just as fast as comparing `[u8; 8]`.
2021-12-10 17:30:39 -08:00
Jethro Beekman
203cf2d366 Add rsplit_array variants to slices and arrays 2021-12-10 21:34:19 +01:00
bors
ce0f7baf56 Auto merge of #91512 - scottmcm:array-intoiter-advance, r=Mark-Simulacrum
Override `Iterator::advance(_back)_by` for `array::IntoIter`

Because I happened to notice that `nth` is currently getting codegen'd as a loop even for `Copy` types: <https://rust.godbolt.org/z/fPqv7Gvs7>

<details>
<summary>LLVM before and after</summary>

Rust:

```rust
#[no_mangle]
pub fn array_intoiter_nth(it: &mut std::array::IntoIter<i32, 100>, n: usize) -> Option<i32> {
    it.nth(n)
}
```

Current nightly:
```llvmir
define { i32, i32 } `@array_intoiter_nth(%"core::array::iter::IntoIter<i32,` 100_usize>"* noalias nocapture align 8 dereferenceable(416) %it, i64 %n) unnamed_addr #0 personality i32 (i32, i32, i64, %"unwind::libunwind::_Unwind_Exception"*, %"unwind::libunwind::_Unwind_Context"*)* `@rust_eh_personality` !dbg !6 {
start:
  %_3.i.i.i4.i.i = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 0, i32 0
  %_4.i.i.i5.i.i = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 0, i32 1
  %_4.i.i.i.i.i.i = load i64, i64* %_4.i.i.i5.i.i, align 8, !alias.scope !10
  %.not.i.i = icmp eq i64 %n, 0, !dbg !15
  %_3.i.i.i.i.pre.i = load i64, i64* %_3.i.i.i4.i.i, align 8, !dbg !40, !alias.scope !41
  br i1 %.not.i.i, label %bb4.i, label %bb4.preheader.i.i, !dbg !42

bb4.preheader.i.i:                                ; preds = %start
  %umax.i = tail call i64 `@llvm.umax.i64(i64` %_3.i.i.i.i.pre.i, i64 %_4.i.i.i.i.i.i) #3, !dbg !43
  %0 = sub i64 %umax.i, %_3.i.i.i.i.pre.i, !dbg !43
  br label %bb4.i.i, !dbg !43

bb4.i.i:                                          ; preds = %bb3.i.i.i.i, %bb4.preheader.i.i
  %_3.i.i.i.i.i.i = phi i64 [ %2, %bb3.i.i.i.i ], [ %_3.i.i.i.i.pre.i, %bb4.preheader.i.i ], !dbg !52
  %iter.sroa.0.016.i.i = phi i64 [ %1, %bb3.i.i.i.i ], [ 0, %bb4.preheader.i.i ]
  %1 = add nuw i64 %iter.sroa.0.016.i.i, 1, !dbg !54
  %exitcond.not.i = icmp eq i64 %iter.sroa.0.016.i.i, %0, !dbg !52
  br i1 %exitcond.not.i, label %core::iter::traits::iterator::Iterator::nth.exit, label %bb3.i.i.i.i, !dbg !43

bb3.i.i.i.i:                                      ; preds = %bb4.i.i
  %2 = add nuw i64 %_3.i.i.i.i.i.i, 1, !dbg !63
  store i64 %2, i64* %_3.i.i.i4.i.i, align 8, !dbg !66, !alias.scope !75
  %exitcond.not.i.i = icmp eq i64 %1, %n, !dbg !15
  br i1 %exitcond.not.i.i, label %bb4.i, label %bb4.i.i, !dbg !42

bb4.i:                                            ; preds = %bb3.i.i.i.i, %start
  %_3.i.i.i.i.i = phi i64 [ %_3.i.i.i.i.pre.i, %start ], [ %2, %bb3.i.i.i.i ], !dbg !84
  %3 = icmp ult i64 %_3.i.i.i.i.i, %_4.i.i.i.i.i.i, !dbg !84
  br i1 %3, label %bb3.i.i.i, label %core::iter::traits::iterator::Iterator::nth.exit, !dbg !89

bb3.i.i.i:                                        ; preds = %bb4.i
  %4 = add nuw i64 %_3.i.i.i.i.i, 1, !dbg !90
  store i64 %4, i64* %_3.i.i.i4.i.i, align 8, !dbg !93, !alias.scope !96
  %5 = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 1, i64 %_3.i.i.i.i.i, !dbg !105
  %6 = load i32, i32* %5, align 4, !dbg !131, !alias.scope !141, !noalias !144
  br label %core::iter::traits::iterator::Iterator::nth.exit, !dbg !149

core::iter::traits::iterator::Iterator::nth.exit: ; preds = %bb4.i.i, %bb4.i, %bb3.i.i.i
  %.sroa.3.0.i = phi i32 [ %6, %bb3.i.i.i ], [ undef, %bb4.i ], [ undef, %bb4.i.i ], !dbg !40
  %.sroa.0.0.i = phi i32 [ 1, %bb3.i.i.i ], [ 0, %bb4.i ], [ 0, %bb4.i.i ], !dbg !40
  %7 = insertvalue { i32, i32 } undef, i32 %.sroa.0.0.i, 0, !dbg !150
  %8 = insertvalue { i32, i32 } %7, i32 %.sroa.3.0.i, 1, !dbg !150
  ret { i32, i32 } %8, !dbg !151
}
```

With this PR:
```llvmir
define { i32, i32 } `@array_intoiter_nth(%"core::array::iter::IntoIter<i32,` 100_usize>"* noalias nocapture align 8 dereferenceable(416) %it, i64 %n) unnamed_addr #0 personality i32 (...)* `@__CxxFrameHandler3` {
start:
  %0 = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 0, i32 1
  %_2.i.i.i.i = load i64, i64* %0, align 8, !alias.scope !6, !noalias !13
  %1 = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 0, i32 0
  %_3.i.i.i.i = load i64, i64* %1, align 8, !alias.scope !16
  %2 = sub i64 %_2.i.i.i.i, %_3.i.i.i.i
  %3 = icmp ult i64 %2, %n
  %.0.sroa.speculated.i.i.i.i.i = select i1 %3, i64 %2, i64 %n
  %_10.i.i = add i64 %.0.sroa.speculated.i.i.i.i.i, %_3.i.i.i.i
  store i64 %_10.i.i, i64* %1, align 8, !alias.scope !16
  %.not.i = xor i1 %3, true
  %4 = icmp ult i64 %_10.i.i, %_2.i.i.i.i
  %or.cond.i = select i1 %.not.i, i1 %4, i1 false
  br i1 %or.cond.i, label %bb3.i.i.i, label %_ZN4core4iter6traits8iterator8Iterator3nth17hcbc727011e9e2a3bE.exit

bb3.i.i.i:                                        ; preds = %start
  %5 = add nuw i64 %_10.i.i, 1
  store i64 %5, i64* %1, align 8, !alias.scope !17
  %6 = getelementptr inbounds %"core::array::iter::IntoIter<i32, 100_usize>", %"core::array::iter::IntoIter<i32, 100_usize>"* %it, i64 0, i32 1, i64 %_10.i.i
  %7 = load i32, i32* %6, align 4, !alias.scope !26, !noalias !29
  br label %_ZN4core4iter6traits8iterator8Iterator3nth17hcbc727011e9e2a3bE.exit

_ZN4core4iter6traits8iterator8Iterator3nth17hcbc727011e9e2a3bE.exit: ; preds = %start, %bb3.i.i.i
  %.sroa.3.0.i = phi i32 [ undef, %start ], [ %7, %bb3.i.i.i ]
  %.sroa.0.0.i = phi i32 [ 0, %start ], [ 1, %bb3.i.i.i ]
  %8 = insertvalue { i32, i32 } undef, i32 %.sroa.0.0.i, 0
  %9 = insertvalue { i32, i32 } %8, i32 %.sroa.3.0.i, 1
  ret { i32, i32 } %9
}
```
</details>
2021-12-08 07:54:30 +00:00
Scott McMurray
9b86c5998c s/from_raw_parts/new_unchecked/ 2021-12-06 22:59:04 -08:00
Scott McMurray
0b90204bc8 Add tracking issue; make empty const too (unstably) 2021-12-06 01:12:59 -08:00
Scott McMurray
ef7c833c20 Move the doc test to edition2021 2021-12-06 00:58:40 -08:00
Scott McMurray
a30f96311a Add array::IntoIter::{empty, from_raw_parts}
`array::IntoIter` has a bunch of really handy logic for dealing with partial arrays, but it's currently hamstrung by only being creatable from a fully-initialized array.

This PR adds two new constructors:
- a safe & const `empty`, since `[].into_iter()` gives `<T, 0>`, not `<T, N>`.
- an unsafe `from_raw_parts`, to allow experimentation with new uses.

(Slice & vec iterators don't need `from_raw_parts` because you `from_raw_parts` the slice or vec instead, but there's no useful way to made a `<[T; N]>::from_raw_parts`, so I think this is a reasonable place to have one.)
2021-12-06 00:58:40 -08:00
Mara Bos
27d39357b7 Update array::IntoIter::new deprecation version. 2021-12-04 19:42:37 +01:00
Mara Bos
b34cf1a9e1 Swap body of array::IntoIter::new and IntoIterator::new. 2021-12-04 19:15:47 +01:00
Mara Bos
911ee9403e Deprecate array::IntoIter::new. 2021-12-04 19:15:44 +01:00
Mara Bos
16711fe076
Update stabilization version of try_from_mut_slice_to_array 2021-12-04 17:17:12 +01:00
woppopo
8f68bdc380 Make Borrow and BorrowMut impls const 2021-12-04 21:57:39 +09:00
Scott McMurray
eb846dbaca Override Iterator::advance(_back)_by for array::IntoIter
Because I happened to notice that `nth` is currently getting codegen'd as a loop even for `Copy` types: <https://rust.godbolt.org/z/fPqv7Gvs7>
2021-12-03 21:36:51 -08:00
Scott McMurray
b96b9b4093 Make array::{try_from_fn, try_map} and Iterator::try_find generic over Try
Fixes 85115

This only updates unstable functions.

`array::try_map` didn't actually exist before, despite the tracking issue 79711 still being open from the old PR 79713.
2021-12-02 11:23:50 -08:00
Mark Rousskov
b221c877e8 Apply cfg-bootstrap switch 2021-11-30 10:51:42 -05:00
Linda_pp
ac083c6b45
Reborrow mut slice instead of converting it with as_ref
Co-authored-by: Noah Lev <camelidcamel@gmail.com>
2021-11-21 11:01:31 +09:00
Linda_pp
66e0523d09
Update version in stable attribute
Co-authored-by: Joshua Nelson <github@jyn.dev>
2021-11-20 23:35:28 +09:00
rhysd
72b411fd89 Implement TryFrom<&'_ mut [T]> for [T; N] 2021-11-20 23:05:08 +09:00
Scott McMurray
5b115fcb68 Moar #[inline] 2021-11-10 11:57:14 -08:00
Scott McMurray
cc7d8014d7 Specialize array cloning for Copy types
Because after PR 86041, the optimizer no longer load-merges at the LLVM IR level, which might be part of the perf loss.  (I'll run perf and see if this makes a difference.)

Also I added a codegen test so this hopefully won't regress in future -- it passes on stable and with my change here, but not on the 2021-11-09 nightly.
2021-11-09 21:43:20 -08:00
bstrie
61b1394ac7 Attempt to address perf regressions with #[inline] 2021-11-08 15:51:56 -05:00
bstrie
ce1143e94d impl Copy/Clone for arrays in std, not in compiler 2021-11-08 13:11:58 -05:00
Matthias Krüger
c16ee19dd4
Rollup merge of #90162 - WaffleLapkin:const_array_slice_from_ref_mut, r=oli-obk
Mark `{array, slice}::{from_ref, from_mut}` as const fn

This PR marks the following APIs as `const`:
```rust
// core::array
pub const fn from_ref<T>(s: &T) -> &[T; 1];
pub const fn from_mut<T>(s: &mut T) -> &mut [T; 1];

// core::slice
pub const fn from_ref<T>(s: &T) -> &[T];
pub const fn from_mut<T>(s: &mut T) -> &mut [T];
```

Note that `from_ref` methods require `const_raw_ptr_deref` feature (which seems totally fine, since it's being stabilized, see #89551), `from_mut` methods require `const_mut_refs` (which seems fine too since this PR marks `from_mut` functions as const unstable).

r? ````@oli-obk````
2021-10-24 15:48:44 +02:00
Maybe Waffle
27d6961134 Fill tracking issue for const_slice_from_ref and const_array_from_ref 2021-10-23 20:59:15 +03:00
Maybe Waffle
a288bf6afb Mark {array,slice}::{from_ref,from_mut} as const fn 2021-10-22 14:53:30 +03:00
Jethro Beekman
4a439769ec Implement split_array and split_array_mut 2021-10-22 09:58:24 +02:00
woppopo
7936ecff48 Make more From impls const 2021-10-18 19:19:28 +09:00
The8472
f1c588f1ef use fold instead of try_fold now that .by_ref().next() has been inlined 2021-10-11 23:36:04 +02:00
Guillaume Gomez
86bf3ce859
Rollup merge of #75644 - c410-f3r:array, r=yaahc
Add 'core::array::from_fn' and 'core::array::try_from_fn'

These auxiliary methods fill uninitialized arrays in a safe way and are particularly useful for elements that don't implement `Default`.

```rust
// Foo doesn't implement Default
struct Foo(usize);

let _array = core::array::from_fn::<_, _, 2>(|idx| Foo(idx));
```

Different from `FromIterator`, it is guaranteed that the array will be fully filled and no error regarding uninitialized state will be throw. In certain scenarios, however, the creation of an **element** can fail and that is why the `try_from_fn` function is also provided.

```rust
#[derive(Debug, PartialEq)]
enum SomeError {
    Foo,
}

let array = core::array::try_from_fn(|i| Ok::<_, SomeError>(i));
assert_eq!(array, Ok([0, 1, 2, 3, 4]));

let another_array = core::array::try_from_fn(|_| Err(SomeError::Foo));
assert_eq!(another_array, Err(SomeError::Foo));
 ```
2021-10-09 17:08:38 +02:00
Manish Goregaokar
70d82e0a6e
Rollup merge of #88353 - jhpratt:stabilize-array-as-ref, r=joshtriplett
Partially stabilize `array_methods`

This stabilizes `<[T; N]>::as_slice` and `<[T; N]>::as_mut_slice`, which is forms part of the `array_methods` feature: #76118.

This also makes `<[T; N]>::as_slice` const due to its trivial nature.
2021-10-03 23:13:19 -07:00
Frank Steffahn
355c7e9415 Remove an unnecessary use of unwrap_unchecked
also add a new SAFETY comment and simplify/remove a closure
2021-09-30 10:09:03 -03:00
Frank Steffahn
325025e74b Improve previous commit 2021-09-30 13:53:24 +02:00
Caio
fdccc7dad9 Use reference instead of raw pointer 2021-09-30 08:40:05 -03:00
Caio
4be574e6c9 Add 'core::array::from_fn' and 'core::array::try_from_fn' 2021-09-30 07:49:32 -03:00
Aman Arora
994793faab PR fixup 2021-09-22 05:17:30 -04:00
Aman Arora
099a34cd95 2229: Annotate stdlib with insignficant dtors 2021-09-21 04:06:00 -04:00
bors
0961e688fd Auto merge of #88469 - patrick-gu:master, r=dtolnay
Add links in docs for some primitive types

This pull request adds additional links in existing documentation of some of the primitive types.

Where items are linked only once, I have used the `[link](destination)` format. For items in `std`, I have linked directly to the HTML, since although the primitives are in `core`, they are not displayed on `core` documentation. I was unsure of what length I should keep lines of documentation to, so I tried to keep them within reason.

Additionally, I have avoided excessively linking to keywords like `self` when they are not relevant to the documentation. I can add these links if it would be an improvement.

I hope this can improve Rust. Please let me know if there's anything I did wrong!
2021-09-05 01:56:25 +00:00
patrick-gu
911d0cbe80 Remove excessive linking 2021-09-03 17:09:37 -07:00
Mara Bos
5ea45f35c0 Update outdated docs of array::IntoIter::new. 2021-09-03 11:24:52 +02:00
ibraheemdev
b99038f478 use unwrap_unchecked where possible 2021-08-30 16:13:56 -04:00
patrick-gu
5719d22125 Add links in docs for some primitive types 2021-08-29 13:48:21 -07:00
Jacob Pratt
905c2ba5f8
Partially stabilize array_methods
This also makes `<[T; N]>::as_slice` const due to its trivial nature.
2021-08-26 05:27:39 -04:00
Frank Steffahn
be9d2699ca Fix more “a”/“an” typos 2021-08-22 16:35:29 +02:00
Deadbeef
b5afa6807b
Constified Default implementations
The libs-api team agrees to allow const_trait_impl to appear in the
standard library as long as stable code cannot be broken (they are
properly gated) this means if the compiler teams thinks it's okay, then
it's okay.

My priority on constifying would be:

	1. Non-generic impls (e.g. Default) or generic impls with no
	   bounds
	2. Generic functions with bounds (that use const impls)
	3. Generic impls with bounds
	4. Impls for traits with associated types

For people opening constification PRs: please cc me and/or oli-obk.
2021-08-17 07:15:54 +00:00
Pietro Albini
24f9de5a44 bump bootstrap compiler to 1.55 2021-08-01 11:19:24 -04:00