Skip to content

Commit 6076dc3

Browse files
chleroympe
authored andcommitted
powerpc/feature-fixups: Refactor entry fixups patching
Several fonctions have the same loop for patching instructions. Introduce function do_patch_entry_fixups() to refactor those loops. Signed-off-by: Christophe Leroy <[email protected]> Signed-off-by: Michael Ellerman <[email protected]> Link: https://lore.kernel.org/r/79eeff7b20a98f7136da5f79b1f7c436928f27f3.1669969781.git.christophe.leroy@csgroup.eu
1 parent 84ecfe6 commit 6076dc3

File tree

1 file changed

+32
-52
lines changed

1 file changed

+32
-52
lines changed

arch/powerpc/lib/feature-fixups.c

Lines changed: 32 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -118,9 +118,33 @@ void do_feature_fixups(unsigned long value, void *fixup_start, void *fixup_end)
118118
}
119119

120120
#ifdef CONFIG_PPC_BOOK3S_64
121+
static int do_patch_entry_fixups(long *start, long *end, unsigned int *instrs,
122+
bool do_fallback, void *fallback)
123+
{
124+
int i;
125+
126+
for (i = 0; start < end; start++, i++) {
127+
unsigned int *dest = (void *)start + *start;
128+
129+
pr_devel("patching dest %lx\n", (unsigned long)dest);
130+
131+
// See comment in do_entry_flush_fixups() RE order of patching
132+
if (do_fallback) {
133+
patch_instruction(dest, ppc_inst(instrs[0]));
134+
patch_instruction(dest + 2, ppc_inst(instrs[2]));
135+
patch_branch(dest + 1, (unsigned long)fallback, BRANCH_SET_LINK);
136+
} else {
137+
patch_instruction(dest + 1, ppc_inst(instrs[1]));
138+
patch_instruction(dest + 2, ppc_inst(instrs[2]));
139+
patch_instruction(dest, ppc_inst(instrs[0]));
140+
}
141+
}
142+
return i;
143+
}
144+
121145
static void do_stf_entry_barrier_fixups(enum stf_barrier_type types)
122146
{
123-
unsigned int instrs[3], *dest;
147+
unsigned int instrs[3];
124148
long *start, *end;
125149
int i;
126150

@@ -144,23 +168,8 @@ static void do_stf_entry_barrier_fixups(enum stf_barrier_type types)
144168
instrs[i++] = PPC_RAW_ORI(_R31, _R31, 0); /* speculation barrier */
145169
}
146170

147-
for (i = 0; start < end; start++, i++) {
148-
dest = (void *)start + *start;
149-
150-
pr_devel("patching dest %lx\n", (unsigned long)dest);
151-
152-
// See comment in do_entry_flush_fixups() RE order of patching
153-
if (types & STF_BARRIER_FALLBACK) {
154-
patch_instruction(dest, ppc_inst(instrs[0]));
155-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
156-
patch_branch(dest + 1,
157-
(unsigned long)&stf_barrier_fallback, BRANCH_SET_LINK);
158-
} else {
159-
patch_instruction(dest + 1, ppc_inst(instrs[1]));
160-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
161-
patch_instruction(dest, ppc_inst(instrs[0]));
162-
}
163-
}
171+
i = do_patch_entry_fixups(start, end, instrs, types & STF_BARRIER_FALLBACK,
172+
&stf_barrier_fallback);
164173

165174
printk(KERN_DEBUG "stf-barrier: patched %d entry locations (%s barrier)\n", i,
166175
(types == STF_BARRIER_NONE) ? "no" :
@@ -325,7 +334,7 @@ void do_uaccess_flush_fixups(enum l1d_flush_type types)
325334
static int __do_entry_flush_fixups(void *data)
326335
{
327336
enum l1d_flush_type types = *(enum l1d_flush_type *)data;
328-
unsigned int instrs[3], *dest;
337+
unsigned int instrs[3];
329338
long *start, *end;
330339
int i;
331340

@@ -375,42 +384,13 @@ static int __do_entry_flush_fixups(void *data)
375384

376385
start = PTRRELOC(&__start___entry_flush_fixup);
377386
end = PTRRELOC(&__stop___entry_flush_fixup);
378-
for (i = 0; start < end; start++, i++) {
379-
dest = (void *)start + *start;
380-
381-
pr_devel("patching dest %lx\n", (unsigned long)dest);
382-
383-
if (types == L1D_FLUSH_FALLBACK) {
384-
patch_instruction(dest, ppc_inst(instrs[0]));
385-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
386-
patch_branch(dest + 1,
387-
(unsigned long)&entry_flush_fallback, BRANCH_SET_LINK);
388-
} else {
389-
patch_instruction(dest + 1, ppc_inst(instrs[1]));
390-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
391-
patch_instruction(dest, ppc_inst(instrs[0]));
392-
}
393-
}
387+
i = do_patch_entry_fixups(start, end, instrs, types == L1D_FLUSH_FALLBACK,
388+
&entry_flush_fallback);
394389

395390
start = PTRRELOC(&__start___scv_entry_flush_fixup);
396391
end = PTRRELOC(&__stop___scv_entry_flush_fixup);
397-
for (; start < end; start++, i++) {
398-
dest = (void *)start + *start;
399-
400-
pr_devel("patching dest %lx\n", (unsigned long)dest);
401-
402-
if (types == L1D_FLUSH_FALLBACK) {
403-
patch_instruction(dest, ppc_inst(instrs[0]));
404-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
405-
patch_branch(dest + 1,
406-
(unsigned long)&scv_entry_flush_fallback, BRANCH_SET_LINK);
407-
} else {
408-
patch_instruction(dest + 1, ppc_inst(instrs[1]));
409-
patch_instruction(dest + 2, ppc_inst(instrs[2]));
410-
patch_instruction(dest, ppc_inst(instrs[0]));
411-
}
412-
}
413-
392+
i += do_patch_entry_fixups(start, end, instrs, types == L1D_FLUSH_FALLBACK,
393+
&scv_entry_flush_fallback);
414394

415395
printk(KERN_DEBUG "entry-flush: patched %d locations (%s flush)\n", i,
416396
(types == L1D_FLUSH_NONE) ? "no" :

0 commit comments

Comments
 (0)