Commit ea8d2319 authored by Linus Torvalds's avatar Linus Torvalds

Merge http://lia64.bkbits.net/linux-ia64-release-2.6.10

into ppc970.osdl.org:/home/torvalds/v2.6/linux
parents 0c4c9f09 2875ca92
......@@ -9,6 +9,7 @@
#define _ELFCORE32_H_
#include <asm/intrinsics.h>
#include <asm/uaccess.h>
#define USE_ELF_CORE_DUMP 1
......
......@@ -28,6 +28,7 @@
#include <asm/io.h>
#include <asm/kregs.h>
#include <asm/meminit.h>
#include <asm/pgtable.h>
#include <asm/processor.h>
#include <asm/mca.h>
......@@ -324,12 +325,12 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg)
* [granule_addr - first_non_wb_addr) is guaranteed to
* be contiguous WB memory.
*/
granule_addr = md->phys_addr & ~(IA64_GRANULE_SIZE - 1);
granule_addr = GRANULEROUNDDOWN(md->phys_addr);
first_non_wb_addr = max(first_non_wb_addr, granule_addr);
if (first_non_wb_addr < md->phys_addr) {
trim_bottom(md, granule_addr + IA64_GRANULE_SIZE);
granule_addr = md->phys_addr & ~(IA64_GRANULE_SIZE - 1);
granule_addr = GRANULEROUNDDOWN(md->phys_addr);
first_non_wb_addr = max(first_non_wb_addr, granule_addr);
}
......@@ -343,24 +344,36 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg)
break; /* non-WB or hole */
}
last_granule_addr = first_non_wb_addr & ~(IA64_GRANULE_SIZE - 1);
last_granule_addr = GRANULEROUNDDOWN(first_non_wb_addr);
if (last_granule_addr < md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT))
trim_top(md, last_granule_addr);
if (is_available_memory(md)) {
if (md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) > max_addr) {
if (md->phys_addr > max_addr)
if (md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) >= max_addr) {
if (md->phys_addr >= max_addr)
continue;
md->num_pages = (max_addr - md->phys_addr) >> EFI_PAGE_SHIFT;
first_non_wb_addr = max_addr;
}
if (total_mem >= mem_limit)
continue;
total_mem += (md->num_pages << EFI_PAGE_SHIFT);
if (total_mem > mem_limit) {
md->num_pages -= ((total_mem - mem_limit) >> EFI_PAGE_SHIFT);
max_addr = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT);
if (total_mem + (md->num_pages << EFI_PAGE_SHIFT) > mem_limit) {
unsigned long limit_addr = md->phys_addr;
limit_addr += mem_limit - total_mem;
limit_addr = GRANULEROUNDDOWN(limit_addr);
if (md->phys_addr > limit_addr)
continue;
md->num_pages = (limit_addr - md->phys_addr) >>
EFI_PAGE_SHIFT;
first_non_wb_addr = max_addr = md->phys_addr +
(md->num_pages << EFI_PAGE_SHIFT);
}
total_mem += (md->num_pages << EFI_PAGE_SHIFT);
if (md->num_pages == 0)
continue;
......@@ -495,13 +508,13 @@ efi_init (void)
for (cp = saved_command_line; *cp; ) {
if (memcmp(cp, "mem=", 4) == 0) {
cp += 4;
mem_limit = memparse(cp, &end) - 2;
mem_limit = memparse(cp, &end);
if (end != cp)
break;
cp = end;
} else if (memcmp(cp, "max_addr=", 9) == 0) {
cp += 9;
max_addr = memparse(cp, &end) - 1;
max_addr = GRANULEROUNDDOWN(memparse(cp, &end));
if (end != cp)
break;
cp = end;
......
......@@ -868,7 +868,7 @@ end_os_mca_restore:
GLOBAL_ENTRY(ia64_monarch_init_handler)
.prologue
// stash the information the SAL passed to os
SAL_TO_OS_MCA_HANDOFF_STATE_SAVE(r2)
;;
......@@ -907,6 +907,7 @@ IVirtual_Switch:
adds out0=16,sp // out0 = pointer to pt_regs
;;
DO_SAVE_SWITCH_STACK
.body
adds out1=16,sp // out0 = pointer to switch_stack
br.call.sptk.many rp=ia64_init_handler
......
......@@ -1638,7 +1638,7 @@ pfm_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned lon
}
/*
* context is locked when coming here and interrupts are disabled
* interrupt cannot be masked when coming here
*/
static inline int
pfm_do_fasync(int fd, struct file *filp, pfm_context_t *ctx, int on)
......@@ -2270,7 +2270,7 @@ pfm_smpl_buffer_alloc(struct task_struct *task, pfm_context_t *ctx, unsigned lon
* return -ENOMEM;
*/
if (size > task->signal->rlim[RLIMIT_MEMLOCK].rlim_cur)
return -EAGAIN;
return -ENOMEM;
/*
* We do the easy to undo allocations first.
......@@ -2295,10 +2295,6 @@ pfm_smpl_buffer_alloc(struct task_struct *task, pfm_context_t *ctx, unsigned lon
/*
* partially initialize the vma for the sampling buffer
*
* The VM_DONTCOPY flag is very important as it ensures that the mapping
* will never be inherited for any child process (via fork()) which is always
* what we want.
*/
vma->vm_mm = mm;
vma->vm_flags = VM_READ| VM_MAYREAD |VM_RESERVED;
......@@ -2328,6 +2324,7 @@ pfm_smpl_buffer_alloc(struct task_struct *task, pfm_context_t *ctx, unsigned lon
goto error;
}
vma->vm_end = vma->vm_start + size;
vma->vm_pgoff = vma->vm_start >> PAGE_SHIFT;
DPRINT(("aligned size=%ld, hdr=%p mapped @0x%lx\n", size, ctx->ctx_smpl_hdr, vma->vm_start));
......@@ -3060,11 +3057,12 @@ pfm_write_pmcs(pfm_context_t *ctx, void *arg, int count, struct pt_regs *regs)
#endif
}
DPRINT(("pmc[%u]=0x%lx loaded=%d access_pmu=%d all_pmcs=0x%lx used_pmds=0x%lx eventid=%ld smpl_pmds=0x%lx reset_pmds=0x%lx reloads_pmcs=0x%lx used_monitors=0x%lx ovfl_regs=0x%lx\n",
DPRINT(("pmc[%u]=0x%lx ld=%d apmu=%d flags=0x%lx all_pmcs=0x%lx used_pmds=0x%lx eventid=%ld smpl_pmds=0x%lx reset_pmds=0x%lx reloads_pmcs=0x%lx used_monitors=0x%lx ovfl_regs=0x%lx\n",
cnum,
value,
is_loaded,
can_access_pmu,
flags,
ctx->ctx_all_pmcs[0],
ctx->ctx_used_pmds[0],
ctx->ctx_pmds[cnum].eventid,
......@@ -3240,8 +3238,8 @@ pfm_write_pmds(pfm_context_t *ctx, void *arg, int count, struct pt_regs *regs)
}
}
DPRINT(("pmd[%u]=0x%lx loaded=%d access_pmu=%d, hw_value=0x%lx ctx_pmd=0x%lx short_reset=0x%lx "
"long_reset=0x%lx notify=%c used_pmds=0x%lx reset_pmds=0x%lx reload_pmds=0x%lx all_pmds=0x%lx ovfl_regs=0x%lx\n",
DPRINT(("pmd[%u]=0x%lx ld=%d apmu=%d, hw_value=0x%lx ctx_pmd=0x%lx short_reset=0x%lx "
"long_reset=0x%lx notify=%c seed=0x%lx mask=0x%lx used_pmds=0x%lx reset_pmds=0x%lx reload_pmds=0x%lx all_pmds=0x%lx ovfl_regs=0x%lx\n",
cnum,
value,
is_loaded,
......@@ -3251,6 +3249,8 @@ pfm_write_pmds(pfm_context_t *ctx, void *arg, int count, struct pt_regs *regs)
ctx->ctx_pmds[cnum].short_reset,
ctx->ctx_pmds[cnum].long_reset,
PMC_OVFL_NOTIFY(ctx, cnum) ? 'Y':'N',
ctx->ctx_pmds[cnum].seed,
ctx->ctx_pmds[cnum].mask,
ctx->ctx_used_pmds[0],
ctx->ctx_pmds[cnum].reset_pmds[0],
ctx->ctx_reload_pmds[0],
......@@ -3328,7 +3328,7 @@ pfm_read_pmds(pfm_context_t *ctx, void *arg, int count, struct pt_regs *regs)
}
expert_mode = pfm_sysctl.expert_mode;
DPRINT(("loaded=%d access_pmu=%d ctx_state=%d\n",
DPRINT(("ld=%d apmu=%d ctx_state=%d\n",
is_loaded,
can_access_pmu,
state));
......@@ -3868,7 +3868,7 @@ pfm_write_ibr_dbr(int mode, pfm_context_t *ctx, void *arg, int count, struct pt_
ctx->ctx_ibrs[rnum] = dbreg.val;
DPRINT(("write ibr%u=0x%lx used_ibrs=0x%x is_loaded=%d access_pmu=%d\n",
DPRINT(("write ibr%u=0x%lx used_ibrs=0x%x ld=%d apmu=%d\n",
rnum, dbreg.val, ctx->ctx_used_ibrs[0], is_loaded, can_access_pmu));
} else {
CTX_USED_DBR(ctx, rnum);
......@@ -3879,7 +3879,7 @@ pfm_write_ibr_dbr(int mode, pfm_context_t *ctx, void *arg, int count, struct pt_
}
ctx->ctx_dbrs[rnum] = dbreg.val;
DPRINT(("write dbr%u=0x%lx used_dbrs=0x%x is_loaded=%d access_pmu=%d\n",
DPRINT(("write dbr%u=0x%lx used_dbrs=0x%x ld=%d apmu=%d\n",
rnum, dbreg.val, ctx->ctx_used_dbrs[0], is_loaded, can_access_pmu));
}
}
......@@ -5854,14 +5854,6 @@ pfm_save_regs(struct task_struct *task)
return;
}
/*
* sanity check
*/
if (ctx->ctx_last_activation != GET_ACTIVATION()) {
pfm_unprotect_ctx_ctxsw(ctx, flags);
return;
}
/*
* save current PSR: needed because we modify it
*/
......
......@@ -73,6 +73,7 @@ EXPORT_SYMBOL(__ia64_memset_c_io);
#undef __ia64_writew
#undef __ia64_writel
#undef __ia64_writeq
#undef __ia64_mmiowb
unsigned int
__ia64_inb (unsigned long port)
......@@ -158,4 +159,10 @@ __ia64_readq_relaxed (void __iomem *addr)
return ___ia64_readq (addr);
}
void
__ia64_mmiowb(void)
{
___ia64_mmiowb();
}
#endif /* CONFIG_IA64_GENERIC */
......@@ -602,7 +602,7 @@ void call_pernode_memory(unsigned long start, unsigned long len, void *arg)
* for each piece of usable memory and will setup these values for each node.
* Very similar to build_maps().
*/
static int count_node_pages(unsigned long start, unsigned long len, int node)
static __init int count_node_pages(unsigned long start, unsigned long len, int node)
{
unsigned long end = start + len;
......@@ -627,7 +627,7 @@ static int count_node_pages(unsigned long start, unsigned long len, int node)
* paging_init() sets up the page tables for each node of the system and frees
* the bootmem allocator memory for general use.
*/
void paging_init(void)
void __init paging_init(void)
{
unsigned long max_dma;
unsigned long zones_size[MAX_NR_ZONES];
......
......@@ -3,14 +3,13 @@
* License. See the file "COPYING" in the main directory of this archive
* for more details.
*
* Copyright (c) 2001-2003 Silicon Graphics, Inc. All rights reserved.
* Copyright (c) 2001-2004 Silicon Graphics, Inc. All rights reserved.
*/
#include <linux/config.h>
#include <asm/sn/leds.h>
#include <asm/sn/simulator.h>
void snidle(int state) {
void snidle(int state)
{
if (state) {
if (pda->idle_flag == 0) {
/*
......@@ -19,11 +18,6 @@ void snidle(int state) {
set_led_bits(0, LED_CPU_ACTIVITY);
}
#ifdef CONFIG_IA64_SGI_SN_SIM
if (IS_RUNNING_ON_SIMULATOR())
SIMULATOR_SLEEP();
#endif
pda->idle_flag = 1;
} else {
/*
......
......@@ -204,10 +204,12 @@ static void sn_pci_fixup_slot(struct pci_dev *dev)
SN_PCIDEV_INFO(dev) = kmalloc(sizeof(struct pcidev_info), GFP_KERNEL);
if (SN_PCIDEV_INFO(dev) <= 0)
BUG(); /* Cannot afford to run out of memory */
memset(SN_PCIDEV_INFO(dev), 0, sizeof(struct pcidev_info));
sn_irq_info = kmalloc(sizeof(struct sn_irq_info), GFP_KERNEL);
if (sn_irq_info <= 0)
BUG(); /* Cannot afford to run out of memory */
memset(sn_irq_info, 0, sizeof(struct sn_irq_info));
/* Call to retrieve pci device information needed by kernel. */
status = sal_get_pcidev_info((u64) segment, (u64) dev->bus->number,
......@@ -248,7 +250,7 @@ static void sn_pci_fixup_slot(struct pci_dev *dev)
SN_PCIDEV_INFO(dev)->pdi_pcibus_info = SN_PCIBUS_BUSSOFT(dev->bus);
/* Only set up IRQ stuff if this device has a host bus context */
if (SN_PCIDEV_BUSSOFT(dev)) {
if (SN_PCIDEV_BUSSOFT(dev) && sn_irq_info->irq_irq) {
SN_PCIDEV_INFO(dev)->pdi_sn_irq_info = sn_irq_info;
dev->irq = SN_PCIDEV_INFO(dev)->pdi_sn_irq_info->irq_irq;
sn_irq_fixup(dev, sn_irq_info);
......
......@@ -9,6 +9,7 @@
#include <linux/module.h>
#include <asm/io.h>
#include <asm/delay.h>
#include <asm/sn/nodepda.h>
#include <asm/sn/simulator.h>
#include <asm/sn/pda.h>
#include <asm/sn/sn_cpuid.h>
......
......@@ -79,7 +79,7 @@ static void sn_ack_irq(unsigned int irq)
int nasid;
irq = irq & 0xff;
nasid = smp_physical_node_id();
nasid = get_nasid();
event_occurred =
HUB_L((uint64_t *) GLOBAL_MMR_ADDR(nasid, SH_EVENT_OCCURRED));
if (event_occurred & SH_EVENT_OCCURRED_UART_INT_MASK) {
......@@ -109,7 +109,7 @@ static void sn_end_irq(unsigned int irq)
ivec = irq & 0xff;
if (ivec == SGI_UART_VECTOR) {
nasid = smp_physical_node_id();
nasid = get_nasid();
event_occurred = HUB_L((uint64_t *) GLOBAL_MMR_ADDR
(nasid, SH_EVENT_OCCURRED));
/* If the UART bit is set here, we may have received an
......@@ -141,8 +141,8 @@ static void sn_set_affinity_irq(unsigned int irq, cpumask_t mask)
cpuid = first_cpu(mask);
cpuphys = cpu_physical_id(cpuid);
t_nasid = cpu_physical_id_to_nasid(cpuphys);
t_slice = cpu_physical_id_to_slice(cpuphys);
t_nasid = cpuid_to_nasid(cpuid);
t_slice = cpuid_to_slice(cpuid);
while (sn_irq_info) {
int status;
......
......@@ -94,15 +94,11 @@ static int
sn_platform_plat_specific_err_print(const u8 * sect_header, u8 ** oemdata,
u64 * oemdata_size)
{
sal_log_plat_specific_err_info_t *psei =
(sal_log_plat_specific_err_info_t *) sect_header;
if (!psei->valid.oem_data)
return 0;
down(&sn_oemdata_mutex);
sn_oemdata = oemdata;
sn_oemdata_size = oemdata_size;
sn_oemdata_bufsize = 0;
ia64_sn_plat_specific_err_print(print_hook, (char *)psei);
ia64_sn_plat_specific_err_print(print_hook, (char *)sect_header);
up(&sn_oemdata_mutex);
return 0;
}
......@@ -110,18 +106,24 @@ sn_platform_plat_specific_err_print(const u8 * sect_header, u8 ** oemdata,
/* Callback when userspace salinfo wants to decode oem data via the platform
* kernel and/or prom.
*/
int sn_salinfo_platform_oemdata(const u8 * sect_header, u8 ** oemdata,
u64 * oemdata_size)
int sn_salinfo_platform_oemdata(const u8 *sect_header, u8 **oemdata, u64 *oemdata_size)
{
efi_guid_t guid = *(efi_guid_t *) sect_header;
efi_guid_t guid = *(efi_guid_t *)sect_header;
int valid = 0;
*oemdata_size = 0;
vfree(*oemdata);
*oemdata = NULL;
if (efi_guidcmp(guid, SAL_PLAT_SPECIFIC_ERR_SECT_GUID) == 0 ||
efi_guidcmp(guid, SAL_PLAT_MEM_DEV_ERR_SECT_GUID) == 0)
return sn_platform_plat_specific_err_print(sect_header, oemdata,
oemdata_size);
return 0;
if (efi_guidcmp(guid, SAL_PLAT_SPECIFIC_ERR_SECT_GUID) == 0) {
sal_log_plat_specific_err_info_t *psei = (sal_log_plat_specific_err_info_t *)sect_header;
valid = psei->valid.oem_data;
} else if (efi_guidcmp(guid, SAL_PLAT_MEM_DEV_ERR_SECT_GUID) == 0) {
sal_log_mem_dev_err_info_t *mdei = (sal_log_mem_dev_err_info_t *)sect_header;
valid = mdei->valid.oem_data;
}
if (valid)
return sn_platform_plat_specific_err_print(sect_header, oemdata, oemdata_size);
else
return 0;
}
static int __init sn_salinfo_init(void)
......
......@@ -127,6 +127,19 @@ extern char drive_info[4 * 16];
char drive_info[4 * 16];
#endif
/*
* Get nasid of current cpu early in boot before nodepda is initialized
*/
static int
boot_get_nasid(void)
{
int nasid;
if (ia64_sn_get_sapic_info(get_sapicid(), &nasid, NULL, NULL))
BUG();
return nasid;
}
/*
* This routine can only be used during init, since
* smp_boot_data is an init data structure.
......@@ -197,7 +210,7 @@ void __init early_sn_setup(void)
if (IS_RUNNING_ON_SIMULATOR()) {
master_node_bedrock_address = (u64 __iomem *)
REMOTE_HUB(get_nasid(), SH_JUNK_BUS_UART0);
REMOTE_HUB(boot_get_nasid(), SH_JUNK_BUS_UART0);
printk(KERN_DEBUG "early_sn_setup: setting "
"master_node_bedrock_address to 0x%p\n",
master_node_bedrock_address);
......@@ -297,7 +310,7 @@ void __init sn_setup(char **cmdline_p)
panic("PROM version too old\n");
}
master_nasid = get_nasid();
master_nasid = boot_get_nasid();
status =
ia64_sal_freq_base(SAL_FREQ_BASE_REALTIME_CLOCK, &ticks_per_sec,
......@@ -314,7 +327,7 @@ void __init sn_setup(char **cmdline_p)
if (IS_RUNNING_ON_SIMULATOR()) {
master_node_bedrock_address = (u64 __iomem *)
REMOTE_HUB(get_nasid(), SH_JUNK_BUS_UART0);
REMOTE_HUB(boot_get_nasid(), SH_JUNK_BUS_UART0);
printk(KERN_DEBUG "sn_setup: setting "
"master_node_bedrock_address to 0x%p\n",
master_node_bedrock_address);
......@@ -372,6 +385,8 @@ void __init sn_init_pdas(char **cmdline_p)
nodepdaindr[cnode] =
alloc_bootmem_node(NODE_DATA(cnode), sizeof(nodepda_t));
memset(nodepdaindr[cnode], 0, sizeof(nodepda_t));
memset(nodepdaindr[cnode]->phys_cpuid, -1,
sizeof(nodepdaindr[cnode]->phys_cpuid));
}
/*
......@@ -422,8 +437,10 @@ void __init sn_cpu_init(void)
int cpuid;
int cpuphyid;
int nasid;
int subnode;
int slice;
int cnode;
int i;
static int wars_have_been_checked;
/*
......@@ -434,10 +451,20 @@ void __init sn_cpu_init(void)
return;
cpuid = smp_processor_id();
cpuphyid = ((ia64_getreg(_IA64_REG_CR_LID) >> 16) & 0xffff);
nasid = cpu_physical_id_to_nasid(cpuphyid);
cpuphyid = get_sapicid();
if (ia64_sn_get_sapic_info(cpuphyid, &nasid, &subnode, &slice))
BUG();
for (i=0; i < NR_NODES; i++) {
if (nodepdaindr[i]) {
nodepdaindr[i]->phys_cpuid[cpuid].nasid = nasid;
nodepdaindr[i]->phys_cpuid[cpuid].slice = slice;
nodepdaindr[i]->phys_cpuid[cpuid].subnode = subnode;
}
}
cnode = nasid_to_cnodeid(nasid);
slice = cpu_physical_id_to_slice(cpuphyid);
memset(pda, 0, sizeof(pda));
pda->p_nodepda = nodepdaindr[cnode];
......@@ -575,3 +602,15 @@ static void __init scan_for_ionodes(void)
}
}
int
nasid_slice_to_cpuid(int nasid, int slice)
{
long cpu;
for (cpu=0; cpu < NR_CPUS; cpu++)
if (nodepda->phys_cpuid[cpu].nasid == nasid && nodepda->phys_cpuid[cpu].slice == slice)
return cpu;
return -1;
}
......@@ -32,6 +32,7 @@
#include <asm/hw_irq.h>
#include <asm/current.h>
#include <asm/sn/sn_cpuid.h>
#include <asm/sn/sn_sal.h>
#include <asm/sn/addrs.h>
#include <asm/sn/shub_mmr.h>
#include <asm/sn/nodepda.h>
......@@ -136,7 +137,7 @@ sn2_global_tlb_purge(unsigned long start, unsigned long end,
ptc0 = (long *)GLOBAL_MMR_PHYS_ADDR(0, SH_PTC_0);
ptc1 = (long *)GLOBAL_MMR_PHYS_ADDR(0, SH_PTC_1);
mynasid = smp_physical_node_id();
mynasid = get_nasid();
spin_lock_irqsave(&sn2_global_ptc_lock, flags);
......@@ -205,6 +206,7 @@ void sn2_ptc_deadlock_recovery(unsigned long data0, unsigned long data1)
/**
* sn_send_IPI_phys - send an IPI to a Nasid and slice
* @nasid: nasid to receive the interrupt (may be outside partition)
* @physid: physical cpuid to receive the interrupt.
* @vector: command to send
* @delivery_mode: delivery mechanism
......@@ -219,15 +221,12 @@ void sn2_ptc_deadlock_recovery(unsigned long data0, unsigned long data1)
* %IA64_IPI_DM_NMI - pend an NMI
* %IA64_IPI_DM_INIT - pend an INIT interrupt
*/
void sn_send_IPI_phys(long physid, int vector, int delivery_mode)
void sn_send_IPI_phys(int nasid, long physid, int vector, int delivery_mode)
{
long nasid, slice, val;
long val;
unsigned long flags = 0;
volatile long *p;
nasid = cpu_physical_id_to_nasid(physid);
slice = cpu_physical_id_to_slice(physid);
p = (long *)GLOBAL_MMR_PHYS_ADDR(nasid, SH_IPI_INT);
val = (1UL << SH_IPI_INT_SEND_SHFT) |
(physid << SH_IPI_INT_PID_SHFT) |
......@@ -268,8 +267,14 @@ EXPORT_SYMBOL(sn_send_IPI_phys);
void sn2_send_IPI(int cpuid, int vector, int delivery_mode, int redirect)
{
long physid;
int nasid;
physid = cpu_physical_id(cpuid);
nasid = cpuid_to_nasid(cpuid);
/* the following is used only when starting cpus at boot time */
if (unlikely(nasid == -1))
ia64_sn_get_sapic_info(physid, &nasid, NULL, NULL);
sn_send_IPI_phys(physid, vector, delivery_mode);
sn_send_IPI_phys(nasid, physid, vector, delivery_mode);
}
......@@ -99,7 +99,7 @@ static int sn_hwperf_geoid_to_cnode(char *location)
this_slot = MODULE_GET_BPOS(module_id);
this_slab = geo_slab(geoid);
if (rack == this_rack && slot == this_slot && slab == this_slab)
break;
break;
}
return cnode < numionodes ? cnode : -1;
......@@ -121,41 +121,35 @@ static int sn_hwperf_generic_ordinal(struct sn_hwperf_object_info *obj,
for (ordinal=0, p=objs; p != obj; p++) {
if (SN_HWPERF_FOREIGN(p))
continue;
if (p->location[3] == obj->location[3])
if (SN_HWPERF_SAME_OBJTYPE(p, obj))
ordinal++;
}
return ordinal;
}
static struct {
char *brick_chars;
char *brick_name;
} brick_names[] = {
{"c^jbf", "node" },
{"r", "router" },
{NULL, "?-brick" }
};
static const char *slabname_node = "node"; /* SHub asic */
static const char *slabname_ionode = "ionode"; /* TIO asic */
static const char *slabname_router = "router"; /* NL3R or NL4R */
static const char *slabname_other = "other"; /* unknown asic */
static char *sn_hwperf_get_brickname(struct sn_hwperf_object_info *obj,
static const char *sn_hwperf_get_slabname(struct sn_hwperf_object_info *obj,
struct sn_hwperf_object_info *objs, int *ordinal)
{
int i;
int isnode;
const char *slabname = slabname_other;
for (i=0; brick_names[i].brick_chars; i++) {
if (strchr(brick_names[i].brick_chars, obj->location[3]))
break;
}
if (strcmp(brick_names[i].brick_name, "node") == 0)
if ((isnode = SN_HWPERF_IS_NODE(obj)) || SN_HWPERF_IS_IONODE(obj)) {
slabname = isnode ? slabname_node : slabname_ionode;
*ordinal = sn_hwperf_obj_to_cnode(obj);
}
else {
*ordinal = sn_hwperf_generic_ordinal(obj, objs);
if (!brick_names[i].brick_chars)
brick_names[i].brick_name[0] = obj->location[3];
if (SN_HWPERF_IS_ROUTER(obj))
slabname = slabname_router;
}
return brick_names[i].brick_name;
return slabname;
}
static int sn_topology_show(struct seq_file *s, void *d)
......@@ -165,7 +159,7 @@ static int sn_topology_show(struct seq_file *s, void *d)
int e;
int i;
int j;
const char *brickname;
const char *slabname;
int ordinal;
cpumask_t cpumask;
char slice;
......@@ -191,11 +185,11 @@ static int sn_topology_show(struct seq_file *s, void *d)
obj->name[i] = '_';
}
brickname = sn_hwperf_get_brickname(obj, objs, &ordinal);
seq_printf(s, "%s %d %s %s asic %s", brickname, ordinal, obj->location,
slabname = sn_hwperf_get_slabname(obj, objs, &ordinal);
seq_printf(s, "%s %d %s %s asic %s", slabname, ordinal, obj->location,
obj->sn_hwp_this_part ? "local" : "shared", obj->name);
if (strcmp(brickname, "node") != 0)
if (!SN_HWPERF_IS_NODE(obj) && !SN_HWPERF_IS_IONODE(obj))
seq_putc(s, '\n');
else {
seq_printf(s, ", nasid 0x%x", cnodeid_to_nasid(ordinal));
......@@ -206,7 +200,7 @@ static int sn_topology_show(struct seq_file *s, void *d)
seq_putc(s, '\n');
/*
* CPUs on this node
* CPUs on this node, if any
*/
cpumask = node_to_cpumask(ordinal);
for_each_online_cpu(i) {
......@@ -278,9 +272,8 @@ static int sn_topology_show(struct seq_file *s, void *d)
*/
seq_printf(s, " endpoint %s-%d, protocol %s\n",
p->location, ptdata[pt].conn_port,
strcmp(obj->name, "NL3Router") == 0 ||
strcmp(p->name, "NL3Router") == 0 ?
"LLP3" : "LLP4");
(SN_HWPERF_IS_NL3ROUTER(obj) ||
SN_HWPERF_IS_NL3ROUTER(p)) ? "LLP3" : "LLP4");
}
vfree(ptdata);
}
......
......@@ -80,7 +80,8 @@ static int sn_force_interrupt_open(struct inode *inode, struct file *file)
static int coherence_id_show(struct seq_file *s, void *p)
{
seq_printf(s, "%d\n", cpuid_to_coherence_id(smp_processor_id()));
seq_printf(s, "%d\n", partition_coherence_id());
return 0;
}
......
......@@ -368,7 +368,7 @@ sgiioc4_INB(unsigned long port)
}
/* Creates a dma map for the scatter-gather list entries */
static void __init
static void __devinit
ide_dma_sgiioc4(ide_hwif_t * hwif, unsigned long dma_base)
{
int num_ports = sizeof (ioc4_dma_regs_t);
......@@ -579,7 +579,7 @@ static int sgiioc4_ide_dma_setup(ide_drive_t *drive)
return 0;
}
static void __init
static void __devinit
ide_init_sgiioc4(ide_hwif_t * hwif)
{
hwif->mmio = 2;
......@@ -614,7 +614,7 @@ ide_init_sgiioc4(ide_hwif_t * hwif)
hwif->INB = &sgiioc4_INB;
}
static int __init
static int __devinit
sgiioc4_ide_setup_pci_device(struct pci_dev *dev, ide_pci_device_t * d)
{
unsigned long base, ctl, dma_base, irqport;
......@@ -677,7 +677,7 @@ sgiioc4_ide_setup_pci_device(struct pci_dev *dev, ide_pci_device_t * d)
return 0;
}
static unsigned int __init
static unsigned int __devinit
pci_init_sgiioc4(struct pci_dev *dev, ide_pci_device_t * d)
{
unsigned int class_rev;
......@@ -730,13 +730,13 @@ static struct pci_device_id sgiioc4_pci_tbl[] = {
};
MODULE_DEVICE_TABLE(pci, sgiioc4_pci_tbl);
static struct pci_driver driver = {
static struct pci_driver __devinitdata driver = {
.name = "SGI-IOC4_IDE",
.id_table = sgiioc4_pci_tbl,
.probe = sgiioc4_init_one,
};
static int
static int __devinit
sgiioc4_ide_init(void)
{
return ide_pci_register_driver(&driver);
......
......@@ -108,7 +108,6 @@ static struct sn_cons_port sal_console_port;
/* Only used if USE_DYNAMIC_MINOR is set to 1 */
static struct miscdevice misc; /* used with misc_register for dynamic */
extern u64 __iomem *master_node_bedrock_address;
extern void early_sn_setup(void);
#undef DEBUG
......@@ -124,9 +123,6 @@ static int snt_hw_puts_raw(const char *, int);
static int snt_hw_puts_buffered(const char *, int);
static int snt_poll_getc(void);
static int snt_poll_input_pending(void);
static int snt_sim_puts(const char *, int);
static int snt_sim_getc(void);
static int snt_sim_input_pending(void);
static int snt_intr_getc(void);
static int snt_intr_input_pending(void);
static void sn_transmit_chars(struct sn_cons_port *, int);
......@@ -140,14 +136,6 @@ static struct sn_sal_ops poll_ops = {
.sal_input_pending = snt_poll_input_pending
};
/* A table for the simulator */
static struct sn_sal_ops sim_ops = {
.sal_puts_raw = snt_sim_puts,
.sal_puts = snt_sim_puts,
.sal_getc = snt_sim_getc,
.sal_input_pending = snt_sim_input_pending
};
/* A table for interrupts enabled */
static struct sn_sal_ops intr_ops = {
.sal_puts_raw = snt_hw_puts_raw,
......@@ -194,53 +182,6 @@ static int snt_poll_input_pending(void)
return !status && input;
}
/* routines for running the console on the simulator */
/**
* snt_sim_puts - send to the console, used in simulator mode
* @str: String to send
* @count: length of string
*
*/
static int snt_sim_puts(const char *str, int count)
{
int counter = count;
#ifdef FLAG_DIRECT_CONSOLE_WRITES
/* This is an easy way to pre-pend the output to know whether the output
* was done via sal or directly */
writeb('[', master_node_bedrock_address + (UART_TX << 3));
writeb('+', master_node_bedrock_address + (UART_TX << 3));
writeb(']', master_node_bedrock_address + (UART_TX << 3));
writeb(' ', master_node_bedrock_address + (UART_TX << 3));
#endif /* FLAG_DIRECT_CONSOLE_WRITES */
while (counter > 0) {
writeb(*str, master_node_bedrock_address + (UART_TX << 3));
counter--;
str++;
}
return count;
}
/**
* snt_sim_getc - Get character from console in simulator mode
*
*/
static int snt_sim_getc(void)
{
return readb(master_node_bedrock_address + (UART_RX << 3));
}
/**
* snt_sim_input_pending - Check if there is input pending in simulator mode
*
*/
static int snt_sim_input_pending(void)
{
return readb(master_node_bedrock_address +
(UART_LSR << 3)) & UART_LSR_DR;
}
/* routines for an interrupt driven console (normal) */
/**
......@@ -491,11 +432,7 @@ static int sn_debug_printf(const char *fmt, ...)
printed_len = vsnprintf(printk_buf, sizeof(printk_buf), fmt, args);
if (!sal_console_port.sc_ops) {
if (IS_RUNNING_ON_SIMULATOR())
sal_console_port.sc_ops = &sim_ops;
else
sal_console_port.sc_ops = &poll_ops;
sal_console_port.sc_ops = &poll_ops;
early_sn_setup();
}
sal_console_port.sc_ops->sal_puts_raw(printk_buf, printed_len);
......@@ -781,12 +718,8 @@ static void __init sn_sal_switch_to_asynch(struct sn_cons_port *port)
spin_lock_irqsave(&port->sc_port.lock, flags);
/* early_printk invocation may have done this for us */
if (!port->sc_ops) {
if (IS_RUNNING_ON_SIMULATOR())
port->sc_ops = &sim_ops;
else
port->sc_ops = &poll_ops;
}
if (!port->sc_ops)
port->sc_ops = &poll_ops;
/* we can't turn on the console interrupt (as request_irq
* calls kmalloc, which isn't set up yet), so we rely on a
......@@ -1155,11 +1088,7 @@ int __init sn_serial_console_early_setup(void)
if (!ia64_platform_is("sn2"))
return -1;
if (IS_RUNNING_ON_SIMULATOR())
sal_console_port.sc_ops = &sim_ops;
else
sal_console_port.sc_ops = &poll_ops;
sal_console_port.sc_ops = &poll_ops;
early_sn_setup(); /* Find SAL entry points */
register_console(&sal_console_early);
......
......@@ -107,7 +107,7 @@ extern int valid_phys_addr_range (unsigned long addr, size_t *count); /* efi.c *
#define __ia64_mf_a() ia64_mfa()
/**
* __ia64_mmiowb - I/O write barrier
* ___ia64_mmiowb - I/O write barrier
*
* Ensure ordering of I/O space writes. This will make sure that writes
* following the barrier will arrive after all previous writes. For most
......@@ -115,7 +115,7 @@ extern int valid_phys_addr_range (unsigned long addr, size_t *count); /* efi.c *
*
* See Documentation/DocBook/deviceiobook.tmpl for more information.
*/
static inline void __ia64_mmiowb(void)
static inline void ___ia64_mmiowb(void)
{
ia64_mfa();
}
......@@ -162,6 +162,7 @@ __ia64_mk_io_addr (unsigned long port)
#define __ia64_writew ___ia64_writew
#define __ia64_writel ___ia64_writel
#define __ia64_writeq ___ia64_writeq
#define __ia64_mmiowb ___ia64_mmiowb
/*
* For the in/out routines, we need to do "mf.a" _after_ doing the I/O access to ensure
......
......@@ -6,7 +6,7 @@
* the IA-64 page table tree.
*
* This hopefully works with any (fixed) IA-64 page-size, as defined
* in <asm/page.h> (currently 8192).
* in <asm/page.h>.
*
* Copyright (C) 1998-2004 Hewlett-Packard Co
* David Mosberger-Tang <davidm@hpl.hp.com>
......@@ -309,15 +309,15 @@ pgd_index (unsigned long address)
}
/* The offset in the 1-level directory is given by the 3 region bits
(61..63) and the seven level-1 bits (33-39). */
(61..63) and the level-1 bits. */
static inline pgd_t*
pgd_offset (struct mm_struct *mm, unsigned long address)
{
return mm->pgd + pgd_index(address);
}
/* In the kernel's mapped region we have a full 43 bit space available and completely
ignore the region number (since we know its in region number 5). */
/* In the kernel's mapped region we completely ignore the region number
(since we know it's in region number 5). */
#define pgd_offset_k(addr) \
(init_mm.pgd + (((addr) >> PGDIR_SHIFT) & (PTRS_PER_PGD - 1)))
......
......@@ -43,7 +43,7 @@ struct sn_irq_info {
int irq_share_cnt; /* num devices sharing IRQ */
};
extern void sn_send_IPI_phys(long, int, int);
extern void sn_send_IPI_phys(int, long, int, int);
#define CPU_VECTOR_TO_IRQ(cpuid,vector) (vector)
......
......@@ -30,6 +30,12 @@
* This structure provides a convenient way of keeping together
* all per-node data structures.
*/
struct phys_cpuid {
short nasid;
char subnode;
char slice;
};
struct nodepda_s {
void *pdinfo; /* Platform-dependent per-node info */
spinlock_t bist_lock;
......@@ -46,6 +52,10 @@ struct nodepda_s {
*/
struct nodepda_s *pernode_pdaindr[MAX_COMPACT_NODES];
/*
* Array of physical cpu identifiers. Indexed by cpuid.
*/
struct phys_cpuid phys_cpuid[NR_CPUS];
};
typedef struct nodepda_s nodepda_t;
......
......@@ -41,7 +41,15 @@ struct sn_hwperf_object_info {
#define sn_hwp_is_shared f.fields.is_shared
#define sn_hwp_flags f.b.flags
#define SN_HWPERF_FOREIGN(x) (!(x)->sn_hwp_this_part && !(x)->sn_hwp_is_shared)
/* macros for object classification */
#define SN_HWPERF_IS_NODE(x) ((x) && strstr((x)->name, "SHub"))
#define SN_HWPERF_IS_IONODE(x) ((x) && strstr((x)->name, "TIO"))
#define SN_HWPERF_IS_ROUTER(x) ((x) && strstr((x)->name, "Router"))
#define SN_HWPERF_IS_NL3ROUTER(x) ((x) && strstr((x)->name, "NL3Router"))
#define SN_HWPERF_FOREIGN(x) ((x) && !(x)->sn_hwp_this_part && !(x)->sn_hwp_is_shared)
#define SN_HWPERF_SAME_OBJTYPE(x,y) ((SN_HWPERF_IS_NODE(x) && SN_HWPERF_IS_NODE(y)) ||\
(SN_HWPERF_IS_IONODE(x) && SN_HWPERF_IS_IONODE(y)) ||\
(SN_HWPERF_IS_ROUTER(x) && SN_HWPERF_IS_ROUTER(y)))
/* numa port structure, SN_HWPERF_ENUM_PORTS returns an array of these */
struct sn_hwperf_port_info {
......
......@@ -7,6 +7,7 @@
* Copyright (C) 2000-2004 Silicon Graphics, Inc. All rights reserved.
*/
#ifndef _ASM_IA64_SN_SN_CPUID_H
#define _ASM_IA64_SN_SN_CPUID_H
......@@ -35,9 +36,6 @@
* the boot cpu is 0.
* smp_processor_id() returns the cpuid of the current cpu.
*
* CPUNUM - On IA64, a cpunum and cpuid are the same. This is NOT true
* on other architectures like IA32.
*
* CPU_PHYSICAL_ID (also known as HARD_PROCESSOR_ID)
* This is the same as 31:24 of the processor LID register
* hard_smp_processor_id()- cpu_physical_id of current processor
......@@ -45,16 +43,16 @@
* cpu_logical_id(phy_id) - convert a <physical_cpuid> to a <cpuid>
* * not real efficient - don't use in perf critical code
*
* LID - processor defined register (see PRM V2).
* SLICE - a number in the range of 0 - 3 (typically) that represents the
* cpu number on a brick.
*
* On SN2
* 31:28 - id Contains 0-3 to identify the cpu on the node
* 27:16 - eid Contains the NASID
* SUBNODE - (almost obsolete) the number of the FSB that a cpu is
* connected to. This is also the same as the PI number. Usually 0 or 1.
*
* NOTE!!!: the value of the bits in the cpu physical id (SAPICid or LID) of a cpu has no
* significance. The SAPIC id (LID) is a 16-bit cookie that has meaning only to the PROM.
*
*
* The following assumes the following mappings for LID register values:
*
* The macros convert between cpu physical ids & slice/nasid/cnodeid.
* These terms are described below:
*
......@@ -83,19 +81,11 @@
*/
#ifndef CONFIG_SMP
#define cpu_logical_id(cpu) 0
#define cpu_logical_id(cpu) 0
#define cpu_physical_id(cpuid) ((ia64_getreg(_IA64_REG_CR_LID) >> 16) & 0xffff)
#endif
/*
* macros for some of these exist in sn/addrs.h & sn/arch.h, etc. However,
* trying #include these files here causes circular dependencies.
*/
#define cpu_physical_id_to_nasid(cpi) ((cpi) &0xfff)
#define cpu_physical_id_to_slice(cpi) ((cpi>>12) & 3)
#define cpu_physical_id_to_coherence_id(cpi) (((cpi) & 0x600) >> 9)
#define get_nasid() ((ia64_getreg(_IA64_REG_CR_LID) >> 16) & 0xfff)
#define get_slice() ((ia64_getreg(_IA64_REG_CR_LID) >> 28) & 0xf)
#define get_node_number(addr) (((unsigned long)(addr)>>38) & 0x7ff)
/*
......@@ -103,43 +93,35 @@
*
* NOTE: on non-MP systems, only cpuid 0 exists
*/
#define id_eid_to_cpu_physical_id(id,eid) (((id)<<8) | (eid))
#define nasid_slice_to_cpuid(nasid,slice) (cpu_logical_id(nasid_slice_to_cpu_physical_id((nasid),(slice))))
#define nasid_slice_to_cpu_physical_id(nasid, slice) (((slice)<<12) | (nasid))
/*
* The following table/struct is used for managing PTC coherency domains.
*/
typedef struct {
u8 domain;
u8 reserved;
u16 sapicid;
} sn_sapicid_info_t;
extern sn_sapicid_info_t sn_sapicid_info[]; /* indexed by cpuid */
extern short physical_node_map[]; /* indexed by nasid to get cnode */
/*
* cpuid_to_slice - convert a cpuid to the slice that it resides on
* There are 4 cpus per node. This function returns 0 .. 3)
* Macros for retrieving info about current cpu
*/
#define cpuid_to_slice(cpuid) (cpu_physical_id_to_slice(cpu_physical_id(cpuid)))
#define get_nasid() (nodepda->phys_cpuid[smp_processor_id()].nasid)
#define get_subnode() (nodepda->phys_cpuid[smp_processor_id()].subnode)
#define get_slice() (nodepda->phys_cpuid[smp_processor_id()].slice)
#define get_cnode() (nodepda->phys_cpuid[smp_processor_id()].cnode)
#define get_sapicid() ((ia64_getreg(_IA64_REG_CR_LID) >> 16) & 0xffff)
/*
* cpuid_to_nasid - convert a cpuid to the NASID that it resides on
* Macros for retrieving info about an arbitrary cpu
* cpuid - logical cpu id
*/
#define cpuid_to_nasid(cpuid) (cpu_physical_id_to_nasid(cpu_physical_id(cpuid)))
#define cpuid_to_nasid(cpuid) (nodepda->phys_cpuid[cpuid].nasid)
#define cpuid_to_subnode(cpuid) (nodepda->phys_cpuid[cpuid].subnode)
#define cpuid_to_slice(cpuid) (nodepda->phys_cpuid[cpuid].slice)
#define cpuid_to_cnodeid(cpuid) (physical_node_map[cpuid_to_nasid(cpuid)])
/*
* cpuid_to_cnodeid - convert a cpuid to the cnode that it resides on
* Dont use the following in performance critical code. They require scans
* of potentially large tables.
*/
#define cpuid_to_cnodeid(cpuid) (physical_node_map[cpuid_to_nasid(cpuid)])
extern int nasid_slice_to_cpuid(int, int);
#define nasid_slice_to_cpu_physical_id(nasid, slice) \
cpu_physical_id(nasid_slice_to_cpuid(nasid, slice))
/*
* cnodeid_to_nasid - convert a cnodeid to a NASID
......@@ -149,36 +131,15 @@ extern short physical_node_map[]; /* indexed by nasid to get cnode */
*/
#define cnodeid_to_nasid(cnodeid) pda->cnodeid_to_nasid_table[cnodeid]
/*
* nasid_to_cnodeid - convert a NASID to a cnodeid
*/
#define nasid_to_cnodeid(nasid) (physical_node_map[nasid])
/*
* cnode_slice_to_cpuid - convert a codeid & slice to a cpuid
*/
#define cnode_slice_to_cpuid(cnodeid,slice) (nasid_slice_to_cpuid(cnodeid_to_nasid(cnodeid),(slice)))
/*
* cpuid_to_subnode - convert a cpuid to the subnode it resides on.
* slice 0 & 1 are on subnode 0
* slice 2 & 3 are on subnode 1.
* partition_coherence_id - cget the coherence ID of the current partition
*/
#define cpuid_to_subnode(cpuid) ((cpuid_to_slice(cpuid)<2) ? 0 : 1)
#define smp_physical_node_id() (cpuid_to_nasid(smp_processor_id()))
/*
* cpuid_to_coherence_id - convert a cpuid to the coherence domain id it
* resides on
*/
#define cpuid_to_coherence_id(cpuid) cpu_physical_id_to_coherence_id(cpu_physical_id(cpuid))
#define partition_coherence_id() (get_nasid() >> 9)
#endif /* _ASM_IA64_SN_SN_CPUID_H */
......@@ -31,6 +31,7 @@
#define SN_SAL_NO_FAULT_ZONE_VIRTUAL 0x02000010
#define SN_SAL_NO_FAULT_ZONE_PHYSICAL 0x02000011
#define SN_SAL_PRINT_ERROR 0x02000012
#define SN_SAL_GET_SAPIC_INFO 0x02009999 //ZZZZ fix
#define SN_SAL_SET_ERROR_HANDLING_FEATURES 0x0200001a // reentrant
#define SN_SAL_GET_FIT_COMPT 0x0200001b // reentrant
#define SN_SAL_CONSOLE_PUTC 0x02000021
......@@ -843,6 +844,37 @@ ia64_sn_irtr_init(nasid_t nasid, void *buf, int len)
return (int) rv.status;
}
/*
* Returns the nasid, subnode & slice corresponding to a SAPIC ID
*/
static inline u64
ia64_sn_get_sapic_info(int sapicid, int *nasid, int *subnode, int *slice)
{
struct ia64_sal_retval ret_stuff;
ret_stuff.status = 0;
ret_stuff.v0 = 0;
ret_stuff.v1 = 0;
ret_stuff.v2 = 0;
SAL_CALL_NOLOCK(ret_stuff, SN_SAL_GET_SAPIC_INFO, sapicid, 0, 0, 0, 0, 0, 0);
/***** BEGIN HACK - temp til new proms available ********/
if (ret_stuff.status == SALRET_NOT_IMPLEMENTED) {
if (nasid) *nasid = sapicid & 0xfff;
if (subnode) *subnode = (sapicid >> 13) & 1;
if (slice) *slice = (sapicid >> 12) & 3;
return 0;
}
/***** END HACK *******/
if (ret_stuff.status < 0)
return ret_stuff.status;
if (nasid) *nasid = (int) ret_stuff.v0;
if (subnode) *subnode = (int) ret_stuff.v1;
if (slice) *slice = (int) ret_stuff.v2;
return 0;
}
/*
* This is the access point to the Altix PROM hardware performance
* and status monitoring interface. For info on using this, see
......
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