Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit cecc4e92 authored by David S. Miller's avatar David S. Miller
Browse files

[SPARC64]: Convert central bus layer to in-kernel PROM device tree.

parent 9c10a58e
Loading
Loading
Loading
Loading
+63 −64
Original line number Diff line number Diff line
@@ -29,28 +29,34 @@ static void central_probe_failure(int line)
	prom_halt();
}

static void central_ranges_init(int cnode, struct linux_central *central)
static void central_ranges_init(struct linux_central *central)
{
	int success;
	struct device_node *dp = central->prom_node;
	void *pval;
	int len;
	
	central->num_central_ranges = 0;
	success = prom_getproperty(central->prom_node, "ranges",
				   (char *) central->central_ranges,
				   sizeof (central->central_ranges));
	if (success != -1)
		central->num_central_ranges = (success/sizeof(struct linux_prom_ranges));
	pval = of_get_property(dp, "ranges", &len);
	if (pval) {
		memcpy(central->central_ranges, pval, len);
		central->num_central_ranges =
			(len / sizeof(struct linux_prom_ranges));
	}
}

static void fhc_ranges_init(int fnode, struct linux_fhc *fhc)
static void fhc_ranges_init(struct linux_fhc *fhc)
{
	int success;
	struct device_node *dp = fhc->prom_node;
	void *pval;
	int len;
	
	fhc->num_fhc_ranges = 0;
	success = prom_getproperty(fhc->prom_node, "ranges",
				   (char *) fhc->fhc_ranges,
				   sizeof (fhc->fhc_ranges));
	if (success != -1)
		fhc->num_fhc_ranges = (success/sizeof(struct linux_prom_ranges));
	pval = of_get_property(dp, "ranges", &len);
	if (pval) {
		memcpy(fhc->fhc_ranges, pval, len);
		fhc->num_fhc_ranges =
			(len / sizeof(struct linux_prom_ranges));
	}
}

/* Range application routines are exported to various drivers,
@@ -112,15 +118,10 @@ static unsigned long prom_reg_to_paddr(struct linux_prom_registers *r)

static void probe_other_fhcs(void)
{
	struct linux_prom64_registers fpregs[6];
	char namebuf[128];
	int node;
	struct device_node *dp;
	struct linux_prom64_registers *fpregs;

	node = prom_getchild(prom_root_node);
	node = prom_searchsiblings(node, "fhc");
	if (node == 0)
		central_probe_failure(__LINE__);
	while (node) {
	for_each_node_by_name(dp, "fhc") {
		struct linux_fhc *fhc;
		int board;
		u32 tmp;
@@ -137,14 +138,12 @@ static void probe_other_fhcs(void)
		/* Toplevel FHCs have no parent. */
		fhc->parent = NULL;
		
		fhc->prom_node = node;
		prom_getstring(node, "name", namebuf, sizeof(namebuf));
		strcpy(fhc->prom_name, namebuf);
		fhc_ranges_init(node, fhc);
		fhc->prom_node = dp;
		fhc_ranges_init(fhc);

		/* Non-central FHC's have 64-bit OBP format registers. */
		if (prom_getproperty(node, "reg",
				    (char *)&fpregs[0], sizeof(fpregs)) == -1)
		fpregs = of_get_property(dp, "reg", NULL);
		if (!fpregs)
			central_probe_failure(__LINE__);

		/* Only central FHC needs special ranges applied. */
@@ -155,7 +154,7 @@ static void probe_other_fhcs(void)
		fhc->fhc_regs.uregs = fpregs[4].phys_addr;
		fhc->fhc_regs.tregs = fpregs[5].phys_addr;

		board = prom_getintdefault(node, "board#", -1);
		board = of_getintprop_default(dp, "board#", -1);
		fhc->board = board;

		tmp = upa_readl(fhc->fhc_regs.pregs + FHC_PREGS_JCTRL);
@@ -179,33 +178,33 @@ static void probe_other_fhcs(void)
		tmp = upa_readl(fhc->fhc_regs.pregs + FHC_PREGS_CTRL);
		tmp |= FHC_CONTROL_IXIST;
		upa_writel(tmp, fhc->fhc_regs.pregs + FHC_PREGS_CTRL);

		/* Look for the next FHC. */
		node = prom_getsibling(node);
		if (node == 0)
			break;
		node = prom_searchsiblings(node, "fhc");
		if (node == 0)
			break;
	}
}

static void probe_clock_board(struct linux_central *central,
			      struct linux_fhc *fhc,
			      int cnode, int fnode)
			      struct device_node *fp)
{
	struct linux_prom_registers cregs[3];
	int clknode, nslots, tmp, nregs;
	struct device_node *dp;
	struct linux_prom_registers cregs[3], *pr;
	int nslots, tmp, nregs;

	clknode = prom_searchsiblings(prom_getchild(fnode), "clock-board");
	if (clknode == 0 || clknode == -1)
	dp = fp->child;
	while (dp) {
		if (!strcmp(dp->name, "clock-board"))
			break;
		dp = dp->sibling;
	}
	if (!dp)
		central_probe_failure(__LINE__);

	nregs = prom_getproperty(clknode, "reg", (char *)&cregs[0], sizeof(cregs));
	if (nregs == -1)
	pr = of_get_property(dp, "reg", &nregs);
	if (!pr)
		central_probe_failure(__LINE__);

	memcpy(cregs, pr, nregs);
	nregs /= sizeof(struct linux_prom_registers);

	apply_fhc_ranges(fhc, &cregs[0], nregs);
	apply_central_ranges(central, &cregs[0], nregs);
	central->cfreg = prom_reg_to_paddr(&cregs[0]);
@@ -296,13 +295,13 @@ static void init_all_fhc_hw(void)

void central_probe(void)
{
	struct linux_prom_registers fpregs[6];
	struct linux_prom_registers fpregs[6], *pr;
	struct linux_fhc *fhc;
	char namebuf[128];
	int cnode, fnode, err;
	struct device_node *dp, *fp;
	int err;

	cnode = prom_finddevice("/central");
	if (cnode == 0 || cnode == -1) {
	dp = of_find_node_by_name(NULL, "central");
	if (!dp) {
		if (this_is_starfire)
			starfire_cpu_setup();
		return;
@@ -321,31 +320,31 @@ void central_probe(void)

	/* First init central. */
	central_bus->child = fhc;
	central_bus->prom_node = cnode;

	prom_getstring(cnode, "name", namebuf, sizeof(namebuf));
	strcpy(central_bus->prom_name, namebuf);

	central_ranges_init(cnode, central_bus);
	central_bus->prom_node = dp;
	central_ranges_init(central_bus);

	/* And then central's FHC. */
	fhc->next = fhc_list;
	fhc_list = fhc;

	fhc->parent = central_bus;
	fnode = prom_searchsiblings(prom_getchild(cnode), "fhc");
	if (fnode == 0 || fnode == -1)
	fp = dp->child;
	while (fp) {
		if (!strcmp(fp->name, "fhc"))
			break;
		fp = fp->sibling;
	}
	if (!fp)
		central_probe_failure(__LINE__);

	fhc->prom_node = fnode;
	prom_getstring(fnode, "name", namebuf, sizeof(namebuf));
	strcpy(fhc->prom_name, namebuf);

	fhc_ranges_init(fnode, fhc);
	fhc->prom_node = fp;
	fhc_ranges_init(fhc);

	/* Now, map in FHC register set. */
	if (prom_getproperty(fnode, "reg", (char *)&fpregs[0], sizeof(fpregs)) == -1)
	pr = of_get_property(fp, "reg", NULL);
	if (!pr)
		central_probe_failure(__LINE__);
	memcpy(fpregs, pr, sizeof(fpregs));

	apply_central_ranges(central_bus, &fpregs[0], 6);
	
@@ -366,7 +365,7 @@ void central_probe(void)
	fhc->jtag_master = 0;

	/* Attach the clock board registers for CENTRAL. */
	probe_clock_board(central_bus, fhc, cnode, fnode);
	probe_clock_board(central_bus, fhc, fp);

	err = upa_readl(fhc->fhc_regs.pregs + FHC_PREGS_ID);
	printk("FHC(board %d): Version[%x] PartID[%x] Manuf[%x] (CENTRAL)\n",
+11 −11
Original line number Diff line number Diff line
@@ -796,26 +796,26 @@ static void __init clock_assign_clk_reg(struct linux_prom_registers *clk_reg,

static int __init clock_probe_central(void)
{
	struct linux_prom_registers clk_reg[2];
	char model[64];
	int node;
	struct linux_prom_registers clk_reg[2], *pr;
	struct device_node *dp;
	char *model;

	if (!central_bus)
		return 0;

	/* Get Central FHC's prom node.  */
	node = central_bus->child->prom_node;
	dp = central_bus->child->prom_node;

	/* Then get the first child device below it.  */
	node = prom_getchild(node);
	dp = dp->child;

	while (node) {
		prom_getstring(node, "model", model, sizeof(model));
		if (!clock_model_matches(model))
	while (dp) {
		model = of_get_property(dp, "model", NULL);
		if (!model || !clock_model_matches(model))
			goto next_sibling;

		prom_getproperty(node, "reg", (char *)clk_reg,
				 sizeof(clk_reg));
		pr = of_get_property(dp, "reg", NULL);
		memcpy(clk_reg, pr, sizeof(clk_reg));

		apply_fhc_ranges(central_bus->child, clk_reg, 1);
		apply_central_ranges(central_bus, clk_reg, 1);
@@ -824,7 +824,7 @@ static int __init clock_probe_central(void)
		return 1;

	next_sibling:
		node = prom_getsibling(node);
		dp = dp->sibling;
	}

	return 0;
+1 −1
Original line number Diff line number Diff line
@@ -1106,7 +1106,7 @@ static struct zilog_layout __iomem * __init get_zs_sun4u(int chip, int zsnode)
				+ FHC_UREGS_ICLR;
			imap = central_bus->child->fhc_regs.uregs
				+ FHC_UREGS_IMAP;
			zilog_irq = build_irq(12, 0, iclr, imap);
			zilog_irq = build_irq(0, iclr, imap);
		} else {
			err = prom_getproperty(zsnode, "interrupts",
					       (char *) &sun4u_ino,
+3 −4
Original line number Diff line number Diff line
@@ -10,6 +10,7 @@
#include <linux/timer.h>

#include <asm/oplib.h>
#include <asm/prom.h>
#include <asm/upa.h>

struct linux_fhc;
@@ -34,8 +35,7 @@ struct linux_central {
	unsigned long			clkregs;
	unsigned long			clkver;
	int				slots;
	int				prom_node;
	char				prom_name[64];
	struct device_node		*prom_node;

	struct linux_prom_ranges	central_ranges[PROMREG_MAX];
	int				num_central_ranges;
@@ -112,8 +112,7 @@ struct linux_fhc {
	struct fhc_regs			fhc_regs;
	int				board;
	int				jtag_master;
	int				prom_node;
	char				prom_name[64];
	struct device_node		*prom_node;

	struct linux_prom_ranges	fhc_ranges[PROMREG_MAX];
	int				num_fhc_ranges;