[PATCH] ppc64: make firmware_has_feature() stronger
Make firmware_has_feature() evaluate at compile time for the non pSeries case and tidy up code where possible. Signed-off-by: Stephen Rothwell <sfr@canb.auug.org.au> Signed-off-by: Paul Mackerras <paulus@samba.org>
This commit is contained in:
committed by
Paul Mackerras
parent
1ababe1148
commit
8d15a3e55f
@@ -11,7 +11,7 @@ obj-y := setup.o entry.o traps.o irq.o idle.o dma.o \
|
|||||||
udbg.o binfmt_elf32.o sys_ppc32.o ioctl32.o \
|
udbg.o binfmt_elf32.o sys_ppc32.o ioctl32.o \
|
||||||
ptrace32.o signal32.o rtc.o init_task.o \
|
ptrace32.o signal32.o rtc.o init_task.o \
|
||||||
lmb.o cputable.o cpu_setup_power4.o idle_power4.o \
|
lmb.o cputable.o cpu_setup_power4.o idle_power4.o \
|
||||||
iommu.o sysfs.o vdso.o pmc.o
|
iommu.o sysfs.o vdso.o pmc.o firmware.o
|
||||||
obj-y += vdso32/ vdso64/
|
obj-y += vdso32/ vdso64/
|
||||||
|
|
||||||
obj-$(CONFIG_PPC_OF) += of_device.o
|
obj-$(CONFIG_PPC_OF) += of_device.o
|
||||||
|
@@ -20,11 +20,9 @@
|
|||||||
#include <linux/module.h>
|
#include <linux/module.h>
|
||||||
|
|
||||||
#include <asm/cputable.h>
|
#include <asm/cputable.h>
|
||||||
#include <asm/firmware.h>
|
|
||||||
|
|
||||||
struct cpu_spec* cur_cpu_spec = NULL;
|
struct cpu_spec* cur_cpu_spec = NULL;
|
||||||
EXPORT_SYMBOL(cur_cpu_spec);
|
EXPORT_SYMBOL(cur_cpu_spec);
|
||||||
unsigned long ppc64_firmware_features;
|
|
||||||
|
|
||||||
/* NOTE:
|
/* NOTE:
|
||||||
* Unlike ppc32, ppc64 will only call this once for the boot CPU, it's
|
* Unlike ppc32, ppc64 will only call this once for the boot CPU, it's
|
||||||
@@ -244,26 +242,3 @@ struct cpu_spec cpu_specs[] = {
|
|||||||
.cpu_setup = __setup_cpu_power4,
|
.cpu_setup = __setup_cpu_power4,
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
firmware_feature_t firmware_features_table[FIRMWARE_MAX_FEATURES] = {
|
|
||||||
{FW_FEATURE_PFT, "hcall-pft"},
|
|
||||||
{FW_FEATURE_TCE, "hcall-tce"},
|
|
||||||
{FW_FEATURE_SPRG0, "hcall-sprg0"},
|
|
||||||
{FW_FEATURE_DABR, "hcall-dabr"},
|
|
||||||
{FW_FEATURE_COPY, "hcall-copy"},
|
|
||||||
{FW_FEATURE_ASR, "hcall-asr"},
|
|
||||||
{FW_FEATURE_DEBUG, "hcall-debug"},
|
|
||||||
{FW_FEATURE_PERF, "hcall-perf"},
|
|
||||||
{FW_FEATURE_DUMP, "hcall-dump"},
|
|
||||||
{FW_FEATURE_INTERRUPT, "hcall-interrupt"},
|
|
||||||
{FW_FEATURE_MIGRATE, "hcall-migrate"},
|
|
||||||
{FW_FEATURE_PERFMON, "hcall-perfmon"},
|
|
||||||
{FW_FEATURE_CRQ, "hcall-crq"},
|
|
||||||
{FW_FEATURE_VIO, "hcall-vio"},
|
|
||||||
{FW_FEATURE_RDMA, "hcall-rdma"},
|
|
||||||
{FW_FEATURE_LLAN, "hcall-lLAN"},
|
|
||||||
{FW_FEATURE_BULK, "hcall-bulk"},
|
|
||||||
{FW_FEATURE_XDABR, "hcall-xdabr"},
|
|
||||||
{FW_FEATURE_MULTITCE, "hcall-multi-tce"},
|
|
||||||
{FW_FEATURE_SPLPAR, "hcall-splpar"},
|
|
||||||
};
|
|
||||||
|
47
arch/ppc64/kernel/firmware.c
Normal file
47
arch/ppc64/kernel/firmware.c
Normal file
@@ -0,0 +1,47 @@
|
|||||||
|
/*
|
||||||
|
* arch/ppc64/kernel/firmware.c
|
||||||
|
*
|
||||||
|
* Extracted from cputable.c
|
||||||
|
*
|
||||||
|
* Copyright (C) 2001 Ben. Herrenschmidt (benh@kernel.crashing.org)
|
||||||
|
*
|
||||||
|
* Modifications for ppc64:
|
||||||
|
* Copyright (C) 2003 Dave Engebretsen <engebret@us.ibm.com>
|
||||||
|
* Copyright (C) 2005 Stephen Rothwell, IBM Corporation
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version
|
||||||
|
* 2 of the License, or (at your option) any later version.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <linux/config.h>
|
||||||
|
|
||||||
|
#include <asm/firmware.h>
|
||||||
|
|
||||||
|
unsigned long ppc64_firmware_features;
|
||||||
|
|
||||||
|
#ifdef CONFIG_PPC_PSERIES
|
||||||
|
firmware_feature_t firmware_features_table[FIRMWARE_MAX_FEATURES] = {
|
||||||
|
{FW_FEATURE_PFT, "hcall-pft"},
|
||||||
|
{FW_FEATURE_TCE, "hcall-tce"},
|
||||||
|
{FW_FEATURE_SPRG0, "hcall-sprg0"},
|
||||||
|
{FW_FEATURE_DABR, "hcall-dabr"},
|
||||||
|
{FW_FEATURE_COPY, "hcall-copy"},
|
||||||
|
{FW_FEATURE_ASR, "hcall-asr"},
|
||||||
|
{FW_FEATURE_DEBUG, "hcall-debug"},
|
||||||
|
{FW_FEATURE_PERF, "hcall-perf"},
|
||||||
|
{FW_FEATURE_DUMP, "hcall-dump"},
|
||||||
|
{FW_FEATURE_INTERRUPT, "hcall-interrupt"},
|
||||||
|
{FW_FEATURE_MIGRATE, "hcall-migrate"},
|
||||||
|
{FW_FEATURE_PERFMON, "hcall-perfmon"},
|
||||||
|
{FW_FEATURE_CRQ, "hcall-crq"},
|
||||||
|
{FW_FEATURE_VIO, "hcall-vio"},
|
||||||
|
{FW_FEATURE_RDMA, "hcall-rdma"},
|
||||||
|
{FW_FEATURE_LLAN, "hcall-lLAN"},
|
||||||
|
{FW_FEATURE_BULK, "hcall-bulk"},
|
||||||
|
{FW_FEATURE_XDABR, "hcall-xdabr"},
|
||||||
|
{FW_FEATURE_MULTITCE, "hcall-multi-tce"},
|
||||||
|
{FW_FEATURE_SPLPAR, "hcall-splpar"},
|
||||||
|
};
|
||||||
|
#endif
|
@@ -231,11 +231,9 @@ static void __init pSeries_setup_arch(void)
|
|||||||
|
|
||||||
pSeries_nvram_init();
|
pSeries_nvram_init();
|
||||||
|
|
||||||
if (firmware_has_feature(FW_FEATURE_SPLPAR))
|
|
||||||
vpa_init(boot_cpuid);
|
|
||||||
|
|
||||||
/* Choose an idle loop */
|
/* Choose an idle loop */
|
||||||
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
||||||
|
vpa_init(boot_cpuid);
|
||||||
if (get_paca()->lppaca.shared_proc) {
|
if (get_paca()->lppaca.shared_proc) {
|
||||||
printk(KERN_INFO "Using shared processor idle loop\n");
|
printk(KERN_INFO "Using shared processor idle loop\n");
|
||||||
ppc_md.idle_loop = pseries_shared_idle;
|
ppc_md.idle_loop = pseries_shared_idle;
|
||||||
|
@@ -203,10 +203,9 @@ struct task_struct *__switch_to(struct task_struct *prev,
|
|||||||
new_thread = &new->thread;
|
new_thread = &new->thread;
|
||||||
old_thread = ¤t->thread;
|
old_thread = ¤t->thread;
|
||||||
|
|
||||||
/* Collect purr utilization data per process and per processor wise */
|
/* Collect purr utilization data per process and per processor
|
||||||
/* purr is nothing but processor time base */
|
* wise purr is nothing but processor time base
|
||||||
|
*/
|
||||||
#if defined(CONFIG_PPC_PSERIES)
|
|
||||||
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
||||||
struct cpu_usage *cu = &__get_cpu_var(cpu_usage_array);
|
struct cpu_usage *cu = &__get_cpu_var(cpu_usage_array);
|
||||||
long unsigned start_tb, current_tb;
|
long unsigned start_tb, current_tb;
|
||||||
@@ -215,8 +214,6 @@ struct task_struct *__switch_to(struct task_struct *prev,
|
|||||||
old_thread->accum_tb += (current_tb - start_tb);
|
old_thread->accum_tb += (current_tb - start_tb);
|
||||||
new_thread->start_tb = current_tb;
|
new_thread->start_tb = current_tb;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
local_irq_save(flags);
|
local_irq_save(flags);
|
||||||
last = _switch(old_thread, new_thread);
|
last = _switch(old_thread, new_thread);
|
||||||
|
@@ -153,11 +153,9 @@ void ppc64_enable_pmcs(void)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef CONFIG_PPC_PSERIES
|
|
||||||
/* instruct hypervisor to maintain PMCs */
|
/* instruct hypervisor to maintain PMCs */
|
||||||
if (firmware_has_feature(FW_FEATURE_SPLPAR))
|
if (firmware_has_feature(FW_FEATURE_SPLPAR))
|
||||||
get_paca()->lppaca.pmcregs_in_use = 1;
|
get_paca()->lppaca.pmcregs_in_use = 1;
|
||||||
#endif /* CONFIG_PPC_PSERIES */
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
@@ -371,13 +371,11 @@ int timer_interrupt(struct pt_regs * regs)
|
|||||||
process_hvlpevents(regs);
|
process_hvlpevents(regs);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* collect purr register values often, for accurate calculations */
|
/* collect purr register values often, for accurate calculations */
|
||||||
#if defined(CONFIG_PPC_PSERIES)
|
|
||||||
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
|
||||||
struct cpu_usage *cu = &__get_cpu_var(cpu_usage_array);
|
struct cpu_usage *cu = &__get_cpu_var(cpu_usage_array);
|
||||||
cu->current_tb = mfspr(SPRN_PURR);
|
cu->current_tb = mfspr(SPRN_PURR);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
irq_exit();
|
irq_exit();
|
||||||
|
|
||||||
|
@@ -45,6 +45,22 @@
|
|||||||
#define FW_FEATURE_MULTITCE (1UL<<19)
|
#define FW_FEATURE_MULTITCE (1UL<<19)
|
||||||
#define FW_FEATURE_SPLPAR (1UL<<20)
|
#define FW_FEATURE_SPLPAR (1UL<<20)
|
||||||
|
|
||||||
|
enum {
|
||||||
|
FW_FEATURE_PSERIES = FW_FEATURE_PFT | FW_FEATURE_TCE |
|
||||||
|
FW_FEATURE_SPRG0 | FW_FEATURE_DABR | FW_FEATURE_COPY |
|
||||||
|
FW_FEATURE_ASR | FW_FEATURE_DEBUG | FW_FEATURE_TERM |
|
||||||
|
FW_FEATURE_PERF | FW_FEATURE_DUMP | FW_FEATURE_INTERRUPT |
|
||||||
|
FW_FEATURE_MIGRATE | FW_FEATURE_PERFMON | FW_FEATURE_CRQ |
|
||||||
|
FW_FEATURE_VIO | FW_FEATURE_RDMA | FW_FEATURE_LLAN |
|
||||||
|
FW_FEATURE_BULK | FW_FEATURE_XDABR | FW_FEATURE_MULTITCE |
|
||||||
|
FW_FEATURE_SPLPAR,
|
||||||
|
FW_FEATURE_POSSIBLE =
|
||||||
|
#ifdef CONFIG_PPC_PSERIES
|
||||||
|
FW_FEATURE_PSERIES |
|
||||||
|
#endif
|
||||||
|
0,
|
||||||
|
};
|
||||||
|
|
||||||
/* This is used to identify firmware features which are available
|
/* This is used to identify firmware features which are available
|
||||||
* to the kernel.
|
* to the kernel.
|
||||||
*/
|
*/
|
||||||
@@ -52,15 +68,17 @@ extern unsigned long ppc64_firmware_features;
|
|||||||
|
|
||||||
static inline unsigned long firmware_has_feature(unsigned long feature)
|
static inline unsigned long firmware_has_feature(unsigned long feature)
|
||||||
{
|
{
|
||||||
return ppc64_firmware_features & feature;
|
return ppc64_firmware_features & feature & FW_FEATURE_POSSIBLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef CONFIG_PPC_PSERIES
|
||||||
typedef struct {
|
typedef struct {
|
||||||
unsigned long val;
|
unsigned long val;
|
||||||
char * name;
|
char * name;
|
||||||
} firmware_feature_t;
|
} firmware_feature_t;
|
||||||
|
|
||||||
extern firmware_feature_t firmware_features_table[];
|
extern firmware_feature_t firmware_features_table[];
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif /* __ASSEMBLY__ */
|
#endif /* __ASSEMBLY__ */
|
||||||
#endif /* __KERNEL__ */
|
#endif /* __KERNEL__ */
|
||||||
|
Reference in New Issue
Block a user