Microblaze patches for 3.14-rc1
- Add CCF support - Fix BS=0 compilation - Wire up defconfig - Some minor cleanups and fixes -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.10 (GNU/Linux) iEYEABECAAYFAlLnf6AACgkQykllyylKDCEPhgCeNZmE2b1pEjeyZ7TGY2+uxi93 WrwAoIfey197x8D+S+bLgWYfaT++cGe+ =R9Zc -----END PGP SIGNATURE----- Merge tag 'microblaze-3.14-rc1' of git://git.monstr.eu/linux-2.6-microblaze Pull microblaze patches from Michal Simek: - add CCF support - fix BS=0 compilation - wire up defconfig - some minor cleanups and fixes * tag 'microblaze-3.14-rc1' of git://git.monstr.eu/linux-2.6-microblaze: microblaze: Add missing v8.50.a version microblaze: Fix missing bracket in printk microblaze: Fix compilation error for BS=0 microblaze: Disable stack protection from bootloader microblaze: Define read/write{b,w,l}_relaxed MMIO microblaze: timer: Do not initialized system timer twice microblaze: timer: Use generic sched_clock implementation microblaze: Add NOTES section to linker script microblaze: Add support for CCF microblaze: Simplify fcpu helper function microblaze/uapi: Use Kbuild logic to include <asm-generic/types.h> microblaze: Remove duplicate declarations of _stext[] and _etext[] microblaze: Remove _fdt_start casts microblaze: Wire up defconfig to mmu_defconfig
This commit is contained in:
commit
627f4b3ee3
|
@ -26,6 +26,8 @@ config MICROBLAZE
|
|||
select GENERIC_CPU_DEVICES
|
||||
select GENERIC_ATOMIC64
|
||||
select GENERIC_CLOCKEVENTS
|
||||
select COMMON_CLK
|
||||
select GENERIC_SCHED_CLOCK
|
||||
select GENERIC_IDLE_POLL_SETUP
|
||||
select MODULES_USE_ELF_RELA
|
||||
select CLONE_BACKWARDS3
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
KBUILD_DEFCONFIG := mmu_defconfig
|
||||
|
||||
ifeq ($(CONFIG_MMU),y)
|
||||
UTS_SYSNAME = -DUTS_SYSNAME=\"Linux\"
|
||||
else
|
||||
|
|
|
@ -91,15 +91,18 @@ extern struct cpuinfo cpuinfo;
|
|||
|
||||
/* fwd declarations of the various CPUinfo populators */
|
||||
void setup_cpuinfo(void);
|
||||
void setup_cpuinfo_clk(void);
|
||||
|
||||
void set_cpuinfo_static(struct cpuinfo *ci, struct device_node *cpu);
|
||||
void set_cpuinfo_pvr_full(struct cpuinfo *ci, struct device_node *cpu);
|
||||
|
||||
static inline unsigned int fcpu(struct device_node *cpu, char *n)
|
||||
{
|
||||
const __be32 *val;
|
||||
return (val = of_get_property(cpu, n, NULL)) ?
|
||||
be32_to_cpup(val) : 0;
|
||||
u32 val = 0;
|
||||
|
||||
of_property_read_u32(cpu, n, &val);
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
#endif /* _ASM_MICROBLAZE_CPUINFO_H */
|
||||
|
|
|
@ -342,4 +342,12 @@ static inline void outsl(unsigned long addr, const void *buffer, int count)
|
|||
#define iowrite32_rep(p, src, count) \
|
||||
outsl((unsigned long) (p), (src), (count))
|
||||
|
||||
#define readb_relaxed readb
|
||||
#define readw_relaxed readw
|
||||
#define readl_relaxed readl
|
||||
|
||||
#define writeb_relaxed writeb
|
||||
#define writew_relaxed writew
|
||||
#define writel_relaxed writel
|
||||
|
||||
#endif /* _ASM_MICROBLAZE_IO_H */
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
# ifndef __ASSEMBLY__
|
||||
extern char _ssbss[], _esbss[];
|
||||
extern unsigned long __ivt_start[], __ivt_end[];
|
||||
extern char _etext[], _stext[];
|
||||
|
||||
extern u32 _fdt_start[], _fdt_end[];
|
||||
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
# UAPI Header export list
|
||||
include include/uapi/asm-generic/Kbuild.asm
|
||||
|
||||
generic-y += types.h
|
||||
|
||||
header-y += auxvec.h
|
||||
header-y += bitsperlong.h
|
||||
header-y += byteorder.h
|
||||
|
@ -31,5 +33,4 @@ header-y += statfs.h
|
|||
header-y += swab.h
|
||||
header-y += termbits.h
|
||||
header-y += termios.h
|
||||
header-y += types.h
|
||||
header-y += unistd.h
|
||||
|
|
|
@ -1 +0,0 @@
|
|||
#include <asm-generic/types.h>
|
|
@ -112,7 +112,4 @@ void set_cpuinfo_pvr_full(struct cpuinfo *ci, struct device_node *cpu)
|
|||
CI(num_wr_brk, NUMBER_OF_WR_ADDR_BRK);
|
||||
|
||||
CI(fpga_family_code, TARGET_FAMILY);
|
||||
|
||||
/* take timebase-frequency from DTS */
|
||||
ci->cpu_clock_freq = fcpu(cpu, "timebase-frequency");
|
||||
}
|
||||
|
|
|
@ -113,8 +113,6 @@ void __init set_cpuinfo_static(struct cpuinfo *ci, struct device_node *cpu)
|
|||
ci->num_rd_brk = fcpu(cpu, "xlnx,number-of-rd-addr-brk");
|
||||
ci->num_wr_brk = fcpu(cpu, "xlnx,number-of-wr-addr-brk");
|
||||
|
||||
ci->cpu_clock_freq = fcpu(cpu, "timebase-frequency");
|
||||
|
||||
ci->pvr_user1 = fcpu(cpu, "xlnx,pvr-user1");
|
||||
ci->pvr_user2 = fcpu(cpu, "xlnx,pvr-user2");
|
||||
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
* for more details.
|
||||
*/
|
||||
|
||||
#include <linux/clk.h>
|
||||
#include <linux/init.h>
|
||||
#include <asm/cpuinfo.h>
|
||||
#include <asm/pvr.h>
|
||||
|
@ -39,6 +40,7 @@ const struct cpu_ver_key cpu_ver_lookup[] = {
|
|||
{"8.30.a", 0x17},
|
||||
{"8.40.a", 0x18},
|
||||
{"8.40.b", 0x19},
|
||||
{"8.50.a", 0x1a},
|
||||
{"9.0", 0x1b},
|
||||
{"9.1", 0x1d},
|
||||
{NULL, 0},
|
||||
|
@ -68,11 +70,10 @@ const struct family_string_key family_string_lookup[] = {
|
|||
};
|
||||
|
||||
struct cpuinfo cpuinfo;
|
||||
static struct device_node *cpu;
|
||||
|
||||
void __init setup_cpuinfo(void)
|
||||
{
|
||||
struct device_node *cpu = NULL;
|
||||
|
||||
cpu = (struct device_node *) of_find_node_by_type(NULL, "cpu");
|
||||
if (!cpu)
|
||||
pr_err("You don't have cpu!!!\n");
|
||||
|
@ -102,3 +103,22 @@ void __init setup_cpuinfo(void)
|
|||
pr_warn("%s: Stream instructions enabled"
|
||||
" - USERSPACE CAN LOCK THIS KERNEL!\n", __func__);
|
||||
}
|
||||
|
||||
void __init setup_cpuinfo_clk(void)
|
||||
{
|
||||
struct clk *clk;
|
||||
|
||||
clk = of_clk_get(cpu, 0);
|
||||
if (IS_ERR(clk)) {
|
||||
pr_err("ERROR: CPU CCF input clock not found\n");
|
||||
/* take timebase-frequency from DTS */
|
||||
cpuinfo.cpu_clock_freq = fcpu(cpu, "timebase-frequency");
|
||||
} else {
|
||||
cpuinfo.cpu_clock_freq = clk_get_rate(clk);
|
||||
}
|
||||
|
||||
if (!cpuinfo.cpu_clock_freq) {
|
||||
pr_err("ERROR: CPU clock frequency not setup\n");
|
||||
BUG();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -64,6 +64,10 @@ real_start:
|
|||
#endif
|
||||
|
||||
mts rmsr, r0
|
||||
/* Disable stack protection from bootloader */
|
||||
mts rslr, r0
|
||||
addi r8, r0, 0xFFFFFFF
|
||||
mts rshr, r8
|
||||
/*
|
||||
* According to Xilinx, msrclr instruction behaves like 'mfs rX,rpc'
|
||||
* if the msrclr instruction is not enabled. We use this to detect
|
||||
|
|
|
@ -147,15 +147,14 @@
|
|||
or r3, r0, NUM_TO_REG (regnum);
|
||||
|
||||
/* Shift right instruction depending on available configuration */
|
||||
#if CONFIG_XILINX_MICROBLAZE0_USE_BARREL > 0
|
||||
#define BSRLI(rD, rA, imm) \
|
||||
bsrli rD, rA, imm
|
||||
#else
|
||||
#define BSRLI(rD, rA, imm) BSRLI ## imm (rD, rA)
|
||||
#if CONFIG_XILINX_MICROBLAZE0_USE_BARREL == 0
|
||||
/* Only the used shift constants defined here - add more if needed */
|
||||
#define BSRLI2(rD, rA) \
|
||||
srl rD, rA; /* << 1 */ \
|
||||
srl rD, rD; /* << 2 */
|
||||
#define BSRLI4(rD, rA) \
|
||||
BSRLI2(rD, rA); \
|
||||
BSRLI2(rD, rD)
|
||||
#define BSRLI10(rD, rA) \
|
||||
srl rD, rA; /* << 1 */ \
|
||||
srl rD, rD; /* << 2 */ \
|
||||
|
@ -170,7 +169,33 @@
|
|||
#define BSRLI20(rD, rA) \
|
||||
BSRLI10(rD, rA); \
|
||||
BSRLI10(rD, rD)
|
||||
|
||||
.macro bsrli, rD, rA, IMM
|
||||
.if (\IMM) == 2
|
||||
BSRLI2(\rD, \rA)
|
||||
.elseif (\IMM) == 10
|
||||
BSRLI10(\rD, \rA)
|
||||
.elseif (\IMM) == 12
|
||||
BSRLI2(\rD, \rA)
|
||||
BSRLI10(\rD, \rD)
|
||||
.elseif (\IMM) == 14
|
||||
BSRLI4(\rD, \rA)
|
||||
BSRLI10(\rD, \rD)
|
||||
.elseif (\IMM) == 20
|
||||
BSRLI20(\rD, \rA)
|
||||
.elseif (\IMM) == 24
|
||||
BSRLI4(\rD, \rA)
|
||||
BSRLI20(\rD, \rD)
|
||||
.elseif (\IMM) == 28
|
||||
BSRLI4(\rD, \rA)
|
||||
BSRLI4(\rD, \rD)
|
||||
BSRLI20(\rD, \rD)
|
||||
.else
|
||||
.error "BSRLI shift macros \IMM"
|
||||
.endif
|
||||
.endm
|
||||
#endif
|
||||
|
||||
#endif /* CONFIG_MMU */
|
||||
|
||||
.extern other_exception_handler /* Defined in exception.c */
|
||||
|
@ -604,7 +629,7 @@ ex_handler_done:
|
|||
ex4:
|
||||
tophys(r4,r4)
|
||||
/* Create L1 (pgdir/pmd) address */
|
||||
BSRLI(r5,r3, PGDIR_SHIFT - 2)
|
||||
bsrli r5, r3, PGDIR_SHIFT - 2
|
||||
andi r5, r5, PAGE_SIZE - 4
|
||||
/* Assume pgdir aligned on 4K boundary, no need for "andi r4,r4,0xfffff003" */
|
||||
or r4, r4, r5
|
||||
|
@ -613,7 +638,7 @@ ex_handler_done:
|
|||
beqi r5, ex2 /* Bail if no table */
|
||||
|
||||
tophys(r5,r5)
|
||||
BSRLI(r6,r3,PTE_SHIFT) /* Compute PTE address */
|
||||
bsrli r6, r3, PTE_SHIFT /* Compute PTE address */
|
||||
andi r6, r6, PAGE_SIZE - 4
|
||||
or r5, r5, r6
|
||||
lwi r4, r5, 0 /* Get Linux PTE */
|
||||
|
@ -705,7 +730,7 @@ ex_handler_done:
|
|||
ex6:
|
||||
tophys(r4,r4)
|
||||
/* Create L1 (pgdir/pmd) address */
|
||||
BSRLI(r5,r3, PGDIR_SHIFT - 2)
|
||||
bsrli r5, r3, PGDIR_SHIFT - 2
|
||||
andi r5, r5, PAGE_SIZE - 4
|
||||
/* Assume pgdir aligned on 4K boundary, no need for "andi r4,r4,0xfffff003" */
|
||||
or r4, r4, r5
|
||||
|
@ -714,7 +739,7 @@ ex_handler_done:
|
|||
beqi r5, ex7 /* Bail if no table */
|
||||
|
||||
tophys(r5,r5)
|
||||
BSRLI(r6,r3,PTE_SHIFT) /* Compute PTE address */
|
||||
bsrli r6, r3, PTE_SHIFT /* Compute PTE address */
|
||||
andi r6, r6, PAGE_SIZE - 4
|
||||
or r5, r5, r6
|
||||
lwi r4, r5, 0 /* Get Linux PTE */
|
||||
|
@ -776,7 +801,7 @@ ex_handler_done:
|
|||
ex9:
|
||||
tophys(r4,r4)
|
||||
/* Create L1 (pgdir/pmd) address */
|
||||
BSRLI(r5,r3, PGDIR_SHIFT - 2)
|
||||
bsrli r5, r3, PGDIR_SHIFT - 2
|
||||
andi r5, r5, PAGE_SIZE - 4
|
||||
/* Assume pgdir aligned on 4K boundary, no need for "andi r4,r4,0xfffff003" */
|
||||
or r4, r4, r5
|
||||
|
@ -785,7 +810,7 @@ ex_handler_done:
|
|||
beqi r5, ex10 /* Bail if no table */
|
||||
|
||||
tophys(r5,r5)
|
||||
BSRLI(r6,r3,PTE_SHIFT) /* Compute PTE address */
|
||||
bsrli r6, r3, PTE_SHIFT /* Compute PTE address */
|
||||
andi r6, r6, PAGE_SIZE - 4
|
||||
or r5, r5, r6
|
||||
lwi r4, r5, 0 /* Get Linux PTE */
|
||||
|
@ -922,7 +947,7 @@ ex_handler_done:
|
|||
.ent _unaligned_data_exception
|
||||
_unaligned_data_exception:
|
||||
andi r8, r3, 0x3E0; /* Mask and extract the register operand */
|
||||
BSRLI(r8,r8,2); /* r8 >> 2 = register operand * 8 */
|
||||
bsrli r8, r8, 2; /* r8 >> 2 = register operand * 8 */
|
||||
andi r6, r3, 0x400; /* Extract ESR[S] */
|
||||
bneid r6, ex_sw_vm;
|
||||
andi r6, r3, 0x800; /* Extract ESR[W] - delay slot */
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
*/
|
||||
|
||||
#include <linux/init.h>
|
||||
#include <linux/clk-provider.h>
|
||||
#include <linux/clocksource.h>
|
||||
#include <linux/string.h>
|
||||
#include <linux/seq_file.h>
|
||||
|
@ -136,7 +137,7 @@ void __init machine_early_init(const char *cmdline, unsigned int ram,
|
|||
lockdep_init();
|
||||
|
||||
/* initialize device tree for usage in early_printk */
|
||||
early_init_devtree((void *)_fdt_start);
|
||||
early_init_devtree(_fdt_start);
|
||||
|
||||
#ifdef CONFIG_EARLY_PRINTK
|
||||
setup_early_printk(NULL);
|
||||
|
@ -152,8 +153,7 @@ void __init machine_early_init(const char *cmdline, unsigned int ram,
|
|||
if (fdt)
|
||||
pr_info("FDT at 0x%08x\n", fdt);
|
||||
else
|
||||
pr_info("Compiled-in FDT at 0x%08x\n",
|
||||
(unsigned int)_fdt_start);
|
||||
pr_info("Compiled-in FDT at %p\n", _fdt_start);
|
||||
|
||||
#ifdef CONFIG_MTD_UCLINUX
|
||||
pr_info("Found romfs @ 0x%08x (0x%08x)\n",
|
||||
|
@ -175,7 +175,7 @@ void __init machine_early_init(const char *cmdline, unsigned int ram,
|
|||
#else
|
||||
if (!msr) {
|
||||
pr_info("!!!Your kernel not setup MSR instruction but ");
|
||||
pr_cont"CPU have it %x\n", msr);
|
||||
pr_cont("CPU have it %x\n", msr);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -196,6 +196,8 @@ void __init machine_early_init(const char *cmdline, unsigned int ram,
|
|||
|
||||
void __init time_init(void)
|
||||
{
|
||||
of_clk_init(NULL);
|
||||
setup_cpuinfo_clk();
|
||||
clocksource_of_init();
|
||||
}
|
||||
|
||||
|
|
|
@ -12,12 +12,12 @@
|
|||
#include <linux/interrupt.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/sched_clock.h>
|
||||
#include <linux/clk.h>
|
||||
#include <linux/clockchips.h>
|
||||
#include <linux/of_address.h>
|
||||
#include <linux/of_irq.h>
|
||||
#include <asm/cpuinfo.h>
|
||||
#include <linux/cnt32_to_63.h>
|
||||
|
||||
static void __iomem *timer_baseaddr;
|
||||
|
||||
|
@ -167,10 +167,15 @@ static __init void xilinx_clockevent_init(void)
|
|||
clockevents_register_device(&clockevent_xilinx_timer);
|
||||
}
|
||||
|
||||
static u64 xilinx_clock_read(void)
|
||||
{
|
||||
return in_be32(timer_baseaddr + TCR1);
|
||||
}
|
||||
|
||||
static cycle_t xilinx_read(struct clocksource *cs)
|
||||
{
|
||||
/* reading actual value of timer 1 */
|
||||
return (cycle_t) (in_be32(timer_baseaddr + TCR1));
|
||||
return (cycle_t)xilinx_clock_read();
|
||||
}
|
||||
|
||||
static struct timecounter xilinx_tc = {
|
||||
|
@ -222,17 +227,17 @@ static int __init xilinx_clocksource_init(void)
|
|||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* We have to protect accesses before timer initialization
|
||||
* and return 0 for sched_clock function below.
|
||||
*/
|
||||
static int timer_initialized;
|
||||
|
||||
static void __init xilinx_timer_init(struct device_node *timer)
|
||||
{
|
||||
struct clk *clk;
|
||||
static int initialized;
|
||||
u32 irq;
|
||||
u32 timer_num = 1;
|
||||
int ret;
|
||||
|
||||
if (initialized)
|
||||
return;
|
||||
|
||||
initialized = 1;
|
||||
|
||||
timer_baseaddr = of_iomap(timer, 0);
|
||||
if (!timer_baseaddr) {
|
||||
|
@ -250,10 +255,20 @@ static void __init xilinx_timer_init(struct device_node *timer)
|
|||
|
||||
pr_info("%s: irq=%d\n", timer->full_name, irq);
|
||||
|
||||
/* If there is clock-frequency property than use it */
|
||||
ret = of_property_read_u32(timer, "clock-frequency", &timer_clock_freq);
|
||||
if (ret < 0)
|
||||
clk = of_clk_get(timer, 0);
|
||||
if (IS_ERR(clk)) {
|
||||
pr_err("ERROR: timer CCF input clock not found\n");
|
||||
/* If there is clock-frequency property than use it */
|
||||
of_property_read_u32(timer, "clock-frequency",
|
||||
&timer_clock_freq);
|
||||
} else {
|
||||
timer_clock_freq = clk_get_rate(clk);
|
||||
}
|
||||
|
||||
if (!timer_clock_freq) {
|
||||
pr_err("ERROR: Using CPU clock frequency\n");
|
||||
timer_clock_freq = cpuinfo.cpu_clock_freq;
|
||||
}
|
||||
|
||||
freq_div_hz = timer_clock_freq / HZ;
|
||||
|
||||
|
@ -263,18 +278,8 @@ static void __init xilinx_timer_init(struct device_node *timer)
|
|||
#endif
|
||||
xilinx_clocksource_init();
|
||||
xilinx_clockevent_init();
|
||||
timer_initialized = 1;
|
||||
}
|
||||
|
||||
unsigned long long notrace sched_clock(void)
|
||||
{
|
||||
if (timer_initialized) {
|
||||
struct clocksource *cs = &clocksource_microblaze;
|
||||
|
||||
cycle_t cyc = cnt32_to_63(cs->read(NULL)) & LLONG_MAX;
|
||||
return clocksource_cyc2ns(cyc, cs->mult, cs->shift);
|
||||
}
|
||||
return 0;
|
||||
sched_clock_register(xilinx_clock_read, 32, timer_clock_freq);
|
||||
}
|
||||
|
||||
CLOCKSOURCE_OF_DECLARE(xilinx_timer, "xlnx,xps-timer-1.00.a",
|
||||
|
|
|
@ -51,6 +51,7 @@ SECTIONS {
|
|||
. = ALIGN(16);
|
||||
RODATA
|
||||
EXCEPTION_TABLE(16)
|
||||
NOTES
|
||||
|
||||
/*
|
||||
* sdata2 section can go anywhere, but must be word aligned
|
||||
|
|
Loading…
Reference in a new issue