Skip to content

Commit 1192b93

Browse files
brooniewilldeacon
authored andcommitted
arm64/fp: Use a struct to pass data to fpsimd_bind_state_to_cpu()
For reasons that are unclear to this reader fpsimd_bind_state_to_cpu() populates the struct fpsimd_last_state_struct that it uses to store the active floating point state for KVM guests by passing an argument for each member of the structure. As the richness of the architecture increases this is resulting in a function with a rather large number of arguments which isn't ideal. Simplify the interface by using the struct directly as the single argument for the function, renaming it as we lift the definition into the header. This could be built on further to reduce the work we do adding storage for new FP state in various places but for now it just simplifies this one interface. Signed-off-by: Mark Brown <[email protected]> Reviewed-by: Catalin Marinas <[email protected]> Reviewed-by: Marc Zyngier <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Will Deacon <[email protected]>
1 parent 8c845e2 commit 1192b93

File tree

3 files changed

+32
-43
lines changed

3 files changed

+32
-43
lines changed

arch/arm64/include/asm/fpsimd.h

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -58,11 +58,18 @@ extern void fpsimd_restore_current_state(void);
5858
extern void fpsimd_update_current_state(struct user_fpsimd_state const *state);
5959
extern void fpsimd_kvm_prepare(void);
6060

61-
extern void fpsimd_bind_state_to_cpu(struct user_fpsimd_state *state,
62-
void *sve_state, unsigned int sve_vl,
63-
void *za_state, unsigned int sme_vl,
64-
u64 *svcr, enum fp_type *type,
65-
enum fp_type to_save);
61+
struct cpu_fp_state {
62+
struct user_fpsimd_state *st;
63+
void *sve_state;
64+
void *za_state;
65+
u64 *svcr;
66+
unsigned int sve_vl;
67+
unsigned int sme_vl;
68+
enum fp_type *fp_type;
69+
enum fp_type to_save;
70+
};
71+
72+
extern void fpsimd_bind_state_to_cpu(struct cpu_fp_state *fp_state);
6673

6774
extern void fpsimd_flush_task_state(struct task_struct *target);
6875
extern void fpsimd_save_and_flush_cpu_state(void);

arch/arm64/kernel/fpsimd.c

Lines changed: 6 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -118,18 +118,8 @@
118118
* returned from the 2nd syscall yet, TIF_FOREIGN_FPSTATE is still set so
119119
* whatever is in the FPSIMD registers is not saved to memory, but discarded.
120120
*/
121-
struct fpsimd_last_state_struct {
122-
struct user_fpsimd_state *st;
123-
void *sve_state;
124-
void *za_state;
125-
u64 *svcr;
126-
unsigned int sve_vl;
127-
unsigned int sme_vl;
128-
enum fp_type *fp_type;
129-
enum fp_type to_save;
130-
};
131121

132-
static DEFINE_PER_CPU(struct fpsimd_last_state_struct, fpsimd_last_state);
122+
static DEFINE_PER_CPU(struct cpu_fp_state, fpsimd_last_state);
133123

134124
__ro_after_init struct vl_info vl_info[ARM64_VEC_MAX] = {
135125
#ifdef CONFIG_ARM64_SVE
@@ -468,7 +458,7 @@ static void task_fpsimd_load(void)
468458
*/
469459
static void fpsimd_save(void)
470460
{
471-
struct fpsimd_last_state_struct const *last =
461+
struct cpu_fp_state const *last =
472462
this_cpu_ptr(&fpsimd_last_state);
473463
/* set by fpsimd_bind_task_to_cpu() or fpsimd_bind_state_to_cpu() */
474464
bool save_sve_regs = false;
@@ -1716,8 +1706,7 @@ void fpsimd_kvm_prepare(void)
17161706
*/
17171707
static void fpsimd_bind_task_to_cpu(void)
17181708
{
1719-
struct fpsimd_last_state_struct *last =
1720-
this_cpu_ptr(&fpsimd_last_state);
1709+
struct cpu_fp_state *last = this_cpu_ptr(&fpsimd_last_state);
17211710

17221711
WARN_ON(!system_supports_fpsimd());
17231712
last->st = &current->thread.uw.fpsimd_state;
@@ -1749,25 +1738,14 @@ static void fpsimd_bind_task_to_cpu(void)
17491738
}
17501739
}
17511740

1752-
void fpsimd_bind_state_to_cpu(struct user_fpsimd_state *st, void *sve_state,
1753-
unsigned int sve_vl, void *za_state,
1754-
unsigned int sme_vl, u64 *svcr,
1755-
enum fp_type *type, enum fp_type to_save)
1741+
void fpsimd_bind_state_to_cpu(struct cpu_fp_state *state)
17561742
{
1757-
struct fpsimd_last_state_struct *last =
1758-
this_cpu_ptr(&fpsimd_last_state);
1743+
struct cpu_fp_state *last = this_cpu_ptr(&fpsimd_last_state);
17591744

17601745
WARN_ON(!system_supports_fpsimd());
17611746
WARN_ON(!in_softirq() && !irqs_disabled());
17621747

1763-
last->st = st;
1764-
last->svcr = svcr;
1765-
last->sve_state = sve_state;
1766-
last->za_state = za_state;
1767-
last->sve_vl = sve_vl;
1768-
last->sme_vl = sme_vl;
1769-
last->fp_type = type;
1770-
last->to_save = to_save;
1748+
*last = *state;
17711749
}
17721750

17731751
/*

arch/arm64/kvm/fpsimd.c

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -130,25 +130,29 @@ void kvm_arch_vcpu_ctxflush_fp(struct kvm_vcpu *vcpu)
130130
*/
131131
void kvm_arch_vcpu_ctxsync_fp(struct kvm_vcpu *vcpu)
132132
{
133-
enum fp_type fp_type;
133+
struct cpu_fp_state fp_state;
134134

135135
WARN_ON_ONCE(!irqs_disabled());
136136

137137
if (vcpu->arch.fp_state == FP_STATE_GUEST_OWNED) {
138-
if (vcpu_has_sve(vcpu))
139-
fp_type = FP_STATE_SVE;
140-
else
141-
fp_type = FP_STATE_FPSIMD;
142138

143139
/*
144140
* Currently we do not support SME guests so SVCR is
145141
* always 0 and we just need a variable to point to.
146142
*/
147-
fpsimd_bind_state_to_cpu(&vcpu->arch.ctxt.fp_regs,
148-
vcpu->arch.sve_state,
149-
vcpu->arch.sve_max_vl,
150-
NULL, 0, &vcpu->arch.svcr,
151-
&vcpu->arch.fp_type, fp_type);
143+
fp_state.st = &vcpu->arch.ctxt.fp_regs;
144+
fp_state.sve_state = vcpu->arch.sve_state;
145+
fp_state.sve_vl = vcpu->arch.sve_max_vl;
146+
fp_state.za_state = NULL;
147+
fp_state.svcr = &vcpu->arch.svcr;
148+
fp_state.fp_type = &vcpu->arch.fp_type;
149+
150+
if (vcpu_has_sve(vcpu))
151+
fp_state.to_save = FP_STATE_SVE;
152+
else
153+
fp_state.to_save = FP_STATE_FPSIMD;
154+
155+
fpsimd_bind_state_to_cpu(&fp_state);
152156

153157
clear_thread_flag(TIF_FOREIGN_FPSTATE);
154158
}

0 commit comments

Comments
 (0)