linux/arch/m32r/lib/delay.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0
   2/*
   3 * linux/arch/m32r/lib/delay.c
   4 *
   5 * Copyright (c) 2002  Hitoshi Yamamoto, Hirokazu Takata
   6 * Copyright (c) 2004  Hirokazu Takata
   7 */
   8
   9#include <linux/param.h>
  10#include <linux/module.h>
  11#ifdef CONFIG_SMP
  12#include <linux/sched.h>
  13#include <asm/current.h>
  14#include <asm/smp.h>
  15#endif  /* CONFIG_SMP */
  16#include <asm/processor.h>
  17
  18void __delay(unsigned long loops)
  19{
  20#ifdef CONFIG_ISA_DUAL_ISSUE
  21        __asm__ __volatile__ (
  22                "beqz   %0, 2f                  \n\t"
  23                "addi   %0, #-1                 \n\t"
  24
  25                " .fillinsn                     \n\t"
  26                "1:                             \n\t"
  27                "cmpz   %0  ||  addi  %0, #-1   \n\t"
  28                "bc     2f  ||  cmpz  %0        \n\t"
  29                "bc     2f  ||  addi  %0, #-1   \n\t"
  30                "cmpz   %0  ||  addi  %0, #-1   \n\t"
  31                "bc     2f  ||  cmpz  %0        \n\t"
  32                "bnc    1b  ||  addi  %0, #-1   \n\t"
  33                " .fillinsn                     \n\t"
  34                "2:                             \n\t"
  35                : "+r" (loops)
  36                : "r" (0)
  37                : "cbit"
  38        );
  39#else
  40        __asm__ __volatile__ (
  41                "beqz   %0, 2f                  \n\t"
  42                " .fillinsn                     \n\t"
  43                "1:                             \n\t"
  44                "addi   %0, #-1                 \n\t"
  45                "blez   %0, 2f                  \n\t"
  46                "addi   %0, #-1                 \n\t"
  47                "blez   %0, 2f                  \n\t"
  48                "addi   %0, #-1                 \n\t"
  49                "blez   %0, 2f                  \n\t"
  50                "addi   %0, #-1                 \n\t"
  51                "bgtz   %0, 1b                  \n\t"
  52                " .fillinsn                     \n\t"
  53                "2:                             \n\t"
  54                : "+r" (loops)
  55                : "r" (0)
  56        );
  57#endif
  58}
  59
  60void __const_udelay(unsigned long xloops)
  61{
  62#if defined(CONFIG_ISA_M32R2) && defined(CONFIG_ISA_DSP_LEVEL2)
  63        /*
  64         * loops [1] = (xloops >> 32) [sec] * loops_per_jiffy [1/jiffy]
  65         *            * HZ [jiffy/sec]
  66         *          = (xloops >> 32) [sec] * (loops_per_jiffy * HZ) [1/sec]
  67         *          = (((xloops * loops_per_jiffy) >> 32) * HZ) [1]
  68         *
  69         * NOTE:
  70         *   - '[]' depicts variable's dimension in the above equation.
  71         *   - "rac" instruction rounds the accumulator in word size.
  72         */
  73        __asm__ __volatile__ (
  74                "srli   %0, #1                          \n\t"
  75                "mulwhi %0, %1  ; a0                    \n\t"
  76                "mulwu1 %0, %1  ; a1                    \n\t"
  77                "sadd           ; a0 += (a1 >> 16)      \n\t"
  78                "rac    a0, a0, #1                      \n\t"
  79                "mvfacmi %0, a0                         \n\t"
  80                : "+r" (xloops)
  81                : "r" (current_cpu_data.loops_per_jiffy)
  82                : "a0", "a1"
  83        );
  84#elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
  85        /*
  86         * u64 ull;
  87         * ull = (u64)xloops * (u64)current_cpu_data.loops_per_jiffy;
  88         * xloops = (ull >> 32);
  89         */
  90        __asm__ __volatile__ (
  91                "and3   r4, %0, #0xffff         \n\t"
  92                "and3   r5, %1, #0xffff         \n\t"
  93                "mul    r4, r5                  \n\t"
  94                "srl3   r6, %0, #16             \n\t"
  95                "srli   r4, #16                 \n\t"
  96                "mul    r5, r6                  \n\t"
  97                "add    r4, r5                  \n\t"
  98                "and3   r5, %0, #0xffff         \n\t"
  99                "srl3   r6, %1, #16             \n\t"
 100                "mul    r5, r6                  \n\t"
 101                "add    r4, r5                  \n\t"
 102                "srl3   r5, %0, #16             \n\t"
 103                "srli   r4, #16                 \n\t"
 104                "mul    r5, r6                  \n\t"
 105                "add    r4, r5                  \n\t"
 106                "mv     %0, r4                  \n\t"
 107                : "+r" (xloops)
 108                : "r" (current_cpu_data.loops_per_jiffy)
 109                : "r4", "r5", "r6"
 110        );
 111#else
 112#error unknown isa configuration
 113#endif
 114        __delay(xloops * HZ);
 115}
 116
 117void __udelay(unsigned long usecs)
 118{
 119        __const_udelay(usecs * 0x000010c7);  /* 2**32 / 1000000 (rounded up) */
 120}
 121
 122void __ndelay(unsigned long nsecs)
 123{
 124        __const_udelay(nsecs * 0x00005);  /* 2**32 / 1000000000 (rounded up) */
 125}
 126
 127EXPORT_SYMBOL(__delay);
 128EXPORT_SYMBOL(__const_udelay);
 129EXPORT_SYMBOL(__udelay);
 130EXPORT_SYMBOL(__ndelay);
 131