From cc19d58d66a88d4ba777d83071e108416f530f10 Mon Sep 17 00:00:00 2001 From: David Mosberger Date: Wed, 15 Oct 2003 00:07:23 -0700 Subject: [PATCH] ia64: Fix __delay() even more: it's just not safe to inline the delay- loop because, e.g., the compiler might decide to unroll the loop when passed a constant, etc. --- arch/ia64/kernel/head.S | 19 +++++++++++++++++++ include/asm-ia64/delay.h | 7 ++++--- 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/arch/ia64/kernel/head.S b/arch/ia64/kernel/head.S index 23a1864d16bbc..db5f71d05bb52 100644 --- a/arch/ia64/kernel/head.S +++ b/arch/ia64/kernel/head.S @@ -797,6 +797,25 @@ GLOBAL_ENTRY(ia64_switch_mode_virt) br.ret.sptk.many rp END(ia64_switch_mode_virt) +GLOBAL_ENTRY(ia64_delay_loop) + .prologue +{ nop 0 // work around GAS unwind info generation bug... + .save ar.lc,r2 + mov r2=ar.lc + .body + ;; + mov ar.lc=r32 +} + ;; + // force loop to be 32-byte aligned (GAS bug means we cannot use .align + // inside function body without corrupting unwind info). +{ nop 0 } +1: br.cloop.sptk.few 1b + ;; + mov ar.lc=r2 + br.ret.sptk.many rp +END(ia64_delay_loop) + #ifdef CONFIG_IA64_BRL_EMU /* diff --git a/include/asm-ia64/delay.h b/include/asm-ia64/delay.h index 8cc00a25d17ab..1b9df23a5641c 100644 --- a/include/asm-ia64/delay.h +++ b/include/asm-ia64/delay.h @@ -67,14 +67,15 @@ ia64_get_itc (void) return result; } +extern void ia64_delay_loop (unsigned long loops); + static __inline__ void __delay (unsigned long loops) { - if (loops < 1) + if (unlikely(loops < 1)) return; - while (loops--) - barrier(); + ia64_delay_loop (loops - 1); } static __inline__ void -- 2.53.0