mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-14 15:54:15 +08:00
MIPS: __delay CPU_DADDI_WORKAROUNDS bug fix
With CPU_DADDI_WORKAROUNDS enabled __delay assembles with a macro in a branch delay slot: {standard input}: Assembler messages: {standard input}:18: Warning: Macro instruction expanded into multiple instructions in a branch delay slot and broken code results: 0000000000000000 <__delay>: 0: 1480ffff bnez a0,0 <__delay> 4: 24010001 li at,1 8: 0081202f dsubu a0,a0,at c: 03e00008 jr ra 10: 00000000 nop 14: 00000000 nop Consequently the function loops indefinitely, showing up prominently as a hang in the delay loop calibration at bootstrap. This change corrects the problem by forcing the immediate 1 into a register while keeping code produced identical where CPU_DADDI_WORKAROUNDS is disabled. Signed-off-by: Maciej W. Rozycki <macro@linux-mips.org> Cc: linux-mips@linux-mips.org Patchwork: https://patchwork.linux-mips.org/patch/6669/ Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
This commit is contained in:
parent
824122a319
commit
2db4bc3418
@ -6,7 +6,7 @@
|
||||
* Copyright (C) 1994 by Waldorf Electronics
|
||||
* Copyright (C) 1995 - 2000, 01, 03 by Ralf Baechle
|
||||
* Copyright (C) 1999, 2000 Silicon Graphics, Inc.
|
||||
* Copyright (C) 2007 Maciej W. Rozycki
|
||||
* Copyright (C) 2007, 2014 Maciej W. Rozycki
|
||||
*/
|
||||
#include <linux/module.h>
|
||||
#include <linux/param.h>
|
||||
@ -15,6 +15,12 @@
|
||||
#include <asm/compiler.h>
|
||||
#include <asm/war.h>
|
||||
|
||||
#ifndef CONFIG_CPU_DADDI_WORKAROUNDS
|
||||
#define GCC_DADDI_IMM_ASM() "I"
|
||||
#else
|
||||
#define GCC_DADDI_IMM_ASM() "r"
|
||||
#endif
|
||||
|
||||
void __delay(unsigned long loops)
|
||||
{
|
||||
__asm__ __volatile__ (
|
||||
@ -22,13 +28,13 @@ void __delay(unsigned long loops)
|
||||
" .align 3 \n"
|
||||
"1: bnez %0, 1b \n"
|
||||
#if BITS_PER_LONG == 32
|
||||
" subu %0, 1 \n"
|
||||
" subu %0, %1 \n"
|
||||
#else
|
||||
" dsubu %0, 1 \n"
|
||||
" dsubu %0, %1 \n"
|
||||
#endif
|
||||
" .set reorder \n"
|
||||
: "=r" (loops)
|
||||
: "0" (loops));
|
||||
: GCC_DADDI_IMM_ASM() (1), "0" (loops));
|
||||
}
|
||||
EXPORT_SYMBOL(__delay);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user