Skip to content

Commit 2d69817

Browse files
committed
Handle argument extension mode
1 parent b5ddb76 commit 2d69817

File tree

1 file changed

+35
-17
lines changed

1 file changed

+35
-17
lines changed

src/abi/pass_mode.rs

Lines changed: 35 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,10 @@
33
use crate::prelude::*;
44
use crate::value_and_place::assert_assignable;
55

6-
use cranelift_codegen::ir::ArgumentPurpose;
7-
use rustc_target::abi::call::{ArgAbi, CastTarget, PassMode, Reg, RegKind};
6+
use cranelift_codegen::ir::{ArgumentExtension, ArgumentPurpose};
7+
use rustc_target::abi::call::{
8+
ArgAbi, ArgAttributes, ArgExtension as RustcArgExtension, CastTarget, PassMode, Reg, RegKind,
9+
};
810
use smallvec::{smallvec, SmallVec};
911

1012
pub(super) trait ArgAbiExt<'tcx> {
@@ -27,6 +29,15 @@ fn reg_to_abi_param(reg: Reg) -> AbiParam {
2729
AbiParam::new(clif_ty)
2830
}
2931

32+
fn apply_arg_attrs_to_abi_param(mut param: AbiParam, arg_attrs: ArgAttributes) -> AbiParam {
33+
match arg_attrs.arg_ext {
34+
RustcArgExtension::None => {}
35+
RustcArgExtension::Zext => param.extension = ArgumentExtension::Uext,
36+
RustcArgExtension::Sext => param.extension = ArgumentExtension::Sext,
37+
}
38+
param
39+
}
40+
3041
fn cast_target_to_abi_params(cast: CastTarget) -> SmallVec<[AbiParam; 2]> {
3142
let (rest_count, rem_bytes) = if cast.rest.unit.size.bytes() == 0 {
3243
(0, 0)
@@ -82,55 +93,62 @@ fn cast_target_to_abi_params(cast: CastTarget) -> SmallVec<[AbiParam; 2]> {
8293
args
8394
}
8495

85-
// FIXME respect argument extension mode
86-
8796
impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> {
8897
fn get_abi_param(&self, tcx: TyCtxt<'tcx>) -> SmallVec<[AbiParam; 2]> {
8998
match self.mode {
9099
PassMode::Ignore => smallvec![],
91-
PassMode::Direct(_) => match &self.layout.abi {
100+
PassMode::Direct(attrs) => match &self.layout.abi {
92101
Abi::Scalar(scalar) => {
93-
smallvec![AbiParam::new(scalar_to_clif_type(tcx, scalar.clone()))]
102+
smallvec![apply_arg_attrs_to_abi_param(
103+
AbiParam::new(scalar_to_clif_type(tcx, scalar.clone())),
104+
attrs
105+
)]
94106
}
95107
Abi::Vector { .. } => {
96108
let vector_ty = crate::intrinsics::clif_vector_type(tcx, self.layout).unwrap();
97109
smallvec![AbiParam::new(vector_ty)]
98110
}
99111
_ => unreachable!("{:?}", self.layout.abi),
100112
},
101-
PassMode::Pair(_, _) => match &self.layout.abi {
113+
PassMode::Pair(attrs_a, attrs_b) => match &self.layout.abi {
102114
Abi::ScalarPair(a, b) => {
103115
let a = scalar_to_clif_type(tcx, a.clone());
104116
let b = scalar_to_clif_type(tcx, b.clone());
105-
smallvec![AbiParam::new(a), AbiParam::new(b)]
117+
smallvec![
118+
apply_arg_attrs_to_abi_param(AbiParam::new(a), attrs_a),
119+
apply_arg_attrs_to_abi_param(AbiParam::new(b), attrs_b),
120+
]
106121
}
107122
_ => unreachable!("{:?}", self.layout.abi),
108123
},
109124
PassMode::Cast(cast) => cast_target_to_abi_params(cast),
110125
PassMode::Indirect {
111-
attrs: _,
126+
attrs,
112127
extra_attrs: None,
113128
on_stack,
114129
} => {
115130
if on_stack {
116131
let size = u32::try_from(self.layout.size.bytes()).unwrap();
117-
smallvec![AbiParam::special(
118-
pointer_ty(tcx),
119-
ArgumentPurpose::StructArgument(size),
132+
smallvec![apply_arg_attrs_to_abi_param(
133+
AbiParam::special(pointer_ty(tcx), ArgumentPurpose::StructArgument(size),),
134+
attrs
120135
)]
121136
} else {
122-
smallvec![AbiParam::new(pointer_ty(tcx))]
137+
smallvec![apply_arg_attrs_to_abi_param(
138+
AbiParam::new(pointer_ty(tcx)),
139+
attrs
140+
)]
123141
}
124142
}
125143
PassMode::Indirect {
126-
attrs: _,
127-
extra_attrs: Some(_),
144+
attrs,
145+
extra_attrs: Some(extra_attrs),
128146
on_stack,
129147
} => {
130148
assert!(!on_stack);
131149
smallvec![
132-
AbiParam::new(pointer_ty(tcx)),
133-
AbiParam::new(pointer_ty(tcx)),
150+
apply_arg_attrs_to_abi_param(AbiParam::new(pointer_ty(tcx)), attrs),
151+
apply_arg_attrs_to_abi_param(AbiParam::new(pointer_ty(tcx)), extra_attrs),
134152
]
135153
}
136154
}

0 commit comments

Comments
 (0)