Commit e9ac0988 authored by Anton Blanchard's avatar Anton Blanchard

Merge samba.org:/scratch/anton/sfr into samba.org:/scratch/anton/export

parents 5c9665e0 76b23457
......@@ -72,6 +72,7 @@ extern void init_ras_IRQ(void);
extern void find_and_init_phbs(void);
extern void pSeries_pcibios_fixup(void);
extern void pSeries_pcibios_fixup_bus(struct pci_bus *bus);
extern void iSeries_pcibios_fixup(void);
extern void pSeries_get_rtc_time(struct rtc_time *rtc_time);
......@@ -245,6 +246,7 @@ chrp_init(unsigned long r3, unsigned long r4, unsigned long r5,
#ifndef CONFIG_PPC_ISERIES
ppc_md.pcibios_fixup = pSeries_pcibios_fixup;
ppc_md.pcibios_fixup_bus = pSeries_pcibios_fixup_bus;
#else
ppc_md.pcibios_fixup = NULL;
// ppc_md.pcibios_fixup = iSeries_pcibios_fixup;
......
......@@ -394,81 +394,6 @@ handle_irq_event(int irq, struct pt_regs *regs, struct irqaction *action)
local_irq_disable();
}
#ifdef CONFIG_SMP
extern unsigned long irq_affinity [NR_IRQS];
typedef struct {
unsigned long cpu;
unsigned long timestamp;
} ____cacheline_aligned irq_balance_t;
static irq_balance_t irq_balance[NR_IRQS] __cacheline_aligned
= { [ 0 ... NR_IRQS-1 ] = { 0, 0 } };
#define IDLE_ENOUGH(cpu,now) \
(idle_cpu(cpu) && ((now) - irq_stat[(cpu)].idle_timestamp > 1))
#define IRQ_ALLOWED(cpu,allowed_mask) \
((1UL << cpu) & (allowed_mask))
#define IRQ_BALANCE_INTERVAL (HZ/50)
static unsigned long move(unsigned long curr_cpu, unsigned long allowed_mask,
unsigned long now, int direction)
{
int search_idle = 1;
int cpu = curr_cpu;
goto inside;
do {
if (unlikely(cpu == curr_cpu))
search_idle = 0;
inside:
if (direction == 1) {
cpu++;
if (cpu >= NR_CPUS)
cpu = 0;
} else {
cpu--;
if (cpu == -1)
cpu = NR_CPUS-1;
}
} while (!cpu_online(cpu) || !IRQ_ALLOWED(cpu,allowed_mask) ||
(search_idle && !IDLE_ENOUGH(cpu,now)));
return cpu;
}
static inline void balance_irq(int irq)
{
irq_balance_t *entry = irq_balance + irq;
unsigned long now = jiffies;
if (unlikely(time_after(now, entry->timestamp + IRQ_BALANCE_INTERVAL))) {
unsigned long allowed_mask;
unsigned int new_cpu;
unsigned long random_number;
if (!irq_desc[irq].handler->set_affinity)
return;
random_number = mftb();
random_number &= 1;
allowed_mask = cpu_online_map & irq_affinity[irq];
entry->timestamp = now;
new_cpu = move(entry->cpu, allowed_mask, now, random_number);
if (entry->cpu != new_cpu) {
entry->cpu = new_cpu;
irq_desc[irq].handler->set_affinity(irq, 1UL << new_cpu);
}
}
}
#else
#define balance_irq(irq) do { } while (0)
#endif
/*
* Eventually, this should take an array of interrupts and an array size
* so it can dispatch multiple interrupts.
......@@ -480,10 +405,6 @@ void ppc_irq_dispatch_handler(struct pt_regs *regs, int irq)
int cpu = smp_processor_id();
irq_desc_t *desc = irq_desc + irq;
/* XXX This causes bad performance and lockups on XICS - Anton */
if (naca->interrupt_controller == IC_OPEN_PIC)
balance_irq(irq);
kstat_cpu(cpu).irqs[irq]++;
spin_lock(&desc->lock);
ack_irq(irq);
......
......@@ -500,6 +500,55 @@ fixup_resources(struct pci_dev *dev)
}
}
void __init pSeries_pcibios_fixup_bus(struct pci_bus *bus)
{
struct pci_controller *phb = PCI_GET_PHB_PTR(bus);
struct resource *res;
int i;
if (bus->parent == NULL) {
/* This is a host bridge - fill in its resources */
phb->bus = bus;
bus->resource[0] = res = &phb->io_resource;
if (!res->flags)
BUG(); /* No I/O resource for this PHB? */
for (i = 0; i < 3; ++i) {
res = &phb->mem_resources[i];
if (!res->flags) {
if (i == 0)
BUG(); /* No memory resource for this PHB? */
}
bus->resource[i+1] = res;
}
} else {
/* This is a subordinate bridge */
pci_read_bridge_bases(bus);
for (i = 0; i < 4; ++i) {
if ((res = bus->resource[i]) == NULL)
continue;
if (!res->flags)
continue;
if (res == pci_find_parent_resource(bus->self, res)) {
/* Transparent resource -- don't try to "fix" it. */
continue;
}
if (res->flags & IORESOURCE_IO) {
unsigned long offset = (unsigned long)phb->io_base_virt - pci_io_base;
res->start += offset;
res->end += offset;
} else if (phb->pci_mem_offset
&& (res->flags & IORESOURCE_MEM)) {
if (res->start < phb->pci_mem_offset) {
res->start += phb->pci_mem_offset;
res->end += phb->pci_mem_offset;
}
}
}
}
}
static void check_s7a(void)
{
struct device_node *root;
......@@ -548,17 +597,6 @@ pci_find_hose_for_OF_device(struct device_node *node)
return NULL;
}
/***********************************************************************
* ppc64_pcibios_init
*
* Chance to initialize and structures or variable before PCI Bus walk.
*
***********************************************************************/
void
pSeries_pcibios_init(void)
{
}
/*
* This is called very early before the page table is setup.
*/
......
......@@ -49,7 +49,6 @@ static void fixup_windbond_82c105(struct pci_dev* dev);
void fixup_resources(struct pci_dev* dev);
void iSeries_pcibios_init(void);
void pSeries_pcibios_init(void);
struct pci_controller* hose_head;
struct pci_controller** hose_tail = &hose_head;
......@@ -410,9 +409,7 @@ pcibios_init(void)
struct pci_bus *bus;
int next_busno;
#ifndef CONFIG_PPC_ISERIES
pSeries_pcibios_init();
#else
#ifdef CONFIG_PPC_ISERIES
iSeries_pcibios_init();
#endif
......@@ -467,54 +464,7 @@ subsys_initcall(pcibios_init);
void __init pcibios_fixup_bus(struct pci_bus *bus)
{
#ifndef CONFIG_PPC_ISERIES
struct pci_controller *phb = PCI_GET_PHB_PTR(bus);
struct resource *res;
int i;
if (bus->parent == NULL) {
/* This is a host bridge - fill in its resources */
phb->bus = bus;
bus->resource[0] = res = &phb->io_resource;
if (!res->flags)
BUG(); /* No I/O resource for this PHB? */
for (i = 0; i < 3; ++i) {
res = &phb->mem_resources[i];
if (!res->flags) {
if (i == 0)
BUG(); /* No memory resource for this PHB? */
}
bus->resource[i+1] = res;
}
} else {
/* This is a subordinate bridge */
pci_read_bridge_bases(bus);
for (i = 0; i < 4; ++i) {
if ((res = bus->resource[i]) == NULL)
continue;
if (!res->flags)
continue;
if (res == pci_find_parent_resource(bus->self, res)) {
/* Transparent resource -- don't try to "fix" it. */
continue;
}
if (res->flags & IORESOURCE_IO) {
unsigned long offset = (unsigned long)phb->io_base_virt - pci_io_base;
res->start += offset;
res->end += offset;
} else if (phb->pci_mem_offset
&& (res->flags & IORESOURCE_MEM)) {
if (res->start < phb->pci_mem_offset) {
res->start += phb->pci_mem_offset;
res->end += phb->pci_mem_offset;
}
}
}
}
#endif
if ( ppc_md.pcibios_fixup_bus )
if (ppc_md.pcibios_fixup_bus)
ppc_md.pcibios_fixup_bus(bus);
}
......
......@@ -688,6 +688,7 @@ static int __init topology_init(void)
sparc64_cpus = kmalloc(NR_CPUS * sizeof(struct cpu), GFP_KERNEL);
if (!sparc64_cpus)
return -ENOMEM;
memset(sparc64_cpus, 0, NR_CPUS * sizeof(struct cpu));
for (i = 0; i < NR_CPUS; i++) {
if (cpu_possible(i))
register_cpu(&sparc64_cpus[i], i, NULL);
......
......@@ -17,6 +17,8 @@
#include <linux/err.h>
#include <linux/kmod.h>
#include <linux/interrupt.h>
#include <linux/sched.h>
#include <linux/string.h>
#include "base.h"
#include "fs/fs.h"
......
......@@ -13,6 +13,7 @@
#include <linux/types.h>
#include <linux/stat.h>
#include <linux/ctype.h>
#include <linux/slab.h>
#include <asm/uaccess.h>
#include "base.h"
......
......@@ -7,6 +7,7 @@
#include <linux/fs.h>
#include <linux/mount.h>
#include <linux/pagemap.h>
#include <linux/init.h>
#include "sysfs.h"
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment