From: Greg KH <gregkh@suse.de>
To: linux-kernel@vger.kernel.org, stable@kernel.org
Cc: stable-review@kernel.org, torvalds@linux-foundation.org,
akpm@linux-foundation.org, alan@lxorguk.ukuu.org.uk,
Thomas Gleixner <tglx@linutronix.de>,
Damien Wyart <damien.wyart@free.fr>,
Venkatesh Pallipadi <venki@google.com>,
Arjan van de Ven <arjan@linux.intel.com>,
Andreas Herrmann <andreas.herrmann3@amd.com>,
Suresh Siddha <suresh.b.siddha@intel.com>,
Konstantin Khlebnikov <khlebnikov@openvz.org>
Subject: [40/55] x86: Hpet: Avoid the comparator readback penalty
Date: Fri, 05 Aug 2011 17:02:10 -0700 [thread overview]
Message-ID: <20110806000252.887106427@clark.kroah.org> (raw)
In-Reply-To: <20110806000257.GA25498@kroah.com>
2.6.32-longterm review patch. If anyone has any objections, please let us know.
------------------
From: Thomas Gleixner <tglx@linutronix.de>
(imported from commit v2.6.36-rc4-167-g995bd3b)
Due to the overly intelligent design of HPETs, we need to workaround
the problem that the compare value which we write is already behind
the actual counter value at the point where the value hits the real
compare register. This happens for two reasons:
1) We read out the counter, add the delta and write the result to the
compare register. When a NMI or SMI hits between the read out and
the write then the counter can be ahead of the event already
2) The write to the compare register is delayed by up to two HPET
cycles in certain chipsets.
We worked around this by reading back the compare register to make
sure that the written value has hit the hardware. For certain ICH9+
chipsets this can require two readouts, as the first one can return
the previous compare register value. That's bad performance wise for
the normal case where the event is far enough in the future.
As we already know that the write can be delayed by up to two cycles
we can avoid the read back of the compare register completely if we
make the decision whether the delta has elapsed already or not based
on the following calculation:
cmp = event - actual_count;
If cmp is less than 8 HPET clock cycles, then we decide that the event
has happened already and return -ETIME. That covers the above #1 and
#2 problems which would cause a wait for HPET wraparound (~306
seconds).
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Tested-by: Nix <nix@esperi.org.uk>
Tested-by: Artur Skawina <art.08.09@gmail.com>
Cc: Damien Wyart <damien.wyart@free.fr>
Tested-by: John Drescher <drescherjm@gmail.com>
Cc: Venkatesh Pallipadi <venki@google.com>
Cc: Arjan van de Ven <arjan@linux.intel.com>
Cc: Andreas Herrmann <andreas.herrmann3@amd.com>
Tested-by: Borislav Petkov <borislav.petkov@amd.com>
Cc: Suresh Siddha <suresh.b.siddha@intel.com>
LKML-Reference: <alpine.LFD.2.00.1009151500060.2416@localhost6.localdomain6>
Signed-off-by: Konstantin Khlebnikov <khlebnikov@openvz.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
---
arch/x86/kernel/hpet.c | 43 +++++++++++++++++++++----------------------
1 file changed, 21 insertions(+), 22 deletions(-)
--- a/arch/x86/kernel/hpet.c
+++ b/arch/x86/kernel/hpet.c
@@ -379,36 +379,35 @@ static int hpet_next_event(unsigned long
struct clock_event_device *evt, int timer)
{
u32 cnt;
+ s32 res;
cnt = hpet_readl(HPET_COUNTER);
cnt += (u32) delta;
hpet_writel(cnt, HPET_Tn_CMP(timer));
/*
- * We need to read back the CMP register on certain HPET
- * implementations (ATI chipsets) which seem to delay the
- * transfer of the compare register into the internal compare
- * logic. With small deltas this might actually be too late as
- * the counter could already be higher than the compare value
- * at that point and we would wait for the next hpet interrupt
- * forever. We found out that reading the CMP register back
- * forces the transfer so we can rely on the comparison with
- * the counter register below. If the read back from the
- * compare register does not match the value we programmed
- * then we might have a real hardware problem. We can not do
- * much about it here, but at least alert the user/admin with
- * a prominent warning.
- * An erratum on some chipsets (ICH9,..), results in comparator read
- * immediately following a write returning old value. Workaround
- * for this is to read this value second time, when first
- * read returns old value.
+ * HPETs are a complete disaster. The compare register is
+ * based on a equal comparison and neither provides a less
+ * than or equal functionality (which would require to take
+ * the wraparound into account) nor a simple count down event
+ * mode. Further the write to the comparator register is
+ * delayed internally up to two HPET clock cycles in certain
+ * chipsets (ATI, ICH9,10). We worked around that by reading
+ * back the compare register, but that required another
+ * workaround for ICH9,10 chips where the first readout after
+ * write can return the old stale value. We already have a
+ * minimum delta of 5us enforced, but a NMI or SMI hitting
+ * between the counter readout and the comparator write can
+ * move us behind that point easily. Now instead of reading
+ * the compare register back several times, we make the ETIME
+ * decision based on the following: Return ETIME if the
+ * counter value after the write is less than 8 HPET cycles
+ * away from the event or if the counter is already ahead of
+ * the event.
*/
- if (unlikely((u32)hpet_readl(HPET_Tn_CMP(timer)) != cnt)) {
- WARN_ONCE((u32)hpet_readl(HPET_Tn_CMP(timer)) != cnt,
- KERN_WARNING "hpet: compare register read back failed.\n");
- }
+ res = (s32)(cnt - (u32)hpet_readl(HPET_COUNTER));
- return (s32)((u32)hpet_readl(HPET_COUNTER) - cnt) >= 0 ? -ETIME : 0;
+ return res < 8 ? -ETIME : 0;
}
static void hpet_legacy_set_mode(enum clock_event_mode mode,
next prev parent reply other threads:[~2011-08-06 0:09 UTC|newest]
Thread overview: 64+ messages / expand[flat|nested] mbox.gz Atom feed top
2011-08-06 0:02 [00/55] 2.6.32.44-longterm review Greg KH
2011-08-06 0:01 ` [01/55] ASoC: Fix Blackfin I2S _pointer() implementation return in bounds values Greg KH
2011-08-06 0:01 ` [02/55] [media] v4l2-ioctl.c: prefill tuner type for g_frequency and g/s_tuner Greg KH
2011-08-06 0:01 ` [03/55] [media] pvrusb2: fix g/s_tuner support Greg KH
2011-08-06 0:01 ` [04/55] [media] bttv: fix s_tuner for radio Greg KH
2011-08-06 0:01 ` [05/55] gro: Only reset frag0 when skb can be pulled Greg KH
2011-08-06 0:01 ` [06/55] NFSv4.1: update nfs4_fattr_bitmap_maxsz Greg KH
2011-08-06 0:01 ` [07/55] SUNRPC: Fix a race between work-queue and rpc_killall_tasks Greg KH
2011-08-07 17:38 ` [Stable-review] " Ben Hutchings
2011-08-08 17:03 ` Greg KH
2011-08-08 18:07 ` Ben Hutchings
2011-08-06 0:01 ` [08/55] SUNRPC: Fix use of static variable in rpcb_getport_async Greg KH
2011-08-06 0:01 ` [09/55] si4713-i2c: avoid potential buffer overflow on si4713 Greg KH
2011-08-06 0:01 ` [10/55] hwmon: (max1111) Fix race condition causing NULL pointer exception Greg KH
2011-08-06 0:01 ` [11/55] bridge: send proper message_age in config BPDU Greg KH
2011-08-06 0:01 ` [12/55] davinci: DM365 EVM: fix video input mux bits Greg KH
2011-08-06 0:01 ` [13/55] libata: fix unexpectedly frozen port after ata_eh_reset() Greg KH
2011-08-06 0:01 ` [14/55] x86: Make Dell Latitude E5420 use reboot=pci Greg KH
2011-08-06 0:01 ` [15/55] USB: pl2303: add AdLink ND-6530 USB IDs Greg KH
2011-08-06 0:01 ` [16/55] USB: pl2303.h: checkpatch cleanups Greg KH
2011-08-06 0:01 ` [17/55] USB: serial: add IDs for WinChipHead USB->RS232 adapter Greg KH
2011-08-06 0:01 ` [18/55] staging: comedi: fix infoleak to userspace Greg KH
2011-08-06 0:01 ` [19/55] USB: OHCI: fix another regression for NVIDIA controllers Greg KH
2011-08-06 0:01 ` [20/55] usb: musb: restore INDEX register in resume path Greg KH
2011-08-06 0:01 ` [21/55] USB: dummy-hcd needs the has_tt flag Greg KH
2011-08-06 0:01 ` [22/55] ARM: pxa/cm-x300: fix V3020 RTC functionality Greg KH
2011-08-06 0:01 ` [23/55] jme: Fix unmap error (Causing system freeze) Greg KH
2011-08-06 0:01 ` [24/55] [SCSI] libsas: remove expander from dev list on error Greg KH
2011-08-06 0:01 ` [25/55] mac80211: Restart STA timers only on associated state Greg KH
2011-08-06 0:01 ` [26/55] [SCSI] Blacklist Traxdata CDR4120 and IOMEGA Zip drive to avoid lock ups Greg KH
2011-08-06 0:01 ` [27/55] [SCSI] ses: requesting a fault indication Greg KH
2011-08-06 0:01 ` [28/55] [SCSI] fix crash in scsi_dispatch_cmd() Greg KH
[not found] ` <1312739411.2591.1026.camel@deadeye>
2011-08-07 17:51 ` [Stable-review] " Ben Hutchings
2011-08-08 17:04 ` Greg KH
2011-08-08 18:10 ` Ben Hutchings
2011-08-08 19:17 ` Dave Jones
2011-08-09 20:22 ` James Bottomley
2011-08-06 0:01 ` [29/55] [SCSI] pmcraid: reject negative request size Greg KH
2011-08-06 0:02 ` [30/55] kexec, x86: Fix incorrect jump back address if not Greg KH
2011-08-06 0:02 ` [31/55] powerpc/kdump: Fix timeout in crash_kexec_wait_realmode Greg KH
2011-08-06 0:02 ` [32/55] PCI: ARI is a PCIe v2 feature Greg KH
2011-08-06 0:02 ` [33/55] cciss: do not attempt to read from a write-only register Greg KH
2011-08-06 0:02 ` [34/55] xtensa: prevent arbitrary read in ptrace Greg KH
2011-08-06 0:02 ` [35/55] ext3: Fix oops in ext3_try_to_allocate_with_rsv() Greg KH
2011-08-06 0:02 ` [36/55] svcrpc: fix list-corrupting race on nfsd shutdown Greg KH
2011-08-06 0:02 ` [37/55] EHCI: only power off port if over-current is active Greg KH
2011-08-06 0:02 ` [38/55] EHCI: fix direction handling for interrupt data toggles Greg KH
2011-08-06 0:02 ` [39/55] powerpc/pseries/hvconsole: Fix dropped console output Greg KH
2011-08-06 0:02 ` Greg KH [this message]
2011-08-06 0:02 ` [41/55] x86: HPET: Chose a paranoid safe value for the ETIME check Greg KH
2011-08-06 0:02 ` [42/55] Revert "block: rescan partitions on invalidated devices on -ENOMEDIA Greg KH
2011-08-06 0:02 ` [43/55] cifs: clean up cifs_find_smb_ses (try #2) Greg KH
2011-08-06 0:02 ` [44/55] cifs: fix NULL pointer dereference in cifs_find_smb_ses Greg KH
2011-08-06 0:02 ` [45/55] cifs: check for NULL session password Greg KH
2011-08-06 0:02 ` [46/55] gre: fix netns vs proto registration ordering Greg KH
2011-08-06 0:02 ` [47/55] netns xfrm: fixup xfrm6_tunnel error propagation Greg KH
2011-08-06 0:02 ` [48/55] tunnels: fix netns vs proto registration ordering Greg KH
2011-08-06 0:02 ` [49/55] alpha: fix several security issues Greg KH
2011-08-06 0:02 ` [50/55] proc: restrict access to /proc/PID/io Greg KH
2011-08-06 0:02 ` [51/55] ALSA: sound/core/pcm_compat.c: adjust array index Greg KH
2011-08-06 0:02 ` [52/55] dm mpath: fix potential NULL pointer in feature arg processing Greg KH
2011-08-06 0:02 ` [53/55] dm: fix idr leak on module removal Greg KH
2011-08-06 0:02 ` [54/55] perf: overflow/perf_count_sw_cpu_clock crashes recent kernels Greg KH
2011-08-06 0:02 ` [55/55] atm: [br2684] allow routed mode operation again Greg KH
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20110806000252.887106427@clark.kroah.org \
--to=gregkh@suse.de \
--cc=akpm@linux-foundation.org \
--cc=alan@lxorguk.ukuu.org.uk \
--cc=andreas.herrmann3@amd.com \
--cc=arjan@linux.intel.com \
--cc=damien.wyart@free.fr \
--cc=khlebnikov@openvz.org \
--cc=linux-kernel@vger.kernel.org \
--cc=stable-review@kernel.org \
--cc=stable@kernel.org \
--cc=suresh.b.siddha@intel.com \
--cc=tglx@linutronix.de \
--cc=torvalds@linux-foundation.org \
--cc=venki@google.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®