Add support for Armada XP A0.
- Add functions to calculate clocks instead using hardcoded values - Update reset and timers functions - Update number of interrupts - Change name of platform from db88f78100 to db78460 - Correct DRAM size and PCI IRQ routing in dts file. Obtained from: Semihalf
This commit is contained in:
parent
68b7bd0469
commit
d65cdf4b9d
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=240488
@ -99,4 +99,4 @@ device vlan
|
||||
#FDT
|
||||
options FDT
|
||||
options FDT_DTB_STATIC
|
||||
makeoptions FDT_DTS_FILE=db88f78160.dts
|
||||
makeoptions FDT_DTS_FILE=db78460.dts
|
||||
|
@ -54,6 +54,8 @@
|
||||
#define NIRQ 128
|
||||
#elif defined(CPU_ARM11)
|
||||
#define NIRQ 128
|
||||
#elif defined(SOC_MV_ARMADAXP)
|
||||
#define NIRQ 148
|
||||
#else
|
||||
#define NIRQ 32
|
||||
#endif
|
||||
|
@ -34,6 +34,7 @@ __FBSDID("$FreeBSD$");
|
||||
#include <sys/bus.h>
|
||||
|
||||
#include <machine/bus.h>
|
||||
#include <machine/armreg.h>
|
||||
|
||||
#include <arm/mv/mvreg.h>
|
||||
#include <arm/mv/mvvar.h>
|
||||
@ -43,24 +44,120 @@ __FBSDID("$FreeBSD$");
|
||||
|
||||
#include <machine/fdt.h>
|
||||
|
||||
#define CPU_FREQ_FIELD(sar) (((0x01 & (sar >> 52)) << 3) | \
|
||||
(0x07 & (sar >> 21)))
|
||||
#define FAB_FREQ_FIELD(sar) (((0x01 & (sar >> 51)) << 4) | \
|
||||
(0x0F & (sar >> 24)))
|
||||
|
||||
static uint32_t count_l2clk(void);
|
||||
|
||||
/* XXX Make gpio driver optional and remove it */
|
||||
struct resource_spec mv_gpio_res[] = {
|
||||
{ SYS_RES_MEMORY, 0, RF_ACTIVE },
|
||||
{ SYS_RES_IRQ, 0, RF_ACTIVE },
|
||||
{ -1, 0 }
|
||||
};
|
||||
|
||||
struct vco_freq_ratio {
|
||||
uint8_t vco_cpu; /* VCO to CLK0(CPU) clock ratio */
|
||||
uint8_t vco_l2c; /* VCO to NB(L2 cache) clock ratio */
|
||||
uint8_t vco_hcl; /* VCO to HCLK(DDR controller) clock ratio */
|
||||
uint8_t vco_ddr; /* VCO to DR(DDR memory) clock ratio */
|
||||
};
|
||||
|
||||
static struct vco_freq_ratio freq_conf_table[] = {
|
||||
/*00*/ { 1, 1, 4, 2 },
|
||||
/*01*/ { 1, 2, 2, 2 },
|
||||
/*02*/ { 2, 2, 6, 3 },
|
||||
/*03*/ { 2, 2, 3, 3 },
|
||||
/*04*/ { 1, 2, 3, 3 },
|
||||
/*05*/ { 1, 2, 4, 2 },
|
||||
/*06*/ { 1, 1, 2, 2 },
|
||||
/*07*/ { 2, 3, 6, 6 },
|
||||
/*08*/ { 2, 3, 5, 5 },
|
||||
/*09*/ { 1, 2, 6, 3 },
|
||||
/*10*/ { 2, 4, 10, 5 },
|
||||
/*11*/ { 1, 3, 6, 6 },
|
||||
/*12*/ { 1, 2, 5, 5 },
|
||||
/*13*/ { 1, 3, 6, 3 },
|
||||
/*14*/ { 1, 2, 5, 5 },
|
||||
/*15*/ { 2, 2, 5, 5 },
|
||||
/*16*/ { 1, 1, 3, 3 },
|
||||
/*17*/ { 2, 5, 10, 10 },
|
||||
/*18*/ { 1, 3, 8, 4 },
|
||||
/*19*/ { 1, 1, 2, 1 },
|
||||
/*20*/ { 2, 3, 6, 3 },
|
||||
/*21*/ { 1, 2, 8, 4 },
|
||||
/*22*/ { 2, 5, 10, 5 }
|
||||
};
|
||||
|
||||
static uint16_t cpu_clock_table[] = {
|
||||
1000, 1066, 1200, 1333, 1500, 1666, 1800, 2000, 600, 667, 800, 1600,
|
||||
2133, 2200, 2400 };
|
||||
|
||||
uint32_t
|
||||
get_tclk(void)
|
||||
{
|
||||
uint32_t cputype;
|
||||
|
||||
cputype = cpufunc_id();
|
||||
cputype &= CPU_ID_CPU_MASK;
|
||||
|
||||
if (cputype == CPU_ID_MV88SV584X_V7)
|
||||
return (TCLK_250MHZ);
|
||||
else
|
||||
return (TCLK_200MHZ);
|
||||
}
|
||||
|
||||
static uint32_t
|
||||
count_l2clk(void)
|
||||
{
|
||||
uint64_t sar_reg;
|
||||
uint32_t freq_vco, freq_l2clk;
|
||||
uint8_t sar_cpu_freq, sar_fab_freq, array_size;
|
||||
|
||||
/* Get value of the SAR register and process it */
|
||||
sar_reg = get_sar_value();
|
||||
sar_cpu_freq = CPU_FREQ_FIELD(sar_reg);
|
||||
sar_fab_freq = FAB_FREQ_FIELD(sar_reg);
|
||||
|
||||
/* Check if CPU frequency field has correct value */
|
||||
array_size = sizeof(cpu_clock_table) / sizeof(cpu_clock_table[0]);
|
||||
if (sar_cpu_freq >= array_size)
|
||||
panic("Reserved value in cpu frequency configuration field: "
|
||||
"%d", sar_cpu_freq);
|
||||
|
||||
/* Check if fabric frequency field has correct value */
|
||||
array_size = sizeof(freq_conf_table) / sizeof(freq_conf_table[0]);
|
||||
if (sar_fab_freq >= array_size)
|
||||
panic("Reserved value in fabric frequency configuration field: "
|
||||
"%d", sar_fab_freq);
|
||||
|
||||
/* Get CPU clock frequency */
|
||||
freq_vco = cpu_clock_table[sar_cpu_freq] *
|
||||
freq_conf_table[sar_fab_freq].vco_cpu;
|
||||
|
||||
/* Get L2CLK clock frequency */
|
||||
freq_l2clk = freq_vco / freq_conf_table[sar_fab_freq].vco_l2c;
|
||||
|
||||
/* Round L2CLK value to integer MHz */
|
||||
if (((freq_vco % freq_conf_table[sar_fab_freq].vco_l2c) * 10 /
|
||||
freq_conf_table[sar_fab_freq].vco_l2c) >= 5)
|
||||
freq_l2clk++;
|
||||
|
||||
return (freq_l2clk * 1000000);
|
||||
}
|
||||
|
||||
uint32_t
|
||||
get_l2clk(void)
|
||||
{
|
||||
static uint32_t l2clk_freq = 0;
|
||||
|
||||
return (TCLK_667MHZ);
|
||||
/* If get_l2clk is called first time get L2CLK value from register */
|
||||
if (l2clk_freq == 0)
|
||||
l2clk_freq = count_l2clk();
|
||||
|
||||
return (l2clk_freq);
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -249,12 +249,47 @@ write_cpu_ctrl(uint32_t reg, uint32_t val)
|
||||
bus_space_write_4(fdtbus_bs_tag, MV_CPU_CONTROL_BASE, reg, val);
|
||||
}
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
uint32_t
|
||||
read_cpu_mp_clocks(uint32_t reg)
|
||||
{
|
||||
|
||||
return (bus_space_read_4(fdtbus_bs_tag, MV_MP_CLOCKS_BASE, reg));
|
||||
}
|
||||
|
||||
void
|
||||
write_cpu_mp_clocks(uint32_t reg, uint32_t val)
|
||||
{
|
||||
|
||||
bus_space_write_4(fdtbus_bs_tag, MV_MP_CLOCKS_BASE, reg, val);
|
||||
}
|
||||
|
||||
uint32_t
|
||||
read_cpu_misc(uint32_t reg)
|
||||
{
|
||||
|
||||
return (bus_space_read_4(fdtbus_bs_tag, MV_MISC_BASE, reg));
|
||||
}
|
||||
|
||||
void
|
||||
write_cpu_misc(uint32_t reg, uint32_t val)
|
||||
{
|
||||
|
||||
bus_space_write_4(fdtbus_bs_tag, MV_MISC_BASE, reg, val);
|
||||
}
|
||||
#endif
|
||||
|
||||
void
|
||||
cpu_reset(void)
|
||||
{
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
write_cpu_misc(RSTOUTn_MASK, SOFT_RST_OUT_EN);
|
||||
write_cpu_misc(SYSTEM_SOFT_RESET, SYS_SOFT_RST);
|
||||
#else
|
||||
write_cpu_ctrl(RSTOUTn_MASK, SOFT_RST_OUT_EN);
|
||||
write_cpu_ctrl(SYSTEM_SOFT_RESET, SYS_SOFT_RST);
|
||||
#endif
|
||||
while (1);
|
||||
}
|
||||
|
||||
@ -2062,19 +2097,26 @@ fdt_fixup_busfreq(phandle_t root)
|
||||
phandle_t sb;
|
||||
pcell_t freq;
|
||||
|
||||
freq = cpu_to_fdt32(get_tclk());
|
||||
|
||||
/*
|
||||
* Fix bus speed in cpu node
|
||||
*/
|
||||
if ((sb = OF_finddevice("cpu")) != 0)
|
||||
if (fdt_is_compatible_strict(sb, "ARM,88VS584"))
|
||||
OF_setprop(sb, "bus-frequency", (void *)&freq,
|
||||
sizeof(freq));
|
||||
|
||||
/*
|
||||
* This fixup sets the simple-bus bus-frequency property.
|
||||
*/
|
||||
|
||||
if ((sb = fdt_find_compatible(root, "simple-bus", 1)) == 0)
|
||||
return;
|
||||
|
||||
freq = cpu_to_fdt32(get_tclk());
|
||||
if ((sb = fdt_find_compatible(root, "simple-bus", 1)) != 0)
|
||||
OF_setprop(sb, "bus-frequency", (void *)&freq, sizeof(freq));
|
||||
}
|
||||
|
||||
struct fdt_fixup_entry fdt_fixup_table[] = {
|
||||
{ "mrvl,DB-88F6281", &fdt_fixup_busfreq },
|
||||
{ "mrvl,DB-78460", &fdt_fixup_busfreq },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
@ -2098,3 +2140,24 @@ fdt_pic_decode_t fdt_pic_table[] = {
|
||||
&fdt_pic_decode_ic,
|
||||
NULL
|
||||
};
|
||||
|
||||
uint64_t
|
||||
get_sar_value(void)
|
||||
{
|
||||
uint32_t sar_low, sar_high;
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
sar_high = bus_space_read_4(fdtbus_bs_tag, MV_MISC_BASE,
|
||||
SAMPLE_AT_RESET_HI);
|
||||
sar_low = bus_space_read_4(fdtbus_bs_tag, MV_MISC_BASE,
|
||||
SAMPLE_AT_RESET_LO);
|
||||
#else
|
||||
/*
|
||||
* TODO: Add getting proper values for other SoC configurations
|
||||
*/
|
||||
sar_high = 0;
|
||||
sar_low = 0;
|
||||
#endif
|
||||
|
||||
return (((uint64_t)sar_high << 32) | sar_low);
|
||||
}
|
||||
|
@ -123,11 +123,21 @@
|
||||
/*
|
||||
* System reset
|
||||
*/
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
#define RSTOUTn_MASK 0x60
|
||||
#define SYSTEM_SOFT_RESET 0x64
|
||||
#define WD_RSTOUTn_MASK 0x4
|
||||
#define WD_GLOBAL_MASK 0x00000100
|
||||
#define WD_CPU0_MASK 0x00000001
|
||||
#define SOFT_RST_OUT_EN 0x00000001
|
||||
#define SYS_SOFT_RST 0x00000001
|
||||
#else
|
||||
#define RSTOUTn_MASK 0x8
|
||||
#define WD_RST_OUT_EN 0x00000002
|
||||
#define SOFT_RST_OUT_EN 0x00000004
|
||||
#define SYSTEM_SOFT_RESET 0xc
|
||||
#define SYS_SOFT_RST 0x00000001
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Power Control
|
||||
@ -334,6 +344,9 @@
|
||||
#define SAMPLE_AT_RESET_HI 0x18
|
||||
#elif defined(SOC_MV_FREY)
|
||||
#define SAMPLE_AT_RESET 0x100
|
||||
#elif defined(SOC_MV_ARMADAXP)
|
||||
#define SAMPLE_AT_RESET_LO 0x30
|
||||
#define SAMPLE_AT_RESET_HI 0x34
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -89,6 +89,7 @@ void soc_id(uint32_t *dev, uint32_t *rev);
|
||||
void soc_dump_decode_win(void);
|
||||
uint32_t soc_power_ctrl_get(uint32_t mask);
|
||||
void soc_power_ctrl_set(uint32_t mask);
|
||||
uint64_t get_sar_value(void);
|
||||
|
||||
int decode_win_cpu_set(int target, int attr, vm_paddr_t base, uint32_t size,
|
||||
vm_paddr_t remap);
|
||||
@ -108,6 +109,13 @@ uint32_t get_l2clk(void);
|
||||
uint32_t read_cpu_ctrl(uint32_t);
|
||||
void write_cpu_ctrl(uint32_t, uint32_t);
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
uint32_t read_cpu_mp_clocks(uint32_t reg);
|
||||
void write_cpu_mp_clocks(uint32_t reg, uint32_t val);
|
||||
uint32_t read_cpu_misc(uint32_t reg);
|
||||
void write_cpu_misc(uint32_t reg, uint32_t val);
|
||||
#endif
|
||||
|
||||
int mv_pcib_bar_win_set(device_t dev, uint32_t base, uint32_t size,
|
||||
uint32_t remap, int winno, int busno);
|
||||
int mv_pcib_cpu_win_remap(device_t dev, uint32_t remap, uint32_t size);
|
||||
|
@ -128,8 +128,10 @@
|
||||
#define MV_MPP_BASE (MV_BASE + 0x10000)
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
#define MV_MISC_BASE (MV_BASE + 0x18200)
|
||||
#define MV_MBUS_BRIDGE_BASE (MV_BASE + 0x20000)
|
||||
#define MV_INTREGS_BASE (MV_MBUS_BRIDGE_BASE + 0x80)
|
||||
#define MV_MP_CLOCKS_BASE (MV_MBUS_BRIDGE_BASE + 0x700)
|
||||
#define MV_CPU_CONTROL_BASE (MV_MBUS_BRIDGE_BASE + 0x1800)
|
||||
#elif !defined(SOC_MV_FREY)
|
||||
#define MV_MBUS_BRIDGE_BASE (MV_BASE + 0x20000)
|
||||
|
@ -311,15 +311,19 @@ mv_watchdog_enable(void)
|
||||
irq_cause &= IRQ_TIMER_WD_CLR;
|
||||
write_cpu_ctrl(BRIDGE_IRQ_CAUSE, irq_cause);
|
||||
|
||||
#if !defined(SOC_MV_ARMADAXP)
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
val = read_cpu_mp_clocks(WD_RSTOUTn_MASK);
|
||||
val |= (WD_GLOBAL_MASK | WD_CPU0_MASK);
|
||||
write_cpu_mp_clocks(WD_RSTOUTn_MASK, val);
|
||||
#else
|
||||
irq_mask = read_cpu_ctrl(BRIDGE_IRQ_MASK);
|
||||
irq_mask |= IRQ_TIMER_WD_MASK;
|
||||
write_cpu_ctrl(BRIDGE_IRQ_MASK, irq_mask);
|
||||
#endif
|
||||
|
||||
val = read_cpu_ctrl(RSTOUTn_MASK);
|
||||
val |= WD_RST_OUT_EN;
|
||||
write_cpu_ctrl(RSTOUTn_MASK, val);
|
||||
#endif
|
||||
|
||||
val = mv_get_timer_control();
|
||||
val |= CPU_TIMER_WD_EN | CPU_TIMER_WD_AUTO;
|
||||
@ -338,11 +342,15 @@ mv_watchdog_disable(void)
|
||||
val &= ~(CPU_TIMER_WD_EN | CPU_TIMER_WD_AUTO);
|
||||
mv_set_timer_control(val);
|
||||
|
||||
#if defined(SOC_MV_ARMADAXP)
|
||||
val = read_cpu_mp_clocks(WD_RSTOUTn_MASK);
|
||||
val &= ~(WD_GLOBAL_MASK | WD_CPU0_MASK);
|
||||
write_cpu_mp_clocks(WD_RSTOUTn_MASK, val);
|
||||
#else
|
||||
val = read_cpu_ctrl(RSTOUTn_MASK);
|
||||
val &= ~WD_RST_OUT_EN;
|
||||
write_cpu_ctrl(RSTOUTn_MASK, val);
|
||||
|
||||
#if !defined(SOC_MV_ARMADAXP)
|
||||
irq_mask = read_cpu_ctrl(BRIDGE_IRQ_MASK);
|
||||
irq_mask &= ~(IRQ_TIMER_WD_MASK);
|
||||
write_cpu_ctrl(BRIDGE_IRQ_MASK, irq_mask);
|
||||
|
@ -24,7 +24,7 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* Marvell DB-88F78160 Device Tree Source.
|
||||
* Marvell DB-78460 Device Tree Source.
|
||||
*
|
||||
* $FreeBSD$
|
||||
*/
|
||||
@ -32,7 +32,7 @@
|
||||
/dts-v1/;
|
||||
|
||||
/ {
|
||||
model = "mrvl,DB-78160";
|
||||
model = "mrvl,DB-78460";
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
|
||||
@ -60,10 +60,10 @@
|
||||
|
||||
memory {
|
||||
device_type = "memory";
|
||||
reg = <0x0 0x40000000>; // 2G at 0x0
|
||||
reg = <0x0 0x80000000>; // 2G at 0x0
|
||||
};
|
||||
|
||||
soc78160@d0000000 {
|
||||
soc78460@d0000000 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
compatible = "simple-bus";
|
||||
@ -115,7 +115,7 @@
|
||||
reg = <0x12000 0x20>;
|
||||
reg-shift = <2>;
|
||||
current-speed = <115200>;
|
||||
clock-frequency = <200000000>;
|
||||
clock-frequency = <0>;
|
||||
interrupts = <41>;
|
||||
interrupt-parent = <&MPIC>;
|
||||
};
|
||||
@ -125,7 +125,7 @@
|
||||
reg = <0x12100 0x20>;
|
||||
reg-shift = <2>;
|
||||
current-speed = <115200>;
|
||||
clock-frequency = <200000000>;
|
||||
clock-frequency = <0>;
|
||||
interrupts = <42>;
|
||||
interrupt-parent = <&MPIC>;
|
||||
};
|
||||
@ -135,7 +135,7 @@
|
||||
reg = <0x12200 0x20>;
|
||||
reg-shift = <2>;
|
||||
current-speed = <115200>;
|
||||
clock-frequency = <200000000>;
|
||||
clock-frequency = <0>;
|
||||
interrupts = <43>;
|
||||
interrupt-parent = <&MPIC>;
|
||||
};
|
||||
@ -145,7 +145,7 @@
|
||||
reg = <0x12300 0x20>;
|
||||
reg-shift = <2>;
|
||||
current-speed = <115200>;
|
||||
clock-frequency = <200000000>;
|
||||
clock-frequency = <0>;
|
||||
interrupts = <44>;
|
||||
interrupt-parent = <&MPIC>;
|
||||
};
|
||||
@ -281,25 +281,25 @@
|
||||
};
|
||||
};
|
||||
|
||||
pci0: pcie@f1040000 {
|
||||
pci0: pcie@d0040000 {
|
||||
compatible = "mrvl,pcie";
|
||||
device_type = "pci";
|
||||
#interrupt-cells = <1>;
|
||||
#size-cells = <2>;
|
||||
#address-cells = <3>;
|
||||
reg = <0xf1040000 0x2000>;
|
||||
reg = <0xd0040000 0x2000>;
|
||||
bus-range = <0 255>;
|
||||
ranges = <0x02000000 0x0 0x80000000 0x80000000 0x0 0x20000000
|
||||
0x01000000 0x0 0x00000000 0xa0000000 0x0 0x08000000>;
|
||||
clock-frequency = <33333333>;
|
||||
interrupt-parent = <&MPIC>;
|
||||
interrupts = <58>;
|
||||
interrupts = <120>;
|
||||
interrupt-map-mask = <0xf800 0x0 0x0 0x7>;
|
||||
interrupt-map = <
|
||||
0x0800 0x0 0x0 0x1 &MPIC 0x20
|
||||
0x0800 0x0 0x0 0x2 &MPIC 0x21
|
||||
0x0800 0x0 0x0 0x3 &MPIC 0x22
|
||||
0x0800 0x0 0x0 0x4 &MPIC 0x23
|
||||
0x0800 0x0 0x0 0x1 &MPIC 0x3A
|
||||
0x0800 0x0 0x0 0x2 &MPIC 0x3A
|
||||
0x0800 0x0 0x0 0x3 &MPIC 0x3A
|
||||
0x0800 0x0 0x0 0x4 &MPIC 0x3A
|
||||
>;
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user