mirror of
https://github.com/Fishwaldo/Star64_linux.git
synced 2025-07-02 20:29:20 +00:00
Merge master.kernel.org:/home/rmk/linux-2.6-arm
This commit is contained in:
commit
92dd7ca0af
27 changed files with 384 additions and 553 deletions
|
@ -30,9 +30,6 @@ extern void __lshrdi3(void);
|
||||||
extern void __modsi3(void);
|
extern void __modsi3(void);
|
||||||
extern void __muldi3(void);
|
extern void __muldi3(void);
|
||||||
extern void __ucmpdi2(void);
|
extern void __ucmpdi2(void);
|
||||||
extern void __udivdi3(void);
|
|
||||||
extern void __umoddi3(void);
|
|
||||||
extern void __udivmoddi4(void);
|
|
||||||
extern void __udivsi3(void);
|
extern void __udivsi3(void);
|
||||||
extern void __umodsi3(void);
|
extern void __umodsi3(void);
|
||||||
extern void __do_div64(void);
|
extern void __do_div64(void);
|
||||||
|
@ -134,9 +131,6 @@ EXPORT_SYMBOL(__lshrdi3);
|
||||||
EXPORT_SYMBOL(__modsi3);
|
EXPORT_SYMBOL(__modsi3);
|
||||||
EXPORT_SYMBOL(__muldi3);
|
EXPORT_SYMBOL(__muldi3);
|
||||||
EXPORT_SYMBOL(__ucmpdi2);
|
EXPORT_SYMBOL(__ucmpdi2);
|
||||||
EXPORT_SYMBOL(__udivdi3);
|
|
||||||
EXPORT_SYMBOL(__umoddi3);
|
|
||||||
EXPORT_SYMBOL(__udivmoddi4);
|
|
||||||
EXPORT_SYMBOL(__udivsi3);
|
EXPORT_SYMBOL(__udivsi3);
|
||||||
EXPORT_SYMBOL(__umodsi3);
|
EXPORT_SYMBOL(__umodsi3);
|
||||||
EXPORT_SYMBOL(__do_div64);
|
EXPORT_SYMBOL(__do_div64);
|
||||||
|
|
|
@ -359,7 +359,8 @@ void cpu_init(void)
|
||||||
"I" (offsetof(struct stack, abt[0])),
|
"I" (offsetof(struct stack, abt[0])),
|
||||||
"I" (PSR_F_BIT | PSR_I_BIT | UND_MODE),
|
"I" (PSR_F_BIT | PSR_I_BIT | UND_MODE),
|
||||||
"I" (offsetof(struct stack, und[0])),
|
"I" (offsetof(struct stack, und[0])),
|
||||||
"I" (PSR_F_BIT | PSR_I_BIT | SVC_MODE));
|
"I" (PSR_F_BIT | PSR_I_BIT | SVC_MODE)
|
||||||
|
: "r14");
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct machine_desc * __init setup_machine(unsigned int nr)
|
static struct machine_desc * __init setup_machine(unsigned int nr)
|
||||||
|
|
|
@ -502,3 +502,126 @@ int __init setup_profiling_timer(unsigned int multiplier)
|
||||||
{
|
{
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
on_each_cpu_mask(void (*func)(void *), void *info, int retry, int wait,
|
||||||
|
cpumask_t mask)
|
||||||
|
{
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
|
preempt_disable();
|
||||||
|
|
||||||
|
ret = smp_call_function_on_cpu(func, info, retry, wait, mask);
|
||||||
|
if (cpu_isset(smp_processor_id(), mask))
|
||||||
|
func(info);
|
||||||
|
|
||||||
|
preempt_enable();
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* TLB operations
|
||||||
|
*/
|
||||||
|
struct tlb_args {
|
||||||
|
struct vm_area_struct *ta_vma;
|
||||||
|
unsigned long ta_start;
|
||||||
|
unsigned long ta_end;
|
||||||
|
};
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_all(void *ignored)
|
||||||
|
{
|
||||||
|
local_flush_tlb_all();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_mm(void *arg)
|
||||||
|
{
|
||||||
|
struct mm_struct *mm = (struct mm_struct *)arg;
|
||||||
|
|
||||||
|
local_flush_tlb_mm(mm);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_page(void *arg)
|
||||||
|
{
|
||||||
|
struct tlb_args *ta = (struct tlb_args *)arg;
|
||||||
|
|
||||||
|
local_flush_tlb_page(ta->ta_vma, ta->ta_start);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_kernel_page(void *arg)
|
||||||
|
{
|
||||||
|
struct tlb_args *ta = (struct tlb_args *)arg;
|
||||||
|
|
||||||
|
local_flush_tlb_kernel_page(ta->ta_start);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_range(void *arg)
|
||||||
|
{
|
||||||
|
struct tlb_args *ta = (struct tlb_args *)arg;
|
||||||
|
|
||||||
|
local_flush_tlb_range(ta->ta_vma, ta->ta_start, ta->ta_end);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void ipi_flush_tlb_kernel_range(void *arg)
|
||||||
|
{
|
||||||
|
struct tlb_args *ta = (struct tlb_args *)arg;
|
||||||
|
|
||||||
|
local_flush_tlb_kernel_range(ta->ta_start, ta->ta_end);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_all(void)
|
||||||
|
{
|
||||||
|
on_each_cpu(ipi_flush_tlb_all, NULL, 1, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_mm(struct mm_struct *mm)
|
||||||
|
{
|
||||||
|
cpumask_t mask = mm->cpu_vm_mask;
|
||||||
|
|
||||||
|
on_each_cpu_mask(ipi_flush_tlb_mm, mm, 1, 1, mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr)
|
||||||
|
{
|
||||||
|
cpumask_t mask = vma->vm_mm->cpu_vm_mask;
|
||||||
|
struct tlb_args ta;
|
||||||
|
|
||||||
|
ta.ta_vma = vma;
|
||||||
|
ta.ta_start = uaddr;
|
||||||
|
|
||||||
|
on_each_cpu_mask(ipi_flush_tlb_page, &ta, 1, 1, mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_kernel_page(unsigned long kaddr)
|
||||||
|
{
|
||||||
|
struct tlb_args ta;
|
||||||
|
|
||||||
|
ta.ta_start = kaddr;
|
||||||
|
|
||||||
|
on_each_cpu(ipi_flush_tlb_kernel_page, &ta, 1, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_range(struct vm_area_struct *vma,
|
||||||
|
unsigned long start, unsigned long end)
|
||||||
|
{
|
||||||
|
cpumask_t mask = vma->vm_mm->cpu_vm_mask;
|
||||||
|
struct tlb_args ta;
|
||||||
|
|
||||||
|
ta.ta_vma = vma;
|
||||||
|
ta.ta_start = start;
|
||||||
|
ta.ta_end = end;
|
||||||
|
|
||||||
|
on_each_cpu_mask(ipi_flush_tlb_range, &ta, 1, 1, mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
void flush_tlb_kernel_range(unsigned long start, unsigned long end)
|
||||||
|
{
|
||||||
|
struct tlb_args ta;
|
||||||
|
|
||||||
|
ta.ta_start = start;
|
||||||
|
ta.ta_end = end;
|
||||||
|
|
||||||
|
on_each_cpu(ipi_flush_tlb_kernel_range, &ta, 1, 1);
|
||||||
|
}
|
||||||
|
|
|
@ -11,7 +11,7 @@ lib-y := backtrace.o changebit.o csumipv6.o csumpartial.o \
|
||||||
strnlen_user.o strchr.o strrchr.o testchangebit.o \
|
strnlen_user.o strchr.o strrchr.o testchangebit.o \
|
||||||
testclearbit.o testsetbit.o uaccess.o getuser.o \
|
testclearbit.o testsetbit.o uaccess.o getuser.o \
|
||||||
putuser.o ashldi3.o ashrdi3.o lshrdi3.o muldi3.o \
|
putuser.o ashldi3.o ashrdi3.o lshrdi3.o muldi3.o \
|
||||||
ucmpdi2.o udivdi3.o lib1funcs.o div64.o \
|
ucmpdi2.o lib1funcs.o div64.o \
|
||||||
io-readsb.o io-writesb.o io-readsl.o io-writesl.o
|
io-readsb.o io-writesb.o io-readsl.o io-writesl.o
|
||||||
|
|
||||||
ifeq ($(CONFIG_CPU_32v3),y)
|
ifeq ($(CONFIG_CPU_32v3),y)
|
||||||
|
|
|
@ -1,183 +0,0 @@
|
||||||
/* longlong.h -- based on code from gcc-2.95.3
|
|
||||||
|
|
||||||
definitions for mixed size 32/64 bit arithmetic.
|
|
||||||
Copyright (C) 1991, 92, 94, 95, 96, 1997, 1998 Free Software Foundation, Inc.
|
|
||||||
|
|
||||||
This definition file is free software; you can redistribute it
|
|
||||||
and/or modify it under the terms of the GNU General Public
|
|
||||||
License as published by the Free Software Foundation; either
|
|
||||||
version 2, or (at your option) any later version.
|
|
||||||
|
|
||||||
This definition file is distributed in the hope that it will be
|
|
||||||
useful, but WITHOUT ANY WARRANTY; without even the implied
|
|
||||||
warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
||||||
See the GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the Free Software
|
|
||||||
Foundation, Inc., 59 Temple Place - Suite 330,
|
|
||||||
Boston, MA 02111-1307, USA. */
|
|
||||||
|
|
||||||
/* Borrowed from GCC 2.95.3, I Molton 29/07/01 */
|
|
||||||
|
|
||||||
#ifndef SI_TYPE_SIZE
|
|
||||||
#define SI_TYPE_SIZE 32
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define __BITS4 (SI_TYPE_SIZE / 4)
|
|
||||||
#define __ll_B (1L << (SI_TYPE_SIZE / 2))
|
|
||||||
#define __ll_lowpart(t) ((u32) (t) % __ll_B)
|
|
||||||
#define __ll_highpart(t) ((u32) (t) / __ll_B)
|
|
||||||
|
|
||||||
/* Define auxiliary asm macros.
|
|
||||||
|
|
||||||
1) umul_ppmm(high_prod, low_prod, multipler, multiplicand)
|
|
||||||
multiplies two u32 integers MULTIPLER and MULTIPLICAND,
|
|
||||||
and generates a two-part u32 product in HIGH_PROD and
|
|
||||||
LOW_PROD.
|
|
||||||
|
|
||||||
2) __umulsidi3(a,b) multiplies two u32 integers A and B,
|
|
||||||
and returns a u64 product. This is just a variant of umul_ppmm.
|
|
||||||
|
|
||||||
3) udiv_qrnnd(quotient, remainder, high_numerator, low_numerator,
|
|
||||||
denominator) divides a two-word unsigned integer, composed by the
|
|
||||||
integers HIGH_NUMERATOR and LOW_NUMERATOR, by DENOMINATOR and
|
|
||||||
places the quotient in QUOTIENT and the remainder in REMAINDER.
|
|
||||||
HIGH_NUMERATOR must be less than DENOMINATOR for correct operation.
|
|
||||||
If, in addition, the most significant bit of DENOMINATOR must be 1,
|
|
||||||
then the pre-processor symbol UDIV_NEEDS_NORMALIZATION is defined to 1.
|
|
||||||
|
|
||||||
4) sdiv_qrnnd(quotient, remainder, high_numerator, low_numerator,
|
|
||||||
denominator). Like udiv_qrnnd but the numbers are signed. The
|
|
||||||
quotient is rounded towards 0.
|
|
||||||
|
|
||||||
5) count_leading_zeros(count, x) counts the number of zero-bits from
|
|
||||||
the msb to the first non-zero bit. This is the number of steps X
|
|
||||||
needs to be shifted left to set the msb. Undefined for X == 0.
|
|
||||||
|
|
||||||
6) add_ssaaaa(high_sum, low_sum, high_addend_1, low_addend_1,
|
|
||||||
high_addend_2, low_addend_2) adds two two-word unsigned integers,
|
|
||||||
composed by HIGH_ADDEND_1 and LOW_ADDEND_1, and HIGH_ADDEND_2 and
|
|
||||||
LOW_ADDEND_2 respectively. The result is placed in HIGH_SUM and
|
|
||||||
LOW_SUM. Overflow (i.e. carry out) is not stored anywhere, and is
|
|
||||||
lost.
|
|
||||||
|
|
||||||
7) sub_ddmmss(high_difference, low_difference, high_minuend,
|
|
||||||
low_minuend, high_subtrahend, low_subtrahend) subtracts two
|
|
||||||
two-word unsigned integers, composed by HIGH_MINUEND_1 and
|
|
||||||
LOW_MINUEND_1, and HIGH_SUBTRAHEND_2 and LOW_SUBTRAHEND_2
|
|
||||||
respectively. The result is placed in HIGH_DIFFERENCE and
|
|
||||||
LOW_DIFFERENCE. Overflow (i.e. carry out) is not stored anywhere,
|
|
||||||
and is lost.
|
|
||||||
|
|
||||||
If any of these macros are left undefined for a particular CPU,
|
|
||||||
C macros are used. */
|
|
||||||
|
|
||||||
#if defined (__arm__)
|
|
||||||
#define add_ssaaaa(sh, sl, ah, al, bh, bl) \
|
|
||||||
__asm__ ("adds %1, %4, %5 \n\
|
|
||||||
adc %0, %2, %3" \
|
|
||||||
: "=r" ((u32) (sh)), \
|
|
||||||
"=&r" ((u32) (sl)) \
|
|
||||||
: "%r" ((u32) (ah)), \
|
|
||||||
"rI" ((u32) (bh)), \
|
|
||||||
"%r" ((u32) (al)), \
|
|
||||||
"rI" ((u32) (bl)))
|
|
||||||
#define sub_ddmmss(sh, sl, ah, al, bh, bl) \
|
|
||||||
__asm__ ("subs %1, %4, %5 \n\
|
|
||||||
sbc %0, %2, %3" \
|
|
||||||
: "=r" ((u32) (sh)), \
|
|
||||||
"=&r" ((u32) (sl)) \
|
|
||||||
: "r" ((u32) (ah)), \
|
|
||||||
"rI" ((u32) (bh)), \
|
|
||||||
"r" ((u32) (al)), \
|
|
||||||
"rI" ((u32) (bl)))
|
|
||||||
#define umul_ppmm(xh, xl, a, b) \
|
|
||||||
{register u32 __t0, __t1, __t2; \
|
|
||||||
__asm__ ("%@ Inlined umul_ppmm \n\
|
|
||||||
mov %2, %5, lsr #16 \n\
|
|
||||||
mov %0, %6, lsr #16 \n\
|
|
||||||
bic %3, %5, %2, lsl #16 \n\
|
|
||||||
bic %4, %6, %0, lsl #16 \n\
|
|
||||||
mul %1, %3, %4 \n\
|
|
||||||
mul %4, %2, %4 \n\
|
|
||||||
mul %3, %0, %3 \n\
|
|
||||||
mul %0, %2, %0 \n\
|
|
||||||
adds %3, %4, %3 \n\
|
|
||||||
addcs %0, %0, #65536 \n\
|
|
||||||
adds %1, %1, %3, lsl #16 \n\
|
|
||||||
adc %0, %0, %3, lsr #16" \
|
|
||||||
: "=&r" ((u32) (xh)), \
|
|
||||||
"=r" ((u32) (xl)), \
|
|
||||||
"=&r" (__t0), "=&r" (__t1), "=r" (__t2) \
|
|
||||||
: "r" ((u32) (a)), \
|
|
||||||
"r" ((u32) (b)));}
|
|
||||||
#define UMUL_TIME 20
|
|
||||||
#define UDIV_TIME 100
|
|
||||||
#endif /* __arm__ */
|
|
||||||
|
|
||||||
#define __umulsidi3(u, v) \
|
|
||||||
({DIunion __w; \
|
|
||||||
umul_ppmm (__w.s.high, __w.s.low, u, v); \
|
|
||||||
__w.ll; })
|
|
||||||
|
|
||||||
#define __udiv_qrnnd_c(q, r, n1, n0, d) \
|
|
||||||
do { \
|
|
||||||
u32 __d1, __d0, __q1, __q0; \
|
|
||||||
u32 __r1, __r0, __m; \
|
|
||||||
__d1 = __ll_highpart (d); \
|
|
||||||
__d0 = __ll_lowpart (d); \
|
|
||||||
\
|
|
||||||
__r1 = (n1) % __d1; \
|
|
||||||
__q1 = (n1) / __d1; \
|
|
||||||
__m = (u32) __q1 * __d0; \
|
|
||||||
__r1 = __r1 * __ll_B | __ll_highpart (n0); \
|
|
||||||
if (__r1 < __m) \
|
|
||||||
{ \
|
|
||||||
__q1--, __r1 += (d); \
|
|
||||||
if (__r1 >= (d)) /* i.e. we didn't get carry when adding to __r1 */\
|
|
||||||
if (__r1 < __m) \
|
|
||||||
__q1--, __r1 += (d); \
|
|
||||||
} \
|
|
||||||
__r1 -= __m; \
|
|
||||||
\
|
|
||||||
__r0 = __r1 % __d1; \
|
|
||||||
__q0 = __r1 / __d1; \
|
|
||||||
__m = (u32) __q0 * __d0; \
|
|
||||||
__r0 = __r0 * __ll_B | __ll_lowpart (n0); \
|
|
||||||
if (__r0 < __m) \
|
|
||||||
{ \
|
|
||||||
__q0--, __r0 += (d); \
|
|
||||||
if (__r0 >= (d)) \
|
|
||||||
if (__r0 < __m) \
|
|
||||||
__q0--, __r0 += (d); \
|
|
||||||
} \
|
|
||||||
__r0 -= __m; \
|
|
||||||
\
|
|
||||||
(q) = (u32) __q1 * __ll_B | __q0; \
|
|
||||||
(r) = __r0; \
|
|
||||||
} while (0)
|
|
||||||
|
|
||||||
#define UDIV_NEEDS_NORMALIZATION 1
|
|
||||||
#define udiv_qrnnd __udiv_qrnnd_c
|
|
||||||
|
|
||||||
#define count_leading_zeros(count, x) \
|
|
||||||
do { \
|
|
||||||
u32 __xr = (x); \
|
|
||||||
u32 __a; \
|
|
||||||
\
|
|
||||||
if (SI_TYPE_SIZE <= 32) \
|
|
||||||
{ \
|
|
||||||
__a = __xr < ((u32)1<<2*__BITS4) \
|
|
||||||
? (__xr < ((u32)1<<__BITS4) ? 0 : __BITS4) \
|
|
||||||
: (__xr < ((u32)1<<3*__BITS4) ? 2*__BITS4 : 3*__BITS4); \
|
|
||||||
} \
|
|
||||||
else \
|
|
||||||
{ \
|
|
||||||
for (__a = SI_TYPE_SIZE - 8; __a > 0; __a -= 8) \
|
|
||||||
if (((__xr >> __a) & 0xff) != 0) \
|
|
||||||
break; \
|
|
||||||
} \
|
|
||||||
\
|
|
||||||
(count) = SI_TYPE_SIZE - (__clz_tab[__xr >> __a] + __a); \
|
|
||||||
} while (0)
|
|
|
@ -1,222 +0,0 @@
|
||||||
/* More subroutines needed by GCC output code on some machines. */
|
|
||||||
/* Compile this one with gcc. */
|
|
||||||
/* Copyright (C) 1989, 92-98, 1999 Free Software Foundation, Inc.
|
|
||||||
|
|
||||||
This file is part of GNU CC.
|
|
||||||
|
|
||||||
GNU CC is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2, or (at your option)
|
|
||||||
any later version.
|
|
||||||
|
|
||||||
GNU CC is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with GNU CC; see the file COPYING. If not, write to
|
|
||||||
the Free Software Foundation, 59 Temple Place - Suite 330,
|
|
||||||
Boston, MA 02111-1307, USA. */
|
|
||||||
|
|
||||||
/* As a special exception, if you link this library with other files,
|
|
||||||
some of which are compiled with GCC, to produce an executable,
|
|
||||||
this library does not by itself cause the resulting executable
|
|
||||||
to be covered by the GNU General Public License.
|
|
||||||
This exception does not however invalidate any other reasons why
|
|
||||||
the executable file might be covered by the GNU General Public License.
|
|
||||||
*/
|
|
||||||
/* support functions required by the kernel. based on code from gcc-2.95.3 */
|
|
||||||
/* I Molton 29/07/01 */
|
|
||||||
|
|
||||||
#include "gcclib.h"
|
|
||||||
#include "longlong.h"
|
|
||||||
|
|
||||||
static const u8 __clz_tab[] = {
|
|
||||||
0, 1, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5,
|
|
||||||
5, 5, 5, 5, 5, 5, 5, 5,
|
|
||||||
6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
|
|
||||||
6, 6, 6, 6, 6, 6, 6, 6,
|
|
||||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
|
||||||
7, 7, 7, 7, 7, 7, 7, 7,
|
|
||||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
|
||||||
7, 7, 7, 7, 7, 7, 7, 7,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
8, 8, 8, 8, 8, 8, 8, 8,
|
|
||||||
};
|
|
||||||
|
|
||||||
u64 __udivmoddi4(u64 n, u64 d, u64 * rp)
|
|
||||||
{
|
|
||||||
DIunion ww;
|
|
||||||
DIunion nn, dd;
|
|
||||||
DIunion rr;
|
|
||||||
u32 d0, d1, n0, n1, n2;
|
|
||||||
u32 q0, q1;
|
|
||||||
u32 b, bm;
|
|
||||||
|
|
||||||
nn.ll = n;
|
|
||||||
dd.ll = d;
|
|
||||||
|
|
||||||
d0 = dd.s.low;
|
|
||||||
d1 = dd.s.high;
|
|
||||||
n0 = nn.s.low;
|
|
||||||
n1 = nn.s.high;
|
|
||||||
|
|
||||||
if (d1 == 0) {
|
|
||||||
if (d0 > n1) {
|
|
||||||
/* 0q = nn / 0D */
|
|
||||||
|
|
||||||
count_leading_zeros(bm, d0);
|
|
||||||
|
|
||||||
if (bm != 0) {
|
|
||||||
/* Normalize, i.e. make the most significant bit of the
|
|
||||||
denominator set. */
|
|
||||||
|
|
||||||
d0 = d0 << bm;
|
|
||||||
n1 = (n1 << bm) | (n0 >> (SI_TYPE_SIZE - bm));
|
|
||||||
n0 = n0 << bm;
|
|
||||||
}
|
|
||||||
|
|
||||||
udiv_qrnnd(q0, n0, n1, n0, d0);
|
|
||||||
q1 = 0;
|
|
||||||
|
|
||||||
/* Remainder in n0 >> bm. */
|
|
||||||
} else {
|
|
||||||
/* qq = NN / 0d */
|
|
||||||
|
|
||||||
if (d0 == 0)
|
|
||||||
d0 = 1 / d0; /* Divide intentionally by zero. */
|
|
||||||
|
|
||||||
count_leading_zeros(bm, d0);
|
|
||||||
|
|
||||||
if (bm == 0) {
|
|
||||||
/* From (n1 >= d0) /\ (the most significant bit of d0 is set),
|
|
||||||
conclude (the most significant bit of n1 is set) /\ (the
|
|
||||||
leading quotient digit q1 = 1).
|
|
||||||
|
|
||||||
This special case is necessary, not an optimization.
|
|
||||||
(Shifts counts of SI_TYPE_SIZE are undefined.) */
|
|
||||||
|
|
||||||
n1 -= d0;
|
|
||||||
q1 = 1;
|
|
||||||
} else {
|
|
||||||
/* Normalize. */
|
|
||||||
|
|
||||||
b = SI_TYPE_SIZE - bm;
|
|
||||||
|
|
||||||
d0 = d0 << bm;
|
|
||||||
n2 = n1 >> b;
|
|
||||||
n1 = (n1 << bm) | (n0 >> b);
|
|
||||||
n0 = n0 << bm;
|
|
||||||
|
|
||||||
udiv_qrnnd(q1, n1, n2, n1, d0);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* n1 != d0... */
|
|
||||||
|
|
||||||
udiv_qrnnd(q0, n0, n1, n0, d0);
|
|
||||||
|
|
||||||
/* Remainder in n0 >> bm. */
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rp != 0) {
|
|
||||||
rr.s.low = n0 >> bm;
|
|
||||||
rr.s.high = 0;
|
|
||||||
*rp = rr.ll;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (d1 > n1) {
|
|
||||||
/* 00 = nn / DD */
|
|
||||||
|
|
||||||
q0 = 0;
|
|
||||||
q1 = 0;
|
|
||||||
|
|
||||||
/* Remainder in n1n0. */
|
|
||||||
if (rp != 0) {
|
|
||||||
rr.s.low = n0;
|
|
||||||
rr.s.high = n1;
|
|
||||||
*rp = rr.ll;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
/* 0q = NN / dd */
|
|
||||||
|
|
||||||
count_leading_zeros(bm, d1);
|
|
||||||
if (bm == 0) {
|
|
||||||
/* From (n1 >= d1) /\ (the most significant bit of d1 is set),
|
|
||||||
conclude (the most significant bit of n1 is set) /\ (the
|
|
||||||
quotient digit q0 = 0 or 1).
|
|
||||||
|
|
||||||
This special case is necessary, not an optimization. */
|
|
||||||
|
|
||||||
/* The condition on the next line takes advantage of that
|
|
||||||
n1 >= d1 (true due to program flow). */
|
|
||||||
if (n1 > d1 || n0 >= d0) {
|
|
||||||
q0 = 1;
|
|
||||||
sub_ddmmss(n1, n0, n1, n0, d1, d0);
|
|
||||||
} else
|
|
||||||
q0 = 0;
|
|
||||||
|
|
||||||
q1 = 0;
|
|
||||||
|
|
||||||
if (rp != 0) {
|
|
||||||
rr.s.low = n0;
|
|
||||||
rr.s.high = n1;
|
|
||||||
*rp = rr.ll;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
u32 m1, m0;
|
|
||||||
/* Normalize. */
|
|
||||||
|
|
||||||
b = SI_TYPE_SIZE - bm;
|
|
||||||
|
|
||||||
d1 = (d1 << bm) | (d0 >> b);
|
|
||||||
d0 = d0 << bm;
|
|
||||||
n2 = n1 >> b;
|
|
||||||
n1 = (n1 << bm) | (n0 >> b);
|
|
||||||
n0 = n0 << bm;
|
|
||||||
|
|
||||||
udiv_qrnnd(q0, n1, n2, n1, d1);
|
|
||||||
umul_ppmm(m1, m0, q0, d0);
|
|
||||||
|
|
||||||
if (m1 > n1 || (m1 == n1 && m0 > n0)) {
|
|
||||||
q0--;
|
|
||||||
sub_ddmmss(m1, m0, m1, m0, d1, d0);
|
|
||||||
}
|
|
||||||
|
|
||||||
q1 = 0;
|
|
||||||
|
|
||||||
/* Remainder in (n1n0 - m1m0) >> bm. */
|
|
||||||
if (rp != 0) {
|
|
||||||
sub_ddmmss(n1, n0, n1, n0, m1, m0);
|
|
||||||
rr.s.low = (n1 << b) | (n0 >> bm);
|
|
||||||
rr.s.high = n1 >> bm;
|
|
||||||
*rp = rr.ll;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ww.s.low = q0;
|
|
||||||
ww.s.high = q1;
|
|
||||||
return ww.ll;
|
|
||||||
}
|
|
||||||
|
|
||||||
u64 __udivdi3(u64 n, u64 d)
|
|
||||||
{
|
|
||||||
return __udivmoddi4(n, d, (u64 *) 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
u64 __umoddi3(u64 u, u64 v)
|
|
||||||
{
|
|
||||||
u64 w;
|
|
||||||
|
|
||||||
(void)__udivmoddi4(u, v, &w);
|
|
||||||
|
|
||||||
return w;
|
|
||||||
}
|
|
|
@ -20,6 +20,7 @@
|
||||||
#include <asm/irq.h>
|
#include <asm/irq.h>
|
||||||
#include <asm/io.h>
|
#include <asm/io.h>
|
||||||
#include <asm/hardware/amba.h>
|
#include <asm/hardware/amba.h>
|
||||||
|
#include <asm/hardware/arm_timer.h>
|
||||||
#include <asm/arch/cm.h>
|
#include <asm/arch/cm.h>
|
||||||
#include <asm/system.h>
|
#include <asm/system.h>
|
||||||
#include <asm/leds.h>
|
#include <asm/leds.h>
|
||||||
|
@ -156,16 +157,6 @@ EXPORT_SYMBOL(cm_control);
|
||||||
#define TICKS2USECS(x) ((x) / TICKS_PER_uSEC)
|
#define TICKS2USECS(x) ((x) / TICKS_PER_uSEC)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/*
|
|
||||||
* What does it look like?
|
|
||||||
*/
|
|
||||||
typedef struct TimerStruct {
|
|
||||||
unsigned long TimerLoad;
|
|
||||||
unsigned long TimerValue;
|
|
||||||
unsigned long TimerControl;
|
|
||||||
unsigned long TimerClear;
|
|
||||||
} TimerStruct_t;
|
|
||||||
|
|
||||||
static unsigned long timer_reload;
|
static unsigned long timer_reload;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -174,7 +165,6 @@ static unsigned long timer_reload;
|
||||||
*/
|
*/
|
||||||
unsigned long integrator_gettimeoffset(void)
|
unsigned long integrator_gettimeoffset(void)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer1 = (TimerStruct_t *)TIMER1_VA_BASE;
|
|
||||||
unsigned long ticks1, ticks2, status;
|
unsigned long ticks1, ticks2, status;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -183,11 +173,11 @@ unsigned long integrator_gettimeoffset(void)
|
||||||
* an interrupt. We get around this by ensuring that the
|
* an interrupt. We get around this by ensuring that the
|
||||||
* counter has not reloaded between our two reads.
|
* counter has not reloaded between our two reads.
|
||||||
*/
|
*/
|
||||||
ticks2 = timer1->TimerValue & 0xffff;
|
ticks2 = readl(TIMER1_VA_BASE + TIMER_VALUE) & 0xffff;
|
||||||
do {
|
do {
|
||||||
ticks1 = ticks2;
|
ticks1 = ticks2;
|
||||||
status = __raw_readl(VA_IC_BASE + IRQ_RAW_STATUS);
|
status = __raw_readl(VA_IC_BASE + IRQ_RAW_STATUS);
|
||||||
ticks2 = timer1->TimerValue & 0xffff;
|
ticks2 = readl(TIMER1_VA_BASE + TIMER_VALUE) & 0xffff;
|
||||||
} while (ticks2 > ticks1);
|
} while (ticks2 > ticks1);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -213,14 +203,12 @@ unsigned long integrator_gettimeoffset(void)
|
||||||
static irqreturn_t
|
static irqreturn_t
|
||||||
integrator_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
|
integrator_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer1 = (volatile TimerStruct_t *)TIMER1_VA_BASE;
|
|
||||||
|
|
||||||
write_seqlock(&xtime_lock);
|
write_seqlock(&xtime_lock);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* clear the interrupt
|
* clear the interrupt
|
||||||
*/
|
*/
|
||||||
timer1->TimerClear = 1;
|
writel(1, TIMER1_VA_BASE + TIMER_INTCLR);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* the clock tick routines are only processed on the
|
* the clock tick routines are only processed on the
|
||||||
|
@ -256,32 +244,29 @@ static struct irqaction integrator_timer_irq = {
|
||||||
*/
|
*/
|
||||||
void __init integrator_time_init(unsigned long reload, unsigned int ctrl)
|
void __init integrator_time_init(unsigned long reload, unsigned int ctrl)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer0 = (volatile TimerStruct_t *)TIMER0_VA_BASE;
|
unsigned int timer_ctrl = TIMER_CTRL_ENABLE | TIMER_CTRL_PERIODIC;
|
||||||
volatile TimerStruct_t *timer1 = (volatile TimerStruct_t *)TIMER1_VA_BASE;
|
|
||||||
volatile TimerStruct_t *timer2 = (volatile TimerStruct_t *)TIMER2_VA_BASE;
|
|
||||||
unsigned int timer_ctrl = 0x80 | 0x40; /* periodic */
|
|
||||||
|
|
||||||
timer_reload = reload;
|
timer_reload = reload;
|
||||||
timer_ctrl |= ctrl;
|
timer_ctrl |= ctrl;
|
||||||
|
|
||||||
if (timer_reload > 0x100000) {
|
if (timer_reload > 0x100000) {
|
||||||
timer_reload >>= 8;
|
timer_reload >>= 8;
|
||||||
timer_ctrl |= 0x08; /* /256 */
|
timer_ctrl |= TIMER_CTRL_DIV256;
|
||||||
} else if (timer_reload > 0x010000) {
|
} else if (timer_reload > 0x010000) {
|
||||||
timer_reload >>= 4;
|
timer_reload >>= 4;
|
||||||
timer_ctrl |= 0x04; /* /16 */
|
timer_ctrl |= TIMER_CTRL_DIV16;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialise to a known state (all timers off)
|
* Initialise to a known state (all timers off)
|
||||||
*/
|
*/
|
||||||
timer0->TimerControl = 0;
|
writel(0, TIMER0_VA_BASE + TIMER_CTRL);
|
||||||
timer1->TimerControl = 0;
|
writel(0, TIMER1_VA_BASE + TIMER_CTRL);
|
||||||
timer2->TimerControl = 0;
|
writel(0, TIMER2_VA_BASE + TIMER_CTRL);
|
||||||
|
|
||||||
timer1->TimerLoad = timer_reload;
|
writel(timer_reload, TIMER1_VA_BASE + TIMER_LOAD);
|
||||||
timer1->TimerValue = timer_reload;
|
writel(timer_reload, TIMER1_VA_BASE + TIMER_VALUE);
|
||||||
timer1->TimerControl = timer_ctrl;
|
writel(timer_ctrl, TIMER1_VA_BASE + TIMER_CTRL);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Make irqs happen for the system timer
|
* Make irqs happen for the system timer
|
||||||
|
|
|
@ -41,7 +41,9 @@
|
||||||
#include <linux/pm.h>
|
#include <linux/pm.h>
|
||||||
|
|
||||||
#include <asm/io.h>
|
#include <asm/io.h>
|
||||||
|
#include <asm/mach/time.h>
|
||||||
#include <asm/mach-types.h>
|
#include <asm/mach-types.h>
|
||||||
|
|
||||||
#include <asm/arch/omap16xx.h>
|
#include <asm/arch/omap16xx.h>
|
||||||
#include <asm/arch/pm.h>
|
#include <asm/arch/pm.h>
|
||||||
#include <asm/arch/mux.h>
|
#include <asm/arch/mux.h>
|
||||||
|
@ -80,13 +82,13 @@ void omap_pm_idle(void)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
mask32 = omap_readl(ARM_SYSST);
|
mask32 = omap_readl(ARM_SYSST);
|
||||||
local_fiq_enable();
|
|
||||||
local_irq_enable();
|
|
||||||
|
|
||||||
#if defined(CONFIG_OMAP_32K_TIMER) && defined(CONFIG_NO_IDLE_HZ)
|
/*
|
||||||
/* Override timer to use VST for the next cycle */
|
* Since an interrupt may set up a timer, we don't want to
|
||||||
omap_32k_timer_next_vst_interrupt();
|
* reprogram the hardware timer with interrupts enabled.
|
||||||
#endif
|
* Re-enable interrupts only after returning from idle.
|
||||||
|
*/
|
||||||
|
timer_dyn_reprogram();
|
||||||
|
|
||||||
if ((mask32 & DSP_IDLE) == 0) {
|
if ((mask32 & DSP_IDLE) == 0) {
|
||||||
__asm__ volatile ("mcr p15, 0, r0, c7, c0, 4");
|
__asm__ volatile ("mcr p15, 0, r0, c7, c0, 4");
|
||||||
|
@ -102,6 +104,8 @@ void omap_pm_idle(void)
|
||||||
|
|
||||||
func_ptr();
|
func_ptr();
|
||||||
}
|
}
|
||||||
|
local_fiq_enable();
|
||||||
|
local_irq_enable();
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
* OMAP Timers
|
* OMAP Timers
|
||||||
*
|
*
|
||||||
* Copyright (C) 2004 Nokia Corporation
|
* Copyright (C) 2004 Nokia Corporation
|
||||||
* Partial timer rewrite and additional VST timer support by
|
* Partial timer rewrite and additional dynamic tick timer support by
|
||||||
* Tony Lindgen <tony@atomide.com> and
|
* Tony Lindgen <tony@atomide.com> and
|
||||||
* Tuukka Tikkanen <tuukka.tikkanen@elektrobit.com>
|
* Tuukka Tikkanen <tuukka.tikkanen@elektrobit.com>
|
||||||
*
|
*
|
||||||
|
@ -261,7 +261,6 @@ unsigned long long sched_clock(void)
|
||||||
* so with HZ = 100, TVR = 327.68.
|
* so with HZ = 100, TVR = 327.68.
|
||||||
*/
|
*/
|
||||||
#define OMAP_32K_TIMER_TICK_PERIOD ((32768 / HZ) - 1)
|
#define OMAP_32K_TIMER_TICK_PERIOD ((32768 / HZ) - 1)
|
||||||
#define MAX_SKIP_JIFFIES 25
|
|
||||||
#define TIMER_32K_SYNCHRONIZED 0xfffbc410
|
#define TIMER_32K_SYNCHRONIZED 0xfffbc410
|
||||||
|
|
||||||
#define JIFFIES_TO_HW_TICKS(nr_jiffies, clock_rate) \
|
#define JIFFIES_TO_HW_TICKS(nr_jiffies, clock_rate) \
|
||||||
|
@ -347,6 +346,42 @@ static irqreturn_t omap_32k_timer_interrupt(int irq, void *dev_id,
|
||||||
return IRQ_HANDLED;
|
return IRQ_HANDLED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef CONFIG_NO_IDLE_HZ
|
||||||
|
/*
|
||||||
|
* Programs the next timer interrupt needed. Called when dynamic tick is
|
||||||
|
* enabled, and to reprogram the ticks to skip from pm_idle. Note that
|
||||||
|
* we can keep the timer continuous, and don't need to set it to run in
|
||||||
|
* one-shot mode. This is because the timer will get reprogrammed again
|
||||||
|
* after next interrupt.
|
||||||
|
*/
|
||||||
|
void omap_32k_timer_reprogram(unsigned long next_tick)
|
||||||
|
{
|
||||||
|
omap_32k_timer_start(JIFFIES_TO_HW_TICKS(next_tick, 32768) + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct irqaction omap_32k_timer_irq;
|
||||||
|
extern struct timer_update_handler timer_update;
|
||||||
|
|
||||||
|
static int omap_32k_timer_enable_dyn_tick(void)
|
||||||
|
{
|
||||||
|
/* No need to reprogram timer, just use the next interrupt */
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int omap_32k_timer_disable_dyn_tick(void)
|
||||||
|
{
|
||||||
|
omap_32k_timer_start(OMAP_32K_TIMER_TICK_PERIOD);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct dyn_tick_timer omap_dyn_tick_timer = {
|
||||||
|
.enable = omap_32k_timer_enable_dyn_tick,
|
||||||
|
.disable = omap_32k_timer_disable_dyn_tick,
|
||||||
|
.reprogram = omap_32k_timer_reprogram,
|
||||||
|
.handler = omap_32k_timer_interrupt,
|
||||||
|
};
|
||||||
|
#endif /* CONFIG_NO_IDLE_HZ */
|
||||||
|
|
||||||
static struct irqaction omap_32k_timer_irq = {
|
static struct irqaction omap_32k_timer_irq = {
|
||||||
.name = "32KHz timer",
|
.name = "32KHz timer",
|
||||||
.flags = SA_INTERRUPT | SA_TIMER,
|
.flags = SA_INTERRUPT | SA_TIMER,
|
||||||
|
@ -355,6 +390,11 @@ static struct irqaction omap_32k_timer_irq = {
|
||||||
|
|
||||||
static __init void omap_init_32k_timer(void)
|
static __init void omap_init_32k_timer(void)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
#ifdef CONFIG_NO_IDLE_HZ
|
||||||
|
omap_timer.dyn_tick = &omap_dyn_tick_timer;
|
||||||
|
#endif
|
||||||
|
|
||||||
setup_irq(INT_OS_TIMER, &omap_32k_timer_irq);
|
setup_irq(INT_OS_TIMER, &omap_32k_timer_irq);
|
||||||
omap_timer.offset = omap_32k_timer_gettimeoffset;
|
omap_timer.offset = omap_32k_timer_gettimeoffset;
|
||||||
omap_32k_last_tick = omap_32k_sync_timer_read();
|
omap_32k_last_tick = omap_32k_sync_timer_read();
|
||||||
|
|
|
@ -154,6 +154,11 @@ config S3C2410_PM_CHECK_CHUNKSIZE
|
||||||
the CRC data block will take more memory, but wil identify any
|
the CRC data block will take more memory, but wil identify any
|
||||||
faults with better precision.
|
faults with better precision.
|
||||||
|
|
||||||
|
config PM_SIMTEC
|
||||||
|
bool
|
||||||
|
depends on PM && (ARCH_BAST || MACH_VR1000)
|
||||||
|
default y
|
||||||
|
|
||||||
config S3C2410_LOWLEVEL_UART_PORT
|
config S3C2410_LOWLEVEL_UART_PORT
|
||||||
int "S3C2410 UART to use for low-level messages"
|
int "S3C2410 UART to use for low-level messages"
|
||||||
default 0
|
default 0
|
||||||
|
|
|
@ -18,6 +18,7 @@ obj-$(CONFIG_S3C2410_DMA) += dma.o
|
||||||
# Power Management support
|
# Power Management support
|
||||||
|
|
||||||
obj-$(CONFIG_PM) += pm.o sleep.o
|
obj-$(CONFIG_PM) += pm.o sleep.o
|
||||||
|
obj-$(CONFIG_PM_SIMTEC) += pm-simtec.o
|
||||||
|
|
||||||
# S3C2440 support
|
# S3C2440 support
|
||||||
|
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
* 10-Mar-2005 LCVR Changed S3C2410_VA to S3C24XX_VA
|
* 10-Mar-2005 LCVR Changed S3C2410_VA to S3C24XX_VA
|
||||||
* 14-Mar-2006 BJD Updated for __iomem changes
|
* 14-Mar-2006 BJD Updated for __iomem changes
|
||||||
* 22-Jun-2006 BJD Added DM9000 platform information
|
* 22-Jun-2006 BJD Added DM9000 platform information
|
||||||
|
* 28-Jun-2006 BJD Moved pm functionality out to common code
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <linux/kernel.h>
|
#include <linux/kernel.h>
|
||||||
|
@ -67,7 +68,6 @@
|
||||||
#include "devs.h"
|
#include "devs.h"
|
||||||
#include "cpu.h"
|
#include "cpu.h"
|
||||||
#include "usb-simtec.h"
|
#include "usb-simtec.h"
|
||||||
#include "pm.h"
|
|
||||||
|
|
||||||
#define COPYRIGHT ", (c) 2004-2005 Simtec Electronics"
|
#define COPYRIGHT ", (c) 2004-2005 Simtec Electronics"
|
||||||
|
|
||||||
|
@ -405,44 +405,13 @@ void __init bast_map_io(void)
|
||||||
usb_simtec_init();
|
usb_simtec_init();
|
||||||
}
|
}
|
||||||
|
|
||||||
void __init bast_init_irq(void)
|
|
||||||
{
|
|
||||||
s3c24xx_init_irq();
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
|
|
||||||
/* bast_init_machine
|
|
||||||
*
|
|
||||||
* enable the power management functions for the EB2410ITX
|
|
||||||
*/
|
|
||||||
|
|
||||||
static __init void bast_init_machine(void)
|
|
||||||
{
|
|
||||||
unsigned long gstatus4;
|
|
||||||
|
|
||||||
printk(KERN_INFO "BAST Power Manangement" COPYRIGHT "\n");
|
|
||||||
|
|
||||||
gstatus4 = (__raw_readl(S3C2410_BANKCON7) & 0x3) << 30;
|
|
||||||
gstatus4 |= (__raw_readl(S3C2410_BANKCON6) & 0x3) << 28;
|
|
||||||
gstatus4 |= (__raw_readl(S3C2410_BANKSIZE) & S3C2410_BANKSIZE_MASK);
|
|
||||||
|
|
||||||
__raw_writel(gstatus4, S3C2410_GSTATUS4);
|
|
||||||
|
|
||||||
s3c2410_pm_init();
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
#define bast_init_machine NULL
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
MACHINE_START(BAST, "Simtec-BAST")
|
MACHINE_START(BAST, "Simtec-BAST")
|
||||||
MAINTAINER("Ben Dooks <ben@simtec.co.uk>")
|
MAINTAINER("Ben Dooks <ben@simtec.co.uk>")
|
||||||
BOOT_MEM(S3C2410_SDRAM_PA, S3C2410_PA_UART, (u32)S3C24XX_VA_UART)
|
BOOT_MEM(S3C2410_SDRAM_PA, S3C2410_PA_UART, (u32)S3C24XX_VA_UART)
|
||||||
BOOT_PARAMS(S3C2410_SDRAM_PA + 0x100)
|
BOOT_PARAMS(S3C2410_SDRAM_PA + 0x100)
|
||||||
MAPIO(bast_map_io)
|
|
||||||
INITIRQ(bast_init_irq)
|
.map_io = bast_map_io,
|
||||||
.init_machine = bast_init_machine,
|
.init_irq = s3c24xx_init_irq,
|
||||||
.timer = &s3c24xx_timer,
|
.timer = &s3c24xx_timer,
|
||||||
MACHINE_END
|
MACHINE_END
|
||||||
|
|
|
@ -371,16 +371,12 @@ void __init vr1000_map_io(void)
|
||||||
usb_simtec_init();
|
usb_simtec_init();
|
||||||
}
|
}
|
||||||
|
|
||||||
void __init vr1000_init_irq(void)
|
|
||||||
{
|
|
||||||
s3c24xx_init_irq();
|
|
||||||
}
|
|
||||||
|
|
||||||
MACHINE_START(VR1000, "Thorcom-VR1000")
|
MACHINE_START(VR1000, "Thorcom-VR1000")
|
||||||
MAINTAINER("Ben Dooks <ben@simtec.co.uk>")
|
MAINTAINER("Ben Dooks <ben@simtec.co.uk>")
|
||||||
BOOT_MEM(S3C2410_SDRAM_PA, S3C2410_PA_UART, (u32)S3C24XX_VA_UART)
|
BOOT_MEM(S3C2410_SDRAM_PA, S3C2410_PA_UART, (u32)S3C24XX_VA_UART)
|
||||||
BOOT_PARAMS(S3C2410_SDRAM_PA + 0x100)
|
BOOT_PARAMS(S3C2410_SDRAM_PA + 0x100)
|
||||||
MAPIO(vr1000_map_io)
|
.map_io = vr1000_map_io,
|
||||||
INITIRQ(vr1000_init_irq)
|
.init_irq = s3c24xx_init_irq,
|
||||||
.timer = &s3c24xx_timer,
|
.timer = &s3c24xx_timer,
|
||||||
MACHINE_END
|
MACHINE_END
|
||||||
|
|
65
arch/arm/mach-s3c2410/pm-simtec.c
Normal file
65
arch/arm/mach-s3c2410/pm-simtec.c
Normal file
|
@ -0,0 +1,65 @@
|
||||||
|
/* linux/arch/arm/mach-s3c2410/pm-simtec.c
|
||||||
|
*
|
||||||
|
* Copyright (c) 2004 Simtec Electronics
|
||||||
|
* Ben Dooks <ben@simtec.co.uk>
|
||||||
|
*
|
||||||
|
* http://armlinux.simtec.co.uk/
|
||||||
|
*
|
||||||
|
* Power Management helpers for Simtec S3C24XX implementations
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License version 2 as
|
||||||
|
* published by the Free Software Foundation.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <linux/kernel.h>
|
||||||
|
#include <linux/types.h>
|
||||||
|
#include <linux/interrupt.h>
|
||||||
|
#include <linux/list.h>
|
||||||
|
#include <linux/timer.h>
|
||||||
|
#include <linux/init.h>
|
||||||
|
#include <linux/device.h>
|
||||||
|
|
||||||
|
#include <asm/mach/arch.h>
|
||||||
|
#include <asm/mach/map.h>
|
||||||
|
|
||||||
|
#include <asm/hardware.h>
|
||||||
|
#include <asm/io.h>
|
||||||
|
|
||||||
|
#include <asm/arch/map.h>
|
||||||
|
#include <asm/arch/regs-serial.h>
|
||||||
|
#include <asm/arch/regs-gpio.h>
|
||||||
|
#include <asm/arch/regs-mem.h>
|
||||||
|
|
||||||
|
#include <asm/mach-types.h>
|
||||||
|
|
||||||
|
#include "pm.h"
|
||||||
|
|
||||||
|
#define COPYRIGHT ", (c) 2005 Simtec Electronics"
|
||||||
|
|
||||||
|
/* pm_simtec_init
|
||||||
|
*
|
||||||
|
* enable the power management functions
|
||||||
|
*/
|
||||||
|
|
||||||
|
static __init int pm_simtec_init(void)
|
||||||
|
{
|
||||||
|
unsigned long gstatus4;
|
||||||
|
|
||||||
|
/* check which machine we are running on */
|
||||||
|
|
||||||
|
if (!machine_is_bast() && !machine_is_vr1000())
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
printk(KERN_INFO "Simtec Board Power Manangement" COPYRIGHT "\n");
|
||||||
|
|
||||||
|
gstatus4 = (__raw_readl(S3C2410_BANKCON7) & 0x3) << 30;
|
||||||
|
gstatus4 |= (__raw_readl(S3C2410_BANKCON6) & 0x3) << 28;
|
||||||
|
gstatus4 |= (__raw_readl(S3C2410_BANKSIZE) & S3C2410_BANKSIZE_MASK);
|
||||||
|
|
||||||
|
__raw_writel(gstatus4, S3C2410_GSTATUS4);
|
||||||
|
|
||||||
|
return s3c2410_pm_init();
|
||||||
|
}
|
||||||
|
|
||||||
|
arch_initcall(pm_simtec_init);
|
|
@ -33,6 +33,7 @@
|
||||||
#include <asm/mach-types.h>
|
#include <asm/mach-types.h>
|
||||||
#include <asm/hardware/amba.h>
|
#include <asm/hardware/amba.h>
|
||||||
#include <asm/hardware/amba_clcd.h>
|
#include <asm/hardware/amba_clcd.h>
|
||||||
|
#include <asm/hardware/arm_timer.h>
|
||||||
#include <asm/hardware/icst307.h>
|
#include <asm/hardware/icst307.h>
|
||||||
|
|
||||||
#include <asm/mach/arch.h>
|
#include <asm/mach/arch.h>
|
||||||
|
@ -788,38 +789,25 @@ void __init versatile_init(void)
|
||||||
*/
|
*/
|
||||||
#define TIMER_INTERVAL (TICKS_PER_uSEC * mSEC_10)
|
#define TIMER_INTERVAL (TICKS_PER_uSEC * mSEC_10)
|
||||||
#if TIMER_INTERVAL >= 0x100000
|
#if TIMER_INTERVAL >= 0x100000
|
||||||
#define TIMER_RELOAD (TIMER_INTERVAL >> 8) /* Divide by 256 */
|
#define TIMER_RELOAD (TIMER_INTERVAL >> 8)
|
||||||
#define TIMER_CTRL 0x88 /* Enable, Clock / 256 */
|
#define TIMER_DIVISOR (TIMER_CTRL_DIV256)
|
||||||
#define TICKS2USECS(x) (256 * (x) / TICKS_PER_uSEC)
|
#define TICKS2USECS(x) (256 * (x) / TICKS_PER_uSEC)
|
||||||
#elif TIMER_INTERVAL >= 0x10000
|
#elif TIMER_INTERVAL >= 0x10000
|
||||||
#define TIMER_RELOAD (TIMER_INTERVAL >> 4) /* Divide by 16 */
|
#define TIMER_RELOAD (TIMER_INTERVAL >> 4) /* Divide by 16 */
|
||||||
#define TIMER_CTRL 0x84 /* Enable, Clock / 16 */
|
#define TIMER_DIVISOR (TIMER_CTRL_DIV16)
|
||||||
#define TICKS2USECS(x) (16 * (x) / TICKS_PER_uSEC)
|
#define TICKS2USECS(x) (16 * (x) / TICKS_PER_uSEC)
|
||||||
#else
|
#else
|
||||||
#define TIMER_RELOAD (TIMER_INTERVAL)
|
#define TIMER_RELOAD (TIMER_INTERVAL)
|
||||||
#define TIMER_CTRL 0x80 /* Enable */
|
#define TIMER_DIVISOR (TIMER_CTRL_DIV1)
|
||||||
#define TICKS2USECS(x) ((x) / TICKS_PER_uSEC)
|
#define TICKS2USECS(x) ((x) / TICKS_PER_uSEC)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define TIMER_CTRL_IE (1 << 5) /* Interrupt Enable */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* What does it look like?
|
|
||||||
*/
|
|
||||||
typedef struct TimerStruct {
|
|
||||||
unsigned long TimerLoad;
|
|
||||||
unsigned long TimerValue;
|
|
||||||
unsigned long TimerControl;
|
|
||||||
unsigned long TimerClear;
|
|
||||||
} TimerStruct_t;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Returns number of ms since last clock interrupt. Note that interrupts
|
* Returns number of ms since last clock interrupt. Note that interrupts
|
||||||
* will have been disabled by do_gettimeoffset()
|
* will have been disabled by do_gettimeoffset()
|
||||||
*/
|
*/
|
||||||
static unsigned long versatile_gettimeoffset(void)
|
static unsigned long versatile_gettimeoffset(void)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer0 = (TimerStruct_t *)TIMER0_VA_BASE;
|
|
||||||
unsigned long ticks1, ticks2, status;
|
unsigned long ticks1, ticks2, status;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -828,11 +816,11 @@ static unsigned long versatile_gettimeoffset(void)
|
||||||
* an interrupt. We get around this by ensuring that the
|
* an interrupt. We get around this by ensuring that the
|
||||||
* counter has not reloaded between our two reads.
|
* counter has not reloaded between our two reads.
|
||||||
*/
|
*/
|
||||||
ticks2 = timer0->TimerValue & 0xffff;
|
ticks2 = readl(TIMER0_VA_BASE + TIMER_VALUE) & 0xffff;
|
||||||
do {
|
do {
|
||||||
ticks1 = ticks2;
|
ticks1 = ticks2;
|
||||||
status = __raw_readl(VA_IC_BASE + VIC_IRQ_RAW_STATUS);
|
status = __raw_readl(VA_IC_BASE + VIC_IRQ_RAW_STATUS);
|
||||||
ticks2 = timer0->TimerValue & 0xffff;
|
ticks2 = readl(TIMER0_VA_BASE + TIMER_VALUE) & 0xffff;
|
||||||
} while (ticks2 > ticks1);
|
} while (ticks2 > ticks1);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -859,12 +847,10 @@ static unsigned long versatile_gettimeoffset(void)
|
||||||
*/
|
*/
|
||||||
static irqreturn_t versatile_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
|
static irqreturn_t versatile_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer0 = (volatile TimerStruct_t *)TIMER0_VA_BASE;
|
|
||||||
|
|
||||||
write_seqlock(&xtime_lock);
|
write_seqlock(&xtime_lock);
|
||||||
|
|
||||||
// ...clear the interrupt
|
// ...clear the interrupt
|
||||||
timer0->TimerClear = 1;
|
writel(1, TIMER0_VA_BASE + TIMER_INTCLR);
|
||||||
|
|
||||||
timer_tick(regs);
|
timer_tick(regs);
|
||||||
|
|
||||||
|
@ -884,31 +870,32 @@ static struct irqaction versatile_timer_irq = {
|
||||||
*/
|
*/
|
||||||
static void __init versatile_timer_init(void)
|
static void __init versatile_timer_init(void)
|
||||||
{
|
{
|
||||||
volatile TimerStruct_t *timer0 = (volatile TimerStruct_t *)TIMER0_VA_BASE;
|
u32 val;
|
||||||
volatile TimerStruct_t *timer1 = (volatile TimerStruct_t *)TIMER1_VA_BASE;
|
|
||||||
volatile TimerStruct_t *timer2 = (volatile TimerStruct_t *)TIMER2_VA_BASE;
|
|
||||||
volatile TimerStruct_t *timer3 = (volatile TimerStruct_t *)TIMER3_VA_BASE;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* set clock frequency:
|
* set clock frequency:
|
||||||
* VERSATILE_REFCLK is 32KHz
|
* VERSATILE_REFCLK is 32KHz
|
||||||
* VERSATILE_TIMCLK is 1MHz
|
* VERSATILE_TIMCLK is 1MHz
|
||||||
*/
|
*/
|
||||||
*(volatile unsigned int *)IO_ADDRESS(VERSATILE_SCTL_BASE) |=
|
val = readl(IO_ADDRESS(VERSATILE_SCTL_BASE));
|
||||||
((VERSATILE_TIMCLK << VERSATILE_TIMER1_EnSel) | (VERSATILE_TIMCLK << VERSATILE_TIMER2_EnSel) |
|
writel((VERSATILE_TIMCLK << VERSATILE_TIMER1_EnSel) |
|
||||||
(VERSATILE_TIMCLK << VERSATILE_TIMER3_EnSel) | (VERSATILE_TIMCLK << VERSATILE_TIMER4_EnSel));
|
(VERSATILE_TIMCLK << VERSATILE_TIMER2_EnSel) |
|
||||||
|
(VERSATILE_TIMCLK << VERSATILE_TIMER3_EnSel) |
|
||||||
|
(VERSATILE_TIMCLK << VERSATILE_TIMER4_EnSel) | val,
|
||||||
|
IO_ADDRESS(VERSATILE_SCTL_BASE));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialise to a known state (all timers off)
|
* Initialise to a known state (all timers off)
|
||||||
*/
|
*/
|
||||||
timer0->TimerControl = 0;
|
writel(0, TIMER0_VA_BASE + TIMER_CTRL);
|
||||||
timer1->TimerControl = 0;
|
writel(0, TIMER1_VA_BASE + TIMER_CTRL);
|
||||||
timer2->TimerControl = 0;
|
writel(0, TIMER2_VA_BASE + TIMER_CTRL);
|
||||||
timer3->TimerControl = 0;
|
writel(0, TIMER3_VA_BASE + TIMER_CTRL);
|
||||||
|
|
||||||
timer0->TimerLoad = TIMER_RELOAD;
|
writel(TIMER_RELOAD, TIMER0_VA_BASE + TIMER_LOAD);
|
||||||
timer0->TimerValue = TIMER_RELOAD;
|
writel(TIMER_RELOAD, TIMER0_VA_BASE + TIMER_VALUE);
|
||||||
timer0->TimerControl = TIMER_CTRL | 0x40 | TIMER_CTRL_IE; /* periodic + IE */
|
writel(TIMER_DIVISOR | TIMER_CTRL_ENABLE | TIMER_CTRL_PERIODIC |
|
||||||
|
TIMER_CTRL_IE, TIMER0_VA_BASE + TIMER_CTRL);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Make irqs happen for the system timer
|
* Make irqs happen for the system timer
|
||||||
|
|
|
@ -437,7 +437,7 @@ void __init paging_init(struct meminfo *mi, struct machine_desc *mdesc)
|
||||||
memtable_init(mi);
|
memtable_init(mi);
|
||||||
if (mdesc->map_io)
|
if (mdesc->map_io)
|
||||||
mdesc->map_io();
|
mdesc->map_io();
|
||||||
flush_tlb_all();
|
local_flush_tlb_all();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* initialise the zones within each node
|
* initialise the zones within each node
|
||||||
|
|
|
@ -682,7 +682,7 @@ void __init memtable_init(struct meminfo *mi)
|
||||||
}
|
}
|
||||||
|
|
||||||
flush_cache_all();
|
flush_cache_all();
|
||||||
flush_tlb_all();
|
local_flush_tlb_all();
|
||||||
|
|
||||||
top_pmd = pmd_off_k(0xffff0000);
|
top_pmd = pmd_off_k(0xffff0000);
|
||||||
}
|
}
|
||||||
|
|
|
@ -117,7 +117,13 @@ static inline u64 vfp_estimate_div128to64(u64 nh, u64 nl, u64 m)
|
||||||
if (nh >= m)
|
if (nh >= m)
|
||||||
return ~0ULL;
|
return ~0ULL;
|
||||||
mh = m >> 32;
|
mh = m >> 32;
|
||||||
z = (mh << 32 <= nh) ? 0xffffffff00000000ULL : (nh / mh) << 32;
|
if (mh << 32 <= nh) {
|
||||||
|
z = 0xffffffff00000000ULL;
|
||||||
|
} else {
|
||||||
|
z = nh;
|
||||||
|
do_div(z, mh);
|
||||||
|
z <<= 32;
|
||||||
|
}
|
||||||
mul64to128(&termh, &terml, m, z);
|
mul64to128(&termh, &terml, m, z);
|
||||||
sub128(&remh, &reml, nh, nl, termh, terml);
|
sub128(&remh, &reml, nh, nl, termh, terml);
|
||||||
ml = m << 32;
|
ml = m << 32;
|
||||||
|
@ -126,7 +132,12 @@ static inline u64 vfp_estimate_div128to64(u64 nh, u64 nl, u64 m)
|
||||||
add128(&remh, &reml, remh, reml, mh, ml);
|
add128(&remh, &reml, remh, reml, mh, ml);
|
||||||
}
|
}
|
||||||
remh = (remh << 32) | (reml >> 32);
|
remh = (remh << 32) | (reml >> 32);
|
||||||
z |= (mh << 32 <= remh) ? 0xffffffff : remh / mh;
|
if (mh << 32 <= remh) {
|
||||||
|
z |= 0xffffffff;
|
||||||
|
} else {
|
||||||
|
do_div(remh, mh);
|
||||||
|
z |= remh;
|
||||||
|
}
|
||||||
return z;
|
return z;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -32,6 +32,8 @@
|
||||||
*/
|
*/
|
||||||
#include <linux/kernel.h>
|
#include <linux/kernel.h>
|
||||||
#include <linux/bitops.h>
|
#include <linux/bitops.h>
|
||||||
|
|
||||||
|
#include <asm/div64.h>
|
||||||
#include <asm/ptrace.h>
|
#include <asm/ptrace.h>
|
||||||
#include <asm/vfp.h>
|
#include <asm/vfp.h>
|
||||||
|
|
||||||
|
|
|
@ -89,7 +89,7 @@ void vfp_raise_sigfpe(unsigned int sicode, struct pt_regs *regs)
|
||||||
current->thread.error_code = 0;
|
current->thread.error_code = 0;
|
||||||
current->thread.trap_no = 6;
|
current->thread.trap_no = 6;
|
||||||
|
|
||||||
force_sig_info(SIGFPE, &info, current);
|
send_sig_info(SIGFPE, &info, current);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void vfp_panic(char *reason)
|
static void vfp_panic(char *reason)
|
||||||
|
|
|
@ -32,6 +32,8 @@
|
||||||
*/
|
*/
|
||||||
#include <linux/kernel.h>
|
#include <linux/kernel.h>
|
||||||
#include <linux/bitops.h>
|
#include <linux/bitops.h>
|
||||||
|
|
||||||
|
#include <asm/div64.h>
|
||||||
#include <asm/ptrace.h>
|
#include <asm/ptrace.h>
|
||||||
#include <asm/vfp.h>
|
#include <asm/vfp.h>
|
||||||
|
|
||||||
|
@ -303,7 +305,11 @@ u32 vfp_estimate_sqrt_significand(u32 exponent, u32 significand)
|
||||||
if (z <= a)
|
if (z <= a)
|
||||||
return (s32)a >> 1;
|
return (s32)a >> 1;
|
||||||
}
|
}
|
||||||
return (u32)(((u64)a << 31) / z) + (z >> 1);
|
{
|
||||||
|
u64 v = (u64)a << 31;
|
||||||
|
do_div(v, z);
|
||||||
|
return v + (z >> 1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static u32 vfp_single_fsqrt(int sd, int unused, s32 m, u32 fpscr)
|
static u32 vfp_single_fsqrt(int sd, int unused, s32 m, u32 fpscr)
|
||||||
|
@ -1107,7 +1113,11 @@ static u32 vfp_single_fdiv(int sd, int sn, s32 m, u32 fpscr)
|
||||||
vsn.significand >>= 1;
|
vsn.significand >>= 1;
|
||||||
vsd.exponent++;
|
vsd.exponent++;
|
||||||
}
|
}
|
||||||
vsd.significand = ((u64)vsn.significand << 32) / vsm.significand;
|
{
|
||||||
|
u64 significand = (u64)vsn.significand << 32;
|
||||||
|
do_div(significand, vsm.significand);
|
||||||
|
vsd.significand = significand;
|
||||||
|
}
|
||||||
if ((vsd.significand & 0x3f) == 0)
|
if ((vsd.significand & 0x3f) == 0)
|
||||||
vsd.significand |= ((u64)vsm.significand * vsd.significand != (u64)vsn.significand << 32);
|
vsd.significand |= ((u64)vsm.significand * vsd.significand != (u64)vsn.significand << 32);
|
||||||
|
|
||||||
|
|
|
@ -68,7 +68,6 @@ struct etherh_priv {
|
||||||
void __iomem *dma_base;
|
void __iomem *dma_base;
|
||||||
unsigned int id;
|
unsigned int id;
|
||||||
void __iomem *ctrl_port;
|
void __iomem *ctrl_port;
|
||||||
void __iomem *base;
|
|
||||||
unsigned char ctrl;
|
unsigned char ctrl;
|
||||||
u32 supported;
|
u32 supported;
|
||||||
};
|
};
|
||||||
|
@ -178,7 +177,7 @@ etherh_setif(struct net_device *dev)
|
||||||
switch (etherh_priv(dev)->id) {
|
switch (etherh_priv(dev)->id) {
|
||||||
case PROD_I3_ETHERLAN600:
|
case PROD_I3_ETHERLAN600:
|
||||||
case PROD_I3_ETHERLAN600A:
|
case PROD_I3_ETHERLAN600A:
|
||||||
addr = etherh_priv(dev)->base + EN0_RCNTHI;
|
addr = (void *)dev->base_addr + EN0_RCNTHI;
|
||||||
|
|
||||||
switch (dev->if_port) {
|
switch (dev->if_port) {
|
||||||
case IF_PORT_10BASE2:
|
case IF_PORT_10BASE2:
|
||||||
|
@ -219,7 +218,7 @@ etherh_getifstat(struct net_device *dev)
|
||||||
switch (etherh_priv(dev)->id) {
|
switch (etherh_priv(dev)->id) {
|
||||||
case PROD_I3_ETHERLAN600:
|
case PROD_I3_ETHERLAN600:
|
||||||
case PROD_I3_ETHERLAN600A:
|
case PROD_I3_ETHERLAN600A:
|
||||||
addr = etherh_priv(dev)->base + EN0_RCNTHI;
|
addr = (void *)dev->base_addr + EN0_RCNTHI;
|
||||||
switch (dev->if_port) {
|
switch (dev->if_port) {
|
||||||
case IF_PORT_10BASE2:
|
case IF_PORT_10BASE2:
|
||||||
stat = 1;
|
stat = 1;
|
||||||
|
@ -282,7 +281,7 @@ static void
|
||||||
etherh_reset(struct net_device *dev)
|
etherh_reset(struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct ei_device *ei_local = netdev_priv(dev);
|
struct ei_device *ei_local = netdev_priv(dev);
|
||||||
void __iomem *addr = etherh_priv(dev)->base;
|
void __iomem *addr = (void *)dev->base_addr;
|
||||||
|
|
||||||
writeb(E8390_NODMA+E8390_PAGE0+E8390_STOP, addr);
|
writeb(E8390_NODMA+E8390_PAGE0+E8390_STOP, addr);
|
||||||
|
|
||||||
|
@ -328,7 +327,7 @@ etherh_block_output (struct net_device *dev, int count, const unsigned char *buf
|
||||||
|
|
||||||
ei_local->dmaing = 1;
|
ei_local->dmaing = 1;
|
||||||
|
|
||||||
addr = etherh_priv(dev)->base;
|
addr = (void *)dev->base_addr;
|
||||||
dma_base = etherh_priv(dev)->dma_base;
|
dma_base = etherh_priv(dev)->dma_base;
|
||||||
|
|
||||||
count = (count + 1) & ~1;
|
count = (count + 1) & ~1;
|
||||||
|
@ -388,7 +387,7 @@ etherh_block_input (struct net_device *dev, int count, struct sk_buff *skb, int
|
||||||
|
|
||||||
ei_local->dmaing = 1;
|
ei_local->dmaing = 1;
|
||||||
|
|
||||||
addr = etherh_priv(dev)->base;
|
addr = (void *)dev->base_addr;
|
||||||
dma_base = etherh_priv(dev)->dma_base;
|
dma_base = etherh_priv(dev)->dma_base;
|
||||||
|
|
||||||
buf = skb->data;
|
buf = skb->data;
|
||||||
|
@ -428,7 +427,7 @@ etherh_get_header (struct net_device *dev, struct e8390_pkt_hdr *hdr, int ring_p
|
||||||
|
|
||||||
ei_local->dmaing = 1;
|
ei_local->dmaing = 1;
|
||||||
|
|
||||||
addr = etherh_priv(dev)->base;
|
addr = (void *)dev->base_addr;
|
||||||
dma_base = etherh_priv(dev)->dma_base;
|
dma_base = etherh_priv(dev)->dma_base;
|
||||||
|
|
||||||
writeb (E8390_NODMA | E8390_PAGE0 | E8390_START, addr + E8390_CMD);
|
writeb (E8390_NODMA | E8390_PAGE0 | E8390_START, addr + E8390_CMD);
|
||||||
|
@ -697,8 +696,7 @@ etherh_probe(struct expansion_card *ec, const struct ecard_id *id)
|
||||||
eh->ctrl_port = eh->ioc_fast;
|
eh->ctrl_port = eh->ioc_fast;
|
||||||
}
|
}
|
||||||
|
|
||||||
eh->base = eh->memc + data->ns8390_offset;
|
dev->base_addr = (unsigned long)eh->memc + data->ns8390_offset;
|
||||||
dev->base_addr = (unsigned long)eh->base;
|
|
||||||
eh->dma_base = eh->memc + data->dataport_offset;
|
eh->dma_base = eh->memc + data->dataport_offset;
|
||||||
eh->ctrl_port += data->ctrlport_offset;
|
eh->ctrl_port += data->ctrlport_offset;
|
||||||
|
|
||||||
|
|
|
@ -11,6 +11,8 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "hardware.h"
|
||||||
|
|
||||||
.macro addruart,rx
|
.macro addruart,rx
|
||||||
mrc p15, 0, \rx, c1, c0
|
mrc p15, 0, \rx, c1, c0
|
||||||
tst \rx, #1 @ MMU enabled?
|
tst \rx, #1 @ MMU enabled?
|
||||||
|
|
21
include/asm-arm/hardware/arm_timer.h
Normal file
21
include/asm-arm/hardware/arm_timer.h
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
#ifndef __ASM_ARM_HARDWARE_ARM_TIMER_H
|
||||||
|
#define __ASM_ARM_HARDWARE_ARM_TIMER_H
|
||||||
|
|
||||||
|
#define TIMER_LOAD 0x00
|
||||||
|
#define TIMER_VALUE 0x04
|
||||||
|
#define TIMER_CTRL 0x08
|
||||||
|
#define TIMER_CTRL_ONESHOT (1 << 0)
|
||||||
|
#define TIMER_CTRL_32BIT (1 << 1)
|
||||||
|
#define TIMER_CTRL_DIV1 (0 << 2)
|
||||||
|
#define TIMER_CTRL_DIV16 (1 << 2)
|
||||||
|
#define TIMER_CTRL_DIV256 (2 << 2)
|
||||||
|
#define TIMER_CTRL_IE (1 << 5) /* Interrupt Enable (versatile only) */
|
||||||
|
#define TIMER_CTRL_PERIODIC (1 << 6)
|
||||||
|
#define TIMER_CTRL_ENABLE (1 << 7)
|
||||||
|
|
||||||
|
#define TIMER_INTCLR 0x0c
|
||||||
|
#define TIMER_RIS 0x10
|
||||||
|
#define TIMER_MIS 0x14
|
||||||
|
#define TIMER_BGLOAD 0x18
|
||||||
|
|
||||||
|
#endif
|
|
@ -290,7 +290,6 @@ do { \
|
||||||
})
|
})
|
||||||
|
|
||||||
#ifdef CONFIG_SMP
|
#ifdef CONFIG_SMP
|
||||||
#error SMP not supported
|
|
||||||
|
|
||||||
#define smp_mb() mb()
|
#define smp_mb() mb()
|
||||||
#define smp_rmb() rmb()
|
#define smp_rmb() rmb()
|
||||||
|
@ -304,6 +303,8 @@ do { \
|
||||||
#define smp_wmb() barrier()
|
#define smp_wmb() barrier()
|
||||||
#define smp_read_barrier_depends() do { } while(0)
|
#define smp_read_barrier_depends() do { } while(0)
|
||||||
|
|
||||||
|
#endif /* CONFIG_SMP */
|
||||||
|
|
||||||
#if defined(CONFIG_CPU_SA1100) || defined(CONFIG_CPU_SA110)
|
#if defined(CONFIG_CPU_SA1100) || defined(CONFIG_CPU_SA110)
|
||||||
/*
|
/*
|
||||||
* On the StrongARM, "swp" is terminally broken since it bypasses the
|
* On the StrongARM, "swp" is terminally broken since it bypasses the
|
||||||
|
@ -316,9 +317,16 @@ do { \
|
||||||
*
|
*
|
||||||
* We choose (1) since its the "easiest" to achieve here and is not
|
* We choose (1) since its the "easiest" to achieve here and is not
|
||||||
* dependent on the processor type.
|
* dependent on the processor type.
|
||||||
|
*
|
||||||
|
* NOTE that this solution won't work on an SMP system, so explcitly
|
||||||
|
* forbid it here.
|
||||||
*/
|
*/
|
||||||
|
#ifdef CONFIG_SMP
|
||||||
|
#error SMP is not supported on SA1100/SA110
|
||||||
|
#else
|
||||||
#define swp_is_buggy
|
#define swp_is_buggy
|
||||||
#endif
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
static inline unsigned long __xchg(unsigned long x, volatile void *ptr, int size)
|
static inline unsigned long __xchg(unsigned long x, volatile void *ptr, int size)
|
||||||
{
|
{
|
||||||
|
@ -361,8 +369,6 @@ static inline unsigned long __xchg(unsigned long x, volatile void *ptr, int size
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif /* CONFIG_SMP */
|
|
||||||
|
|
||||||
#endif /* __ASSEMBLY__ */
|
#endif /* __ASSEMBLY__ */
|
||||||
|
|
||||||
#define arch_align_stack(x) (x)
|
#define arch_align_stack(x) (x)
|
||||||
|
|
|
@ -235,7 +235,7 @@ extern struct cpu_tlb_fns cpu_tlb;
|
||||||
|
|
||||||
#define tlb_flag(f) ((always_tlb_flags & (f)) || (__tlb_flag & possible_tlb_flags & (f)))
|
#define tlb_flag(f) ((always_tlb_flags & (f)) || (__tlb_flag & possible_tlb_flags & (f)))
|
||||||
|
|
||||||
static inline void flush_tlb_all(void)
|
static inline void local_flush_tlb_all(void)
|
||||||
{
|
{
|
||||||
const int zero = 0;
|
const int zero = 0;
|
||||||
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
||||||
|
@ -253,7 +253,7 @@ static inline void flush_tlb_all(void)
|
||||||
asm("mcr%? p15, 0, %0, c8, c5, 0" : : "r" (zero));
|
asm("mcr%? p15, 0, %0, c8, c5, 0" : : "r" (zero));
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void flush_tlb_mm(struct mm_struct *mm)
|
static inline void local_flush_tlb_mm(struct mm_struct *mm)
|
||||||
{
|
{
|
||||||
const int zero = 0;
|
const int zero = 0;
|
||||||
const int asid = ASID(mm);
|
const int asid = ASID(mm);
|
||||||
|
@ -282,7 +282,7 @@ static inline void flush_tlb_mm(struct mm_struct *mm)
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void
|
static inline void
|
||||||
flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr)
|
local_flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr)
|
||||||
{
|
{
|
||||||
const int zero = 0;
|
const int zero = 0;
|
||||||
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
||||||
|
@ -313,7 +313,7 @@ flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr)
|
||||||
asm("mcr%? p15, 0, %0, c8, c5, 1" : : "r" (uaddr));
|
asm("mcr%? p15, 0, %0, c8, c5, 1" : : "r" (uaddr));
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void flush_tlb_kernel_page(unsigned long kaddr)
|
static inline void local_flush_tlb_kernel_page(unsigned long kaddr)
|
||||||
{
|
{
|
||||||
const int zero = 0;
|
const int zero = 0;
|
||||||
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
const unsigned int __tlb_flag = __cpu_tlb_flags;
|
||||||
|
@ -384,8 +384,24 @@ static inline void clean_pmd_entry(pmd_t *pmd)
|
||||||
/*
|
/*
|
||||||
* Convert calls to our calling convention.
|
* Convert calls to our calling convention.
|
||||||
*/
|
*/
|
||||||
#define flush_tlb_range(vma,start,end) __cpu_flush_user_tlb_range(start,end,vma)
|
#define local_flush_tlb_range(vma,start,end) __cpu_flush_user_tlb_range(start,end,vma)
|
||||||
#define flush_tlb_kernel_range(s,e) __cpu_flush_kern_tlb_range(s,e)
|
#define local_flush_tlb_kernel_range(s,e) __cpu_flush_kern_tlb_range(s,e)
|
||||||
|
|
||||||
|
#ifndef CONFIG_SMP
|
||||||
|
#define flush_tlb_all local_flush_tlb_all
|
||||||
|
#define flush_tlb_mm local_flush_tlb_mm
|
||||||
|
#define flush_tlb_page local_flush_tlb_page
|
||||||
|
#define flush_tlb_kernel_page local_flush_tlb_kernel_page
|
||||||
|
#define flush_tlb_range local_flush_tlb_range
|
||||||
|
#define flush_tlb_kernel_range local_flush_tlb_kernel_range
|
||||||
|
#else
|
||||||
|
extern void flush_tlb_all(void);
|
||||||
|
extern void flush_tlb_mm(struct mm_struct *mm);
|
||||||
|
extern void flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr);
|
||||||
|
extern void flush_tlb_kernel_page(unsigned long kaddr);
|
||||||
|
extern void flush_tlb_range(struct vm_area_struct *vma, unsigned long start, unsigned long end);
|
||||||
|
extern void flush_tlb_kernel_range(unsigned long start, unsigned long end);
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if PG_dcache_dirty is set for the page, we need to ensure that any
|
* if PG_dcache_dirty is set for the page, we need to ensure that any
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue