Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
int
Rust
提交
8e6d126b
R
Rust
项目概览
int
/
Rust
12 个月 前同步成功
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
R
Rust
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
8e6d126b
编写于
8月 25, 2021
作者:
E
Eduard-Mihai Burtescu
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
rustc_target: `TyAndLayout::field` should never error.
上级
87d1fb74
变更
10
隐藏空白更改
内联
并排
Showing
10 changed file
with
77 addition
and
77 deletion
+77
-77
compiler/rustc_codegen_cranelift/src/debuginfo/mod.rs
compiler/rustc_codegen_cranelift/src/debuginfo/mod.rs
+4
-6
compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
+2
-2
compiler/rustc_codegen_ssa/src/mir/block.rs
compiler/rustc_codegen_ssa/src/mir/block.rs
+2
-4
compiler/rustc_middle/src/ty/layout.rs
compiler/rustc_middle/src/ty/layout.rs
+53
-48
compiler/rustc_mir/src/interpret/cast.rs
compiler/rustc_mir/src/interpret/cast.rs
+1
-1
compiler/rustc_mir/src/interpret/eval_context.rs
compiler/rustc_mir/src/interpret/eval_context.rs
+2
-2
compiler/rustc_mir/src/interpret/operand.rs
compiler/rustc_mir/src/interpret/operand.rs
+1
-1
compiler/rustc_mir/src/interpret/place.rs
compiler/rustc_mir/src/interpret/place.rs
+3
-3
compiler/rustc_mir/src/interpret/terminator.rs
compiler/rustc_mir/src/interpret/terminator.rs
+1
-1
compiler/rustc_target/src/abi/mod.rs
compiler/rustc_target/src/abi/mod.rs
+8
-9
未找到文件。
compiler/rustc_codegen_cranelift/src/debuginfo/mod.rs
浏览文件 @
8e6d126b
...
...
@@ -160,12 +160,10 @@ fn dwarf_ty(&mut self, ty: Ty<'tcx>) -> UnitEntryId {
for
(
field_idx
,
field_def
)
in
variant
.fields
.iter
()
.enumerate
()
{
let
field_offset
=
layout
.fields
.offset
(
field_idx
);
let
field_layout
=
layout
.field
(
&
layout
::
LayoutCx
{
tcx
:
self
.tcx
,
param_env
:
ParamEnv
::
reveal_all
()
},
field_idx
,
)
.unwrap
();
let
field_layout
=
layout
.field
(
&
layout
::
LayoutCx
{
tcx
:
self
.tcx
,
param_env
:
ParamEnv
::
reveal_all
()
},
field_idx
,
);
let
field_type
=
self
.dwarf_ty
(
field_layout
.ty
);
...
...
compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
浏览文件 @
8e6d126b
...
...
@@ -789,7 +789,7 @@ fn swap(bcx: &mut FunctionBuilder<'_>, v: Value) -> Value {
return
;
}
if
intrinsic
==
sym
::
assert_zero_valid
&&
!
layout
.might_permit_raw_init
(
fx
,
/*zero:*/
true
)
.unwrap
()
{
if
intrinsic
==
sym
::
assert_zero_valid
&&
!
layout
.might_permit_raw_init
(
fx
,
/*zero:*/
true
)
{
with_no_trimmed_paths
(||
crate
::
base
::
codegen_panic
(
fx
,
&
format!
(
"attempted to zero-initialize type `{}`, which is invalid"
,
T
),
...
...
@@ -798,7 +798,7 @@ fn swap(bcx: &mut FunctionBuilder<'_>, v: Value) -> Value {
return
;
}
if
intrinsic
==
sym
::
assert_uninit_valid
&&
!
layout
.might_permit_raw_init
(
fx
,
/*zero:*/
false
)
.unwrap
()
{
if
intrinsic
==
sym
::
assert_uninit_valid
&&
!
layout
.might_permit_raw_init
(
fx
,
/*zero:*/
false
)
{
with_no_trimmed_paths
(||
crate
::
base
::
codegen_panic
(
fx
,
&
format!
(
"attempted to leave type `{}` uninitialized, which is invalid"
,
T
),
...
...
compiler/rustc_codegen_ssa/src/mir/block.rs
浏览文件 @
8e6d126b
...
...
@@ -472,10 +472,8 @@ enum AssertIntrinsic {
let
layout
=
bx
.layout_of
(
ty
);
let
do_panic
=
match
intrinsic
{
Inhabited
=>
layout
.abi
.is_uninhabited
(),
// We unwrap as the error type is `!`.
ZeroValid
=>
!
layout
.might_permit_raw_init
(
bx
,
/*zero:*/
true
)
.unwrap
(),
// We unwrap as the error type is `!`.
UninitValid
=>
!
layout
.might_permit_raw_init
(
bx
,
/*zero:*/
false
)
.unwrap
(),
ZeroValid
=>
!
layout
.might_permit_raw_init
(
bx
,
/*zero:*/
true
),
UninitValid
=>
!
layout
.might_permit_raw_init
(
bx
,
/*zero:*/
false
),
};
if
do_panic
{
let
msg_str
=
with_no_trimmed_paths
(||
{
...
...
compiler/rustc_middle/src/ty/layout.rs
浏览文件 @
8e6d126b
...
...
@@ -1788,22 +1788,18 @@ fn record_layout_for_printing_outlined(&self, layout: TyAndLayout<'tcx>) {
let
field_info
:
Vec
<
_
>
=
flds
.iter
()
.enumerate
()
.map
(|(
i
,
&
name
)|
match
layout
.field
(
self
,
i
)
{
Err
(
err
)
=>
{
bug!
(
"no layout found for field {}: `{:?}`"
,
name
,
err
);
.map
(|(
i
,
&
name
)|
{
let
field_layout
=
layout
.field
(
self
,
i
);
let
offset
=
layout
.fields
.offset
(
i
);
let
field_end
=
offset
+
field_layout
.size
;
if
min_size
<
field_end
{
min_size
=
field_end
;
}
Ok
(
field_layout
)
=>
{
let
offset
=
layout
.fields
.offset
(
i
);
let
field_end
=
offset
+
field_layout
.size
;
if
min_size
<
field_end
{
min_size
=
field_end
;
}
FieldInfo
{
name
:
name
.to_string
(),
offset
:
offset
.bytes
(),
size
:
field_layout
.size
.bytes
(),
align
:
field_layout
.align.abi
.bytes
(),
}
FieldInfo
{
name
:
name
.to_string
(),
offset
:
offset
.bytes
(),
size
:
field_layout
.size
.bytes
(),
align
:
field_layout
.align.abi
.bytes
(),
}
})
.collect
();
...
...
@@ -2146,30 +2142,24 @@ fn ty_and_layout_for_variant(
TyAndLayout
{
ty
:
this
.ty
,
layout
}
}
fn
ty_and_layout_field
(
this
:
TyAndLayout
<
'tcx
>
,
cx
:
&
C
,
i
:
usize
)
->
C
::
TyAndLayout
{
enum
TyMaybeWithLayout
<
'tcx
,
C
:
LayoutOf
<
'tcx
>
>
{
Ty
(
C
::
Ty
),
TyAndLayout
(
C
::
TyAndLayout
),
fn
ty_and_layout_field
(
this
:
TyAndLayout
<
'tcx
>
,
cx
:
&
C
,
i
:
usize
)
->
TyAndLayout
<
'tcx
>
{
enum
TyMaybeWithLayout
<
'tcx
>
{
Ty
(
Ty
<
'tcx
>
),
TyAndLayout
(
TyAndLayout
<
'tcx
>
),
}
fn
ty_and_layout_kind
<
C
:
LayoutOf
<
'tcx
,
Ty
=
Ty
<
'tcx
>>
+
HasTyCtxt
<
'tcx
>
+
HasParamEnv
<
'tcx
>
,
>
(
fn
field_ty_or_layout
(
this
:
TyAndLayout
<
'tcx
>
,
cx
:
&
C
,
cx
:
&
(
impl
HasTyCtxt
<
'tcx
>
+
HasParamEnv
<
'tcx
>
)
,
i
:
usize
,
ty
:
C
::
Ty
,
)
->
TyMaybeWithLayout
<
'tcx
,
C
>
{
)
->
TyMaybeWithLayout
<
'tcx
>
{
let
tcx
=
cx
.tcx
();
let
tag_layout
=
|
tag
:
&
Scalar
|
->
C
::
TyAndLayout
{
let
tag_layout
=
|
tag
:
&
Scalar
|
->
TyAndLayout
<
'tcx
>
{
let
layout
=
Layout
::
scalar
(
cx
,
tag
.clone
());
MaybeResult
::
from
(
Ok
(
TyAndLayout
{
layout
:
tcx
.intern_layout
(
layout
),
ty
:
tag
.value
.to_ty
(
tcx
),
}))
TyAndLayout
{
layout
:
tcx
.intern_layout
(
layout
),
ty
:
tag
.value
.to_ty
(
tcx
)
}
};
match
*
ty
.kind
()
{
match
*
t
his
.t
y
.kind
()
{
ty
::
Bool
|
ty
::
Char
|
ty
::
Int
(
_
)
...
...
@@ -2180,7 +2170,7 @@ fn ty_and_layout_kind<
|
ty
::
FnDef
(
..
)
|
ty
::
GeneratorWitness
(
..
)
|
ty
::
Foreign
(
..
)
|
ty
::
Dynamic
(
..
)
=>
bug!
(
"TyAndLayout::field
_type
({:?}): not applicable"
,
this
),
|
ty
::
Dynamic
(
..
)
=>
bug!
(
"TyAndLayout::field({:?}): not applicable"
,
this
),
// Potentially-fat pointers.
ty
::
Ref
(
_
,
pointee
,
_
)
|
ty
::
RawPtr
(
ty
::
TypeAndMut
{
ty
:
pointee
,
..
})
=>
{
...
...
@@ -2192,17 +2182,19 @@ fn ty_and_layout_kind<
// as the `Abi` or `FieldsShape` is checked by users.
if
i
==
0
{
let
nil
=
tcx
.mk_unit
();
let
ptr_ty
=
if
ty
.is_unsafe_ptr
()
{
let
unit_ptr_ty
=
if
this
.
ty
.is_unsafe_ptr
()
{
tcx
.mk_mut_ptr
(
nil
)
}
else
{
tcx
.mk_mut_ref
(
tcx
.lifetimes.re_static
,
nil
)
};
return
TyMaybeWithLayout
::
TyAndLayout
(
MaybeResult
::
from
(
cx
.layout_of
(
ptr_ty
)
.to_result
()
.map
(|
mut
ptr_layout
|
{
ptr_layout
.ty
=
ty
;
ptr_layout
}),
));
// NOTE(eddyb) using an empty `ParamEnv`, and `unwrap`-ing
// the `Result` should always work because the type is
// always either `*mut ()` or `&'static mut ()`.
return
TyMaybeWithLayout
::
TyAndLayout
(
TyAndLayout
{
ty
:
this
.ty
,
..
tcx
.layout_of
(
ty
::
ParamEnv
::
reveal_all
()
.and
(
unit_ptr_ty
))
.unwrap
()
});
}
match
tcx
.struct_tail_erasing_lifetimes
(
pointee
,
cx
.param_env
())
.kind
()
{
...
...
@@ -2226,7 +2218,7 @@ fn ty_and_layout_kind<
])
*/
}
_
=>
bug!
(
"TyAndLayout::field
_type
({:?}): not applicable"
,
this
),
_
=>
bug!
(
"TyAndLayout::field({:?}): not applicable"
,
this
),
}
}
...
...
@@ -2235,9 +2227,11 @@ fn ty_and_layout_kind<
ty
::
Str
=>
TyMaybeWithLayout
::
Ty
(
tcx
.types.u8
),
// Tuples, generators and closures.
ty
::
Closure
(
_
,
ref
substs
)
=>
{
ty_and_layout_kind
(
this
,
cx
,
i
,
substs
.as_closure
()
.tupled_upvars_ty
())
}
ty
::
Closure
(
_
,
ref
substs
)
=>
field_ty_or_layout
(
TyAndLayout
{
ty
:
substs
.as_closure
()
.tupled_upvars_ty
(),
..
this
},
cx
,
i
,
),
ty
::
Generator
(
def_id
,
ref
substs
,
_
)
=>
match
this
.variants
{
Variants
::
Single
{
index
}
=>
TyMaybeWithLayout
::
Ty
(
...
...
@@ -2280,14 +2274,25 @@ fn ty_and_layout_kind<
|
ty
::
Opaque
(
..
)
|
ty
::
Param
(
_
)
|
ty
::
Infer
(
_
)
|
ty
::
Error
(
_
)
=>
bug!
(
"TyAndLayout::field
_type
: unexpected type `{}`"
,
this
.ty
),
|
ty
::
Error
(
_
)
=>
bug!
(
"TyAndLayout::field: unexpected type `{}`"
,
this
.ty
),
}
}
cx
.layout_of
(
match
ty_and_layout_kind
(
this
,
cx
,
i
,
this
.ty
)
{
TyMaybeWithLayout
::
Ty
(
result
)
=>
result
,
TyMaybeWithLayout
::
TyAndLayout
(
result
)
=>
return
result
,
})
match
field_ty_or_layout
(
this
,
cx
,
i
)
{
TyMaybeWithLayout
::
Ty
(
field_ty
)
=>
{
cx
.tcx
()
.layout_of
(
cx
.param_env
()
.and
(
field_ty
))
.unwrap_or_else
(|
e
|
{
bug!
(
"failed to get layout for `{}`: {},
\n
\
despite it being a field (#{}) of an existing layout: {:#?}"
,
field_ty
,
e
,
i
,
this
)
})
}
TyMaybeWithLayout
::
TyAndLayout
(
field_layout
)
=>
field_layout
,
}
}
fn
ty_and_layout_pointee_info_at
(
...
...
compiler/rustc_mir/src/interpret/cast.rs
浏览文件 @
8e6d126b
...
...
@@ -340,7 +340,7 @@ fn unsize_into(
// Example: `Arc<T>` -> `Arc<Trait>`
// here we need to increase the size of every &T thin ptr field to a fat ptr
for
i
in
0
..
src
.layout.fields
.count
()
{
let
cast_ty_field
=
cast_ty
.field
(
self
,
i
)
?
;
let
cast_ty_field
=
cast_ty
.field
(
self
,
i
);
if
cast_ty_field
.is_zst
()
{
continue
;
}
...
...
compiler/rustc_mir/src/interpret/eval_context.rs
浏览文件 @
8e6d126b
...
...
@@ -592,7 +592,7 @@ pub(super) fn size_and_align_of(
// Recurse to get the size of the dynamically sized field (must be
// the last field). Can't have foreign types here, how would we
// adjust alignment and size for them?
let
field
=
layout
.field
(
self
,
layout
.fields
.count
()
-
1
)
?
;
let
field
=
layout
.field
(
self
,
layout
.fields
.count
()
-
1
);
let
(
unsized_size
,
unsized_align
)
=
match
self
.size_and_align_of
(
metadata
,
&
field
)
?
{
Some
(
size_and_align
)
=>
size_and_align
,
...
...
@@ -645,7 +645,7 @@ pub(super) fn size_and_align_of(
ty
::
Slice
(
_
)
|
ty
::
Str
=>
{
let
len
=
metadata
.unwrap_meta
()
.to_machine_usize
(
self
)
?
;
let
elem
=
layout
.field
(
self
,
0
)
?
;
let
elem
=
layout
.field
(
self
,
0
);
// Make sure the slice is not too big.
let
size
=
elem
.size
.checked_mul
(
len
,
self
)
.ok_or_else
(||
{
...
...
compiler/rustc_mir/src/interpret/operand.rs
浏览文件 @
8e6d126b
...
...
@@ -364,7 +364,7 @@ pub fn operand_field(
Err
(
value
)
=>
value
,
};
let
field_layout
=
op
.layout
.field
(
self
,
field
)
?
;
let
field_layout
=
op
.layout
.field
(
self
,
field
);
if
field_layout
.is_zst
()
{
let
immediate
=
Scalar
::
ZST
.into
();
return
Ok
(
OpTy
{
op
:
Operand
::
Immediate
(
immediate
),
layout
:
field_layout
});
...
...
compiler/rustc_mir/src/interpret/place.rs
浏览文件 @
8e6d126b
...
...
@@ -355,7 +355,7 @@ pub fn mplace_field(
field
:
usize
,
)
->
InterpResult
<
'tcx
,
MPlaceTy
<
'tcx
,
M
::
PointerTag
>>
{
let
offset
=
base
.layout.fields
.offset
(
field
);
let
field_layout
=
base
.layout
.field
(
self
,
field
)
?
;
let
field_layout
=
base
.layout
.field
(
self
,
field
);
// Offset may need adjustment for unsized fields.
let
(
meta
,
offset
)
=
if
field_layout
.is_unsized
()
{
...
...
@@ -405,7 +405,7 @@ pub fn mplace_index(
}
let
offset
=
stride
*
index
;
// `Size` multiplication
// All fields have the same layout.
let
field_layout
=
base
.layout
.field
(
self
,
0
)
?
;
let
field_layout
=
base
.layout
.field
(
self
,
0
);
assert
!
(
!
field_layout
.is_unsized
());
base
.offset
(
offset
,
MemPlaceMeta
::
None
,
field_layout
,
self
)
...
...
@@ -430,7 +430,7 @@ pub(super) fn mplace_array_fields(
FieldsShape
::
Array
{
stride
,
..
}
=>
stride
,
_
=>
span_bug!
(
self
.cur_span
(),
"mplace_array_fields: expected an array layout"
),
};
let
layout
=
base
.layout
.field
(
self
,
0
)
?
;
let
layout
=
base
.layout
.field
(
self
,
0
);
let
dl
=
&
self
.tcx.data_layout
;
// `Size` multiplication
Ok
((
0
..
len
)
.map
(
move
|
i
|
base
.offset
(
stride
*
i
,
MemPlaceMeta
::
None
,
layout
,
dl
)))
...
...
compiler/rustc_mir/src/interpret/terminator.rs
浏览文件 @
8e6d126b
...
...
@@ -461,7 +461,7 @@ fn eval_fn_call(
// a thin pointer.
assert
!
(
receiver_place
.layout
.is_unsized
());
let
receiver_ptr_ty
=
self
.tcx
.mk_mut_ptr
(
receiver_place
.layout.ty
);
let
this_receiver_ptr
=
self
.layout_of
(
receiver_ptr_ty
)
?
.field
(
self
,
0
)
?
;
let
this_receiver_ptr
=
self
.layout_of
(
receiver_ptr_ty
)
?
.field
(
self
,
0
);
// Adjust receiver argument.
args
[
0
]
=
OpTy
::
from
(
ImmTy
::
from_immediate
(
Scalar
::
from_maybe_pointer
(
receiver_place
.ptr
,
self
)
.into
(),
...
...
compiler/rustc_target/src/abi/mod.rs
浏览文件 @
8e6d126b
...
...
@@ -1244,7 +1244,7 @@ fn ty_and_layout_for_variant(
cx
:
&
C
,
variant_index
:
VariantIdx
,
)
->
TyAndLayout
<
'a
,
Self
>
;
fn
ty_and_layout_field
(
this
:
TyAndLayout
<
'a
,
Self
>
,
cx
:
&
C
,
i
:
usize
)
->
C
::
TyAndLayout
;
fn
ty_and_layout_field
(
this
:
TyAndLayout
<
'a
,
Self
>
,
cx
:
&
C
,
i
:
usize
)
->
TyAndLayout
<
'a
,
Self
>
;
fn
ty_and_layout_pointee_info_at
(
this
:
TyAndLayout
<
'a
,
Self
>
,
cx
:
&
C
,
...
...
@@ -1261,7 +1261,7 @@ pub fn for_variant<C>(self, cx: &C, variant_index: VariantIdx) -> Self
Ty
::
ty_and_layout_for_variant
(
self
,
cx
,
variant_index
)
}
pub
fn
field
<
C
>
(
self
,
cx
:
&
C
,
i
:
usize
)
->
C
::
TyAndLayout
pub
fn
field
<
C
>
(
self
,
cx
:
&
C
,
i
:
usize
)
->
Self
where
Ty
:
TyAbiInterface
<
'a
,
C
>
,
C
:
LayoutOf
<
'a
,
Ty
=
Ty
>
,
...
...
@@ -1302,11 +1302,11 @@ pub fn is_zst(&self) -> bool {
/// FIXME: Once we removed all the conservatism, we could alternatively
/// create an all-0/all-undef constant and run the const value validator to see if
/// this is a valid value for the given type.
pub
fn
might_permit_raw_init
<
C
,
E
>
(
self
,
cx
:
&
C
,
zero
:
bool
)
->
Result
<
bool
,
E
>
pub
fn
might_permit_raw_init
<
C
>
(
self
,
cx
:
&
C
,
zero
:
bool
)
->
bool
where
Self
:
Copy
,
Ty
:
TyAbiInterface
<
'a
,
C
>
,
C
:
LayoutOf
<
'a
,
Ty
=
Ty
,
TyAndLayout
:
MaybeResult
<
Self
,
Error
=
E
>
>
+
HasDataLayout
,
C
:
LayoutOf
<
'a
,
Ty
=
Ty
>
+
HasDataLayout
,
{
let
scalar_allows_raw_init
=
move
|
s
:
&
Scalar
|
->
bool
{
if
zero
{
...
...
@@ -1331,7 +1331,7 @@ pub fn might_permit_raw_init<C, E>(self, cx: &C, zero: bool) -> Result<bool, E>
};
if
!
valid
{
// This is definitely not okay.
return
Ok
(
false
)
;
return
false
;
}
// If we have not found an error yet, we need to recursively descend into fields.
...
...
@@ -1342,16 +1342,15 @@ pub fn might_permit_raw_init<C, E>(self, cx: &C, zero: bool) -> Result<bool, E>
}
FieldsShape
::
Arbitrary
{
offsets
,
..
}
=>
{
for
idx
in
0
..
offsets
.len
()
{
let
field
=
self
.field
(
cx
,
idx
)
.to_result
()
?
;
if
!
field
.might_permit_raw_init
(
cx
,
zero
)
?
{
if
!
self
.field
(
cx
,
idx
)
.might_permit_raw_init
(
cx
,
zero
)
{
// We found a field that is unhappy with this kind of initialization.
return
Ok
(
false
)
;
return
false
;
}
}
}
}
// FIXME(#66151): For now, we are conservative and do not check `self.variants`.
Ok
(
true
)
true
}
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录