Commit e6a997ed authored by Linus Torvalds's avatar Linus Torvalds

Merge branch 'x86-fixes-for-linus' of...

Merge branch 'x86-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip

* 'x86-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip:
  x86: fix resume (S2R) broken by Intel microcode module, on A110L
  x86 gart: don't complain if no AMD GART found
  AMD IOMMU: panic if completion wait loop fails
  AMD IOMMU: set cmd buffer pointers to zero manually
  x86: re-enable MCE on secondary CPUS after suspend/resume
  AMD IOMMU: allocate rlookup_table with __GFP_ZERO
parents 9a1d1035 280a9ca5
...@@ -235,8 +235,9 @@ static int iommu_completion_wait(struct amd_iommu *iommu) ...@@ -235,8 +235,9 @@ static int iommu_completion_wait(struct amd_iommu *iommu)
status &= ~MMIO_STATUS_COM_WAIT_INT_MASK; status &= ~MMIO_STATUS_COM_WAIT_INT_MASK;
writel(status, iommu->mmio_base + MMIO_STATUS_OFFSET); writel(status, iommu->mmio_base + MMIO_STATUS_OFFSET);
if (unlikely((i == EXIT_LOOP_COUNT) && printk_ratelimit())) if (unlikely(i == EXIT_LOOP_COUNT))
printk(KERN_WARNING "AMD IOMMU: Completion wait loop failed\n"); panic("AMD IOMMU: Completion wait loop failed\n");
out: out:
spin_unlock_irqrestore(&iommu->lock, flags); spin_unlock_irqrestore(&iommu->lock, flags);
......
...@@ -427,6 +427,10 @@ static u8 * __init alloc_command_buffer(struct amd_iommu *iommu) ...@@ -427,6 +427,10 @@ static u8 * __init alloc_command_buffer(struct amd_iommu *iommu)
memcpy_toio(iommu->mmio_base + MMIO_CMD_BUF_OFFSET, memcpy_toio(iommu->mmio_base + MMIO_CMD_BUF_OFFSET,
&entry, sizeof(entry)); &entry, sizeof(entry));
/* set head and tail to zero manually */
writel(0x00, iommu->mmio_base + MMIO_CMD_HEAD_OFFSET);
writel(0x00, iommu->mmio_base + MMIO_CMD_TAIL_OFFSET);
iommu_feature_enable(iommu, CONTROL_CMDBUF_EN); iommu_feature_enable(iommu, CONTROL_CMDBUF_EN);
return cmd_buf; return cmd_buf;
...@@ -1074,7 +1078,8 @@ int __init amd_iommu_init(void) ...@@ -1074,7 +1078,8 @@ int __init amd_iommu_init(void)
goto free; goto free;
/* IOMMU rlookup table - find the IOMMU for a specific device */ /* IOMMU rlookup table - find the IOMMU for a specific device */
amd_iommu_rlookup_table = (void *)__get_free_pages(GFP_KERNEL, amd_iommu_rlookup_table = (void *)__get_free_pages(
GFP_KERNEL | __GFP_ZERO,
get_order(rlookup_table_size)); get_order(rlookup_table_size));
if (amd_iommu_rlookup_table == NULL) if (amd_iommu_rlookup_table == NULL)
goto free; goto free;
......
...@@ -510,12 +510,9 @@ static void __cpuinit mce_cpu_features(struct cpuinfo_x86 *c) ...@@ -510,12 +510,9 @@ static void __cpuinit mce_cpu_features(struct cpuinfo_x86 *c)
*/ */
void __cpuinit mcheck_init(struct cpuinfo_x86 *c) void __cpuinit mcheck_init(struct cpuinfo_x86 *c)
{ {
static cpumask_t mce_cpus = CPU_MASK_NONE;
mce_cpu_quirks(c); mce_cpu_quirks(c);
if (mce_dont_init || if (mce_dont_init ||
cpu_test_and_set(smp_processor_id(), mce_cpus) ||
!mce_available(c)) !mce_available(c))
return; return;
......
...@@ -272,13 +272,18 @@ static struct attribute_group mc_attr_group = { ...@@ -272,13 +272,18 @@ static struct attribute_group mc_attr_group = {
.name = "microcode", .name = "microcode",
}; };
static void microcode_fini_cpu(int cpu) static void __microcode_fini_cpu(int cpu)
{ {
struct ucode_cpu_info *uci = ucode_cpu_info + cpu; struct ucode_cpu_info *uci = ucode_cpu_info + cpu;
mutex_lock(&microcode_mutex);
microcode_ops->microcode_fini_cpu(cpu); microcode_ops->microcode_fini_cpu(cpu);
uci->valid = 0; uci->valid = 0;
}
static void microcode_fini_cpu(int cpu)
{
mutex_lock(&microcode_mutex);
__microcode_fini_cpu(cpu);
mutex_unlock(&microcode_mutex); mutex_unlock(&microcode_mutex);
} }
...@@ -306,12 +311,16 @@ static int microcode_resume_cpu(int cpu) ...@@ -306,12 +311,16 @@ static int microcode_resume_cpu(int cpu)
* to this cpu (a bit of paranoia): * to this cpu (a bit of paranoia):
*/ */
if (microcode_ops->collect_cpu_info(cpu, &nsig)) { if (microcode_ops->collect_cpu_info(cpu, &nsig)) {
microcode_fini_cpu(cpu); __microcode_fini_cpu(cpu);
printk(KERN_ERR "failed to collect_cpu_info for resuming cpu #%d\n",
cpu);
return -1; return -1;
} }
if (memcmp(&nsig, &uci->cpu_sig, sizeof(nsig))) { if ((nsig.sig != uci->cpu_sig.sig) || (nsig.pf != uci->cpu_sig.pf)) {
microcode_fini_cpu(cpu); __microcode_fini_cpu(cpu);
printk(KERN_ERR "cached ucode doesn't match the resuming cpu #%d\n",
cpu);
/* Should we look for a new ucode here? */ /* Should we look for a new ucode here? */
return 1; return 1;
} }
......
...@@ -155,6 +155,7 @@ static DEFINE_SPINLOCK(microcode_update_lock); ...@@ -155,6 +155,7 @@ static DEFINE_SPINLOCK(microcode_update_lock);
static int collect_cpu_info(int cpu_num, struct cpu_signature *csig) static int collect_cpu_info(int cpu_num, struct cpu_signature *csig)
{ {
struct cpuinfo_x86 *c = &cpu_data(cpu_num); struct cpuinfo_x86 *c = &cpu_data(cpu_num);
unsigned long flags;
unsigned int val[2]; unsigned int val[2];
memset(csig, 0, sizeof(*csig)); memset(csig, 0, sizeof(*csig));
...@@ -174,11 +175,16 @@ static int collect_cpu_info(int cpu_num, struct cpu_signature *csig) ...@@ -174,11 +175,16 @@ static int collect_cpu_info(int cpu_num, struct cpu_signature *csig)
csig->pf = 1 << ((val[1] >> 18) & 7); csig->pf = 1 << ((val[1] >> 18) & 7);
} }
/* serialize access to the physical write to MSR 0x79 */
spin_lock_irqsave(&microcode_update_lock, flags);
wrmsr(MSR_IA32_UCODE_REV, 0, 0); wrmsr(MSR_IA32_UCODE_REV, 0, 0);
/* see notes above for revision 1.07. Apparent chip bug */ /* see notes above for revision 1.07. Apparent chip bug */
sync_core(); sync_core();
/* get the current revision from MSR 0x8B */ /* get the current revision from MSR 0x8B */
rdmsr(MSR_IA32_UCODE_REV, val[0], csig->rev); rdmsr(MSR_IA32_UCODE_REV, val[0], csig->rev);
spin_unlock_irqrestore(&microcode_update_lock, flags);
pr_debug("microcode: collect_cpu_info : sig=0x%x, pf=0x%x, rev=0x%x\n", pr_debug("microcode: collect_cpu_info : sig=0x%x, pf=0x%x, rev=0x%x\n",
csig->sig, csig->pf, csig->rev); csig->sig, csig->pf, csig->rev);
......
...@@ -745,10 +745,8 @@ void __init gart_iommu_init(void) ...@@ -745,10 +745,8 @@ void __init gart_iommu_init(void)
unsigned long scratch; unsigned long scratch;
long i; long i;
if (cache_k8_northbridges() < 0 || num_k8_northbridges == 0) { if (cache_k8_northbridges() < 0 || num_k8_northbridges == 0)
printk(KERN_INFO "PCI-GART: No AMD GART found.\n");
return; return;
}
#ifndef CONFIG_AGP_AMD64 #ifndef CONFIG_AGP_AMD64
no_agp = 1; no_agp = 1;
......
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