@@ -163,21 +163,31 @@ where
163
163
/// Converts an array to a SIMD vector.
164
164
pub const fn from_array ( array : [ T ; LANES ] ) -> Self {
165
165
// SAFETY: Transmuting between `Simd<T, LANES>` and `[T; LANES]`
166
- // is always valid.
166
+ // is always valid. We need to use `read_unaligned` here, since
167
+ // the array may have a lower alignment than the vector.
168
+ //
169
+ // FIXME: We currently use a pointer read instead of `transmute_copy` because
170
+ // it results in better codegen with optimizations disabled, but we should
171
+ // probably just use `transmute` once that works on const generic types.
167
172
//
168
173
// NOTE: This deliberately doesn't just use `Self(array)`, see the comment
169
174
// on the struct definition for details.
170
- unsafe { core :: mem :: transmute_copy ( & array) }
175
+ unsafe { ( & array as * const [ T ; LANES ] as * const Self ) . read_unaligned ( ) }
171
176
}
172
177
173
178
/// Converts a SIMD vector to an array.
174
179
pub const fn to_array ( self ) -> [ T ; LANES ] {
175
180
// SAFETY: Transmuting between `Simd<T, LANES>` and `[T; LANES]`
176
- // is always valid.
181
+ // is always valid. No need to use `read_unaligned` here, since
182
+ // the vector never has a lower alignment than the array.
183
+ //
184
+ // FIXME: We currently use a pointer read instead of `transmute_copy` because
185
+ // it results in better codegen with optimizations disabled, but we should
186
+ // probably just use `transmute` once that works on const generic types.
177
187
//
178
188
// NOTE: This deliberately doesn't just use `self.0`, see the comment
179
189
// on the struct definition for details.
180
- unsafe { core :: mem :: transmute_copy ( & self ) }
190
+ unsafe { ( & self as * const Self as * const [ T ; LANES ] ) . read ( ) }
181
191
}
182
192
183
193
/// Converts a slice to a SIMD vector containing `slice[..LANES]`.
0 commit comments