Skip to content

Commit 351bec3

Browse files
committed
Don't require the user to enable the unsized features.
Rather than forcing the user to enable the unsized_fn_params and unsized_locals features, we condition those features tests with if the type is a scalable simd type.
1 parent 17a06d9 commit 351bec3

File tree

8 files changed

+96
-6
lines changed

8 files changed

+96
-6
lines changed

compiler/rustc_borrowck/src/type_check/mod.rs

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1349,7 +1349,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
13491349
}
13501350

13511351
self.check_rvalue(body, rv, location);
1352-
if !self.unsized_feature_enabled() {
1352+
if !(self.unsized_feature_enabled() || place_ty.is_scalable_simd()) {
13531353
let trait_ref = ty::TraitRef::from_lang_item(
13541354
tcx,
13551355
LangItem::Sized,
@@ -1857,7 +1857,9 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
18571857
if !self.unsized_feature_enabled() {
18581858
let span = local_decl.source_info.span;
18591859
let ty = local_decl.ty;
1860-
self.ensure_place_sized(ty, span);
1860+
if !ty.is_scalable_simd() {
1861+
self.ensure_place_sized(ty, span);
1862+
}
18611863
}
18621864
}
18631865

compiler/rustc_feature/src/unstable.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -620,8 +620,22 @@ declare_features! (
620620
/// Allows unnamed fields of struct and union type
621621
(incomplete, unnamed_fields, "1.74.0", Some(49804)),
622622
/// Allows unsized fn parameters.
623+
///
624+
/// Note: `repr_scalable` depends on this feature. Rather than forcing the developer to also
625+
/// enable this feature to use scalable SIMD, we have done a check along side this feature to
626+
/// check if the type is a scalable SIMD type. If this feature becomes stable, those checks
627+
/// should be safe to remove so we can just use this feature. The check has been done specific
628+
/// to the type rather than enabling this feature on their behalf to avoid enabling more unsized
629+
/// than is actually required for what they are using.
623630
(unstable, unsized_fn_params, "1.49.0", Some(48055)),
624631
/// Allows unsized rvalues at arguments and parameters.
632+
///
633+
/// Note: `repr_scalable` depends on this feature. Rather than forcing the developer to also
634+
/// enable this feature to use scalable SIMD, we have done a check along side this feature to
635+
/// check if the type is a scalable SIMD type. If this feature becomes stable, those checks
636+
/// should be safe to remove so we can just use this feature. The check has been done specific
637+
/// to the type rather than enabling this feature on their behalf to avoid enabling more unsized
638+
/// than is actually required for what they are using.
625639
(incomplete, unsized_locals, "1.30.0", Some(48055)),
626640
/// Allows unsized tuple coercion.
627641
(unstable, unsized_tuple_coercion, "1.20.0", Some(42877)),

compiler/rustc_hir_typeck/src/check.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ pub(super) fn check_fn<'a, 'tcx>(
8383
}
8484

8585
// Check that argument is Sized.
86-
if !params_can_be_unsized {
86+
if !(params_can_be_unsized || param_ty.is_scalable_simd()) {
8787
fcx.require_type_is_sized(
8888
param_ty,
8989
param.pat.span,

compiler/rustc_hir_typeck/src/expr.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -575,6 +575,11 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
575575
infer::BoundRegionConversionTime::FnCall,
576576
fn_sig.input(i),
577577
);
578+
579+
if input.is_scalable_simd() {
580+
continue;
581+
}
582+
578583
self.require_type_is_sized_deferred(
579584
input,
580585
span,

compiler/rustc_hir_typeck/src/gather_locals.rs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -144,7 +144,9 @@ impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> {
144144
let var_ty = self.assign(p.span, p.hir_id, None);
145145

146146
if let Some((ty_span, hir_id)) = self.outermost_fn_param_pat {
147-
if !self.fcx.tcx.features().unsized_fn_params {
147+
if !(self.fcx.tcx.features().unsized_fn_params
148+
|| self.fcx.tcx.features().repr_scalable)
149+
{
148150
self.fcx.require_type_is_sized(
149151
var_ty,
150152
p.span,
@@ -162,7 +164,9 @@ impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> {
162164
);
163165
}
164166
} else {
165-
if !self.fcx.tcx.features().unsized_locals {
167+
if !(self.fcx.tcx.features().unsized_locals
168+
|| self.fcx.tcx.features().repr_scalable)
169+
{
166170
self.fcx.require_type_is_sized(var_ty, p.span, traits::VariableType(p.hir_id));
167171
}
168172
}

compiler/rustc_hir_typeck/src/lib.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -212,7 +212,6 @@ fn typeck_with_fallback<'tcx>(
212212

213213
for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
214214
let ty = fcx.normalize(span, ty);
215-
// ScalableSIMD: Justify this.
216215
if !ty.is_scalable_simd() {
217216
fcx.require_type_is_sized(ty, span, code);
218217
}
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
#![allow(incomplete_features, internal_features, improper_ctypes)]
2+
#![feature(
3+
repr_simd,
4+
repr_scalable,
5+
simd_ffi,
6+
unsized_locals,
7+
unsized_fn_params,
8+
link_llvm_intrinsics
9+
)]
10+
11+
#[repr(simd, scalable(4))]
12+
#[allow(non_camel_case_types)]
13+
pub struct svint32_t {
14+
_ty: [i32],
15+
}
16+
17+
#[inline(never)]
18+
#[target_feature(enable = "sve")]
19+
pub unsafe fn svdup_n_s32(op: i32) -> svint32_t {
20+
extern "C" {
21+
#[cfg_attr(target_arch = "aarch64", link_name = "llvm.aarch64.sve.dup.x.nxv4i32")]
22+
fn _svdup_n_s32(op: i32) -> svint32_t;
23+
}
24+
unsafe { _svdup_n_s32(op) }
25+
}
26+
27+
#[inline]
28+
#[target_feature(enable = "sve,sve2")]
29+
pub unsafe fn svxar_n_s32<const IMM3: i32>(op1: svint32_t, op2: svint32_t) -> svint32_t {
30+
extern "C" {
31+
#[cfg_attr(target_arch = "aarch64", link_name = "llvm.aarch64.sve.xar.nxv4i32")]
32+
fn _svxar_n_s32(op1: svint32_t, op2: svint32_t, imm3: i32) -> svint32_t;
33+
}
34+
unsafe { _svxar_n_s32(op1, op2, IMM3) }
35+
}
36+
37+
#[inline(never)]
38+
fn run(f: impl Fn() -> ()) {
39+
f();
40+
}
41+
42+
fn main() {
43+
let a = svdup_n_s32(42);
44+
run(move || {
45+
svxar_n_s32::<2>(a, a); //~ ERROR E0277
46+
});
47+
}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
error[E0277]: the size for values of type `[i32]` cannot be known at compilation time
2+
--> $DIR/disallow-capture-closure.rs:45:26
3+
|
4+
LL | run(move || {
5+
| -- this closure captures all values by move
6+
LL | svxar_n_s32::<2>(a, a);
7+
| ^ doesn't have a size known at compile-time
8+
|
9+
= help: within `svint32_t`, the trait `Sized` is not implemented for `[i32]`, which is required by `svint32_t: Sized`
10+
note: required because it appears within the type `svint32_t`
11+
--> $DIR/disallow-capture-closure.rs:13:12
12+
|
13+
LL | pub struct svint32_t {
14+
| ^^^^^^^^^
15+
= note: all values captured by value by a closure must have a statically known size
16+
17+
error: aborting due to 1 previous error
18+
19+
For more information about this error, try `rustc --explain E0277`.

0 commit comments

Comments
 (0)