--- /dev/null
+From stable-bounces@linux.kernel.org Tue Aug 12 08:45:39 2008
+From: Timur Tabi <timur@freescale.com>
+Date: Tue, 12 Aug 2008 17:11:11 +0200
+Subject: ALSA: ASoC: fix SNDCTL_DSP_SYNC support in Freescale 8610 sound drivers
+To: stable@kernel.org
+Cc: Timur Tabi <timur@freescale.com>
+Message-ID: <s5hk5emjmk0.wl%tiwai@suse.de>
+
+From: Timur Tabi <timur@freescale.com>
+
+Upstream-commit-id: bf9c8c9ddef7ef761ae9747349175adad0ef16ce
+
+If an OSS application calls SNDCTL_DSP_SYNC, then ALSA will call the driver's
+_hw_params and _prepare functions again. On the Freescale MPC8610 DMA ASoC
+driver, this caused the DMA controller to be unneccessarily re-programmed, and
+apparently it doesn't like that. The DMA will then not operate when
+instructed. This patch relocates much of the DMA programming to
+fsl_dma_open(), which is called only once.
+
+Signed-off-by: Timur Tabi <timur@freescale.com>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ sound/soc/fsl/fsl_dma.c | 235 +++++++++++++++++++++++++-----------------------
+ 1 file changed, 124 insertions(+), 111 deletions(-)
+
+--- a/sound/soc/fsl/fsl_dma.c
++++ b/sound/soc/fsl/fsl_dma.c
+@@ -327,14 +327,75 @@ static int fsl_dma_new(struct snd_card *
+ * fsl_dma_open: open a new substream.
+ *
+ * Each substream has its own DMA buffer.
++ *
++ * ALSA divides the DMA buffer into N periods. We create NUM_DMA_LINKS link
++ * descriptors that ping-pong from one period to the next. For example, if
++ * there are six periods and two link descriptors, this is how they look
++ * before playback starts:
++ *
++ * The last link descriptor
++ * ____________ points back to the first
++ * | |
++ * V |
++ * ___ ___ |
++ * | |->| |->|
++ * |___| |___|
++ * | |
++ * | |
++ * V V
++ * _________________________________________
++ * | | | | | | | The DMA buffer is
++ * | | | | | | | divided into 6 parts
++ * |______|______|______|______|______|______|
++ *
++ * and here's how they look after the first period is finished playing:
++ *
++ * ____________
++ * | |
++ * V |
++ * ___ ___ |
++ * | |->| |->|
++ * |___| |___|
++ * | |
++ * |______________
++ * | |
++ * V V
++ * _________________________________________
++ * | | | | | | |
++ * | | | | | | |
++ * |______|______|______|______|______|______|
++ *
++ * The first link descriptor now points to the third period. The DMA
++ * controller is currently playing the second period. When it finishes, it
++ * will jump back to the first descriptor and play the third period.
++ *
++ * There are four reasons we do this:
++ *
++ * 1. The only way to get the DMA controller to automatically restart the
++ * transfer when it gets to the end of the buffer is to use chaining
++ * mode. Basic direct mode doesn't offer that feature.
++ * 2. We need to receive an interrupt at the end of every period. The DMA
++ * controller can generate an interrupt at the end of every link transfer
++ * (aka segment). Making each period into a DMA segment will give us the
++ * interrupts we need.
++ * 3. By creating only two link descriptors, regardless of the number of
++ * periods, we do not need to reallocate the link descriptors if the
++ * number of periods changes.
++ * 4. All of the audio data is still stored in a single, contiguous DMA
++ * buffer, which is what ALSA expects. We're just dividing it into
++ * contiguous parts, and creating a link descriptor for each one.
+ */
+ static int fsl_dma_open(struct snd_pcm_substream *substream)
+ {
+ struct snd_pcm_runtime *runtime = substream->runtime;
+ struct fsl_dma_private *dma_private;
++ struct ccsr_dma_channel __iomem *dma_channel;
+ dma_addr_t ld_buf_phys;
++ u64 temp_link; /* Pointer to next link descriptor */
++ u32 mr;
+ unsigned int channel;
+ int ret = 0;
++ unsigned int i;
+
+ /*
+ * Reject any DMA buffer whose size is not a multiple of the period
+@@ -395,68 +456,74 @@ static int fsl_dma_open(struct snd_pcm_s
+ snd_soc_set_runtime_hwparams(substream, &fsl_dma_hardware);
+ runtime->private_data = dma_private;
+
++ /* Program the fixed DMA controller parameters */
++
++ dma_channel = dma_private->dma_channel;
++
++ temp_link = dma_private->ld_buf_phys +
++ sizeof(struct fsl_dma_link_descriptor);
++
++ for (i = 0; i < NUM_DMA_LINKS; i++) {
++ struct fsl_dma_link_descriptor *link = &dma_private->link[i];
++
++ link->source_attr = cpu_to_be32(CCSR_DMA_ATR_SNOOP);
++ link->dest_attr = cpu_to_be32(CCSR_DMA_ATR_SNOOP);
++ link->next = cpu_to_be64(temp_link);
++
++ temp_link += sizeof(struct fsl_dma_link_descriptor);
++ }
++ /* The last link descriptor points to the first */
++ dma_private->link[i - 1].next = cpu_to_be64(dma_private->ld_buf_phys);
++
++ /* Tell the DMA controller where the first link descriptor is */
++ out_be32(&dma_channel->clndar,
++ CCSR_DMA_CLNDAR_ADDR(dma_private->ld_buf_phys));
++ out_be32(&dma_channel->eclndar,
++ CCSR_DMA_ECLNDAR_ADDR(dma_private->ld_buf_phys));
++
++ /* The manual says the BCR must be clear before enabling EMP */
++ out_be32(&dma_channel->bcr, 0);
++
++ /*
++ * Program the mode register for interrupts, external master control,
++ * and source/destination hold. Also clear the Channel Abort bit.
++ */
++ mr = in_be32(&dma_channel->mr) &
++ ~(CCSR_DMA_MR_CA | CCSR_DMA_MR_DAHE | CCSR_DMA_MR_SAHE);
++
++ /*
++ * We want External Master Start and External Master Pause enabled,
++ * because the SSI is controlling the DMA controller. We want the DMA
++ * controller to be set up in advance, and then we signal only the SSI
++ * to start transferring.
++ *
++ * We want End-Of-Segment Interrupts enabled, because this will generate
++ * an interrupt at the end of each segment (each link descriptor
++ * represents one segment). Each DMA segment is the same thing as an
++ * ALSA period, so this is how we get an interrupt at the end of every
++ * period.
++ *
++ * We want Error Interrupt enabled, so that we can get an error if
++ * the DMA controller is mis-programmed somehow.
++ */
++ mr |= CCSR_DMA_MR_EOSIE | CCSR_DMA_MR_EIE | CCSR_DMA_MR_EMP_EN |
++ CCSR_DMA_MR_EMS_EN;
++
++ /* For playback, we want the destination address to be held. For
++ capture, set the source address to be held. */
++ mr |= (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ?
++ CCSR_DMA_MR_DAHE : CCSR_DMA_MR_SAHE;
++
++ out_be32(&dma_channel->mr, mr);
++
+ return 0;
+ }
+
+ /**
+- * fsl_dma_hw_params: allocate the DMA buffer and the DMA link descriptors.
+- *
+- * ALSA divides the DMA buffer into N periods. We create NUM_DMA_LINKS link
+- * descriptors that ping-pong from one period to the next. For example, if
+- * there are six periods and two link descriptors, this is how they look
+- * before playback starts:
+- *
+- * The last link descriptor
+- * ____________ points back to the first
+- * | |
+- * V |
+- * ___ ___ |
+- * | |->| |->|
+- * |___| |___|
+- * | |
+- * | |
+- * V V
+- * _________________________________________
+- * | | | | | | | The DMA buffer is
+- * | | | | | | | divided into 6 parts
+- * |______|______|______|______|______|______|
+- *
+- * and here's how they look after the first period is finished playing:
+- *
+- * ____________
+- * | |
+- * V |
+- * ___ ___ |
+- * | |->| |->|
+- * |___| |___|
+- * | |
+- * |______________
+- * | |
+- * V V
+- * _________________________________________
+- * | | | | | | |
+- * | | | | | | |
+- * |______|______|______|______|______|______|
++ * fsl_dma_hw_params: continue initializing the DMA links
+ *
+- * The first link descriptor now points to the third period. The DMA
+- * controller is currently playing the second period. When it finishes, it
+- * will jump back to the first descriptor and play the third period.
+- *
+- * There are four reasons we do this:
+- *
+- * 1. The only way to get the DMA controller to automatically restart the
+- * transfer when it gets to the end of the buffer is to use chaining
+- * mode. Basic direct mode doesn't offer that feature.
+- * 2. We need to receive an interrupt at the end of every period. The DMA
+- * controller can generate an interrupt at the end of every link transfer
+- * (aka segment). Making each period into a DMA segment will give us the
+- * interrupts we need.
+- * 3. By creating only two link descriptors, regardless of the number of
+- * periods, we do not need to reallocate the link descriptors if the
+- * number of periods changes.
+- * 4. All of the audio data is still stored in a single, contiguous DMA
+- * buffer, which is what ALSA expects. We're just dividing it into
+- * contiguous parts, and creating a link descriptor for each one.
++ * This function obtains hardware parameters about the opened stream and
++ * programs the DMA controller accordingly.
+ *
+ * Note that due to a quirk of the SSI's STX register, the target address
+ * for the DMA operations depends on the sample size. So we don't program
+@@ -468,11 +535,8 @@ static int fsl_dma_hw_params(struct snd_
+ {
+ struct snd_pcm_runtime *runtime = substream->runtime;
+ struct fsl_dma_private *dma_private = runtime->private_data;
+- struct ccsr_dma_channel __iomem *dma_channel = dma_private->dma_channel;
+
+ dma_addr_t temp_addr; /* Pointer to next period */
+- u64 temp_link; /* Pointer to next link descriptor */
+- u32 mr; /* Temporary variable for MR register */
+
+ unsigned int i;
+
+@@ -490,8 +554,6 @@ static int fsl_dma_hw_params(struct snd_
+ dma_private->dma_buf_next = dma_private->dma_buf_phys;
+
+ /*
+- * Initialize each link descriptor.
+- *
+ * The actual address in STX0 (destination for playback, source for
+ * capture) is based on the sample size, but we don't know the sample
+ * size in this function, so we'll have to adjust that later. See
+@@ -507,16 +569,11 @@ static int fsl_dma_hw_params(struct snd_
+ * buffer itself.
+ */
+ temp_addr = substream->dma_buffer.addr;
+- temp_link = dma_private->ld_buf_phys +
+- sizeof(struct fsl_dma_link_descriptor);
+
+ for (i = 0; i < NUM_DMA_LINKS; i++) {
+ struct fsl_dma_link_descriptor *link = &dma_private->link[i];
+
+ link->count = cpu_to_be32(period_size);
+- link->source_attr = cpu_to_be32(CCSR_DMA_ATR_SNOOP);
+- link->dest_attr = cpu_to_be32(CCSR_DMA_ATR_SNOOP);
+- link->next = cpu_to_be64(temp_link);
+
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
+ link->source_addr = cpu_to_be32(temp_addr);
+@@ -524,51 +581,7 @@ static int fsl_dma_hw_params(struct snd_
+ link->dest_addr = cpu_to_be32(temp_addr);
+
+ temp_addr += period_size;
+- temp_link += sizeof(struct fsl_dma_link_descriptor);
+ }
+- /* The last link descriptor points to the first */
+- dma_private->link[i - 1].next = cpu_to_be64(dma_private->ld_buf_phys);
+-
+- /* Tell the DMA controller where the first link descriptor is */
+- out_be32(&dma_channel->clndar,
+- CCSR_DMA_CLNDAR_ADDR(dma_private->ld_buf_phys));
+- out_be32(&dma_channel->eclndar,
+- CCSR_DMA_ECLNDAR_ADDR(dma_private->ld_buf_phys));
+-
+- /* The manual says the BCR must be clear before enabling EMP */
+- out_be32(&dma_channel->bcr, 0);
+-
+- /*
+- * Program the mode register for interrupts, external master control,
+- * and source/destination hold. Also clear the Channel Abort bit.
+- */
+- mr = in_be32(&dma_channel->mr) &
+- ~(CCSR_DMA_MR_CA | CCSR_DMA_MR_DAHE | CCSR_DMA_MR_SAHE);
+-
+- /*
+- * We want External Master Start and External Master Pause enabled,
+- * because the SSI is controlling the DMA controller. We want the DMA
+- * controller to be set up in advance, and then we signal only the SSI
+- * to start transfering.
+- *
+- * We want End-Of-Segment Interrupts enabled, because this will generate
+- * an interrupt at the end of each segment (each link descriptor
+- * represents one segment). Each DMA segment is the same thing as an
+- * ALSA period, so this is how we get an interrupt at the end of every
+- * period.
+- *
+- * We want Error Interrupt enabled, so that we can get an error if
+- * the DMA controller is mis-programmed somehow.
+- */
+- mr |= CCSR_DMA_MR_EOSIE | CCSR_DMA_MR_EIE | CCSR_DMA_MR_EMP_EN |
+- CCSR_DMA_MR_EMS_EN;
+-
+- /* For playback, we want the destination address to be held. For
+- capture, set the source address to be held. */
+- mr |= (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ?
+- CCSR_DMA_MR_DAHE : CCSR_DMA_MR_SAHE;
+-
+- out_be32(&dma_channel->mr, mr);
+
+ return 0;
+ }
--- /dev/null
+From stable-bounces@linux.kernel.org Tue Aug 12 09:25:40 2008
+From: Timur Tabi <timur@freescale.com>
+Date: Tue, 12 Aug 2008 17:09:25 +0200
+Subject: ALSA: asoc: restrict sample rate and size in Freescale MPC8610 sound drivers
+To: stable@kernel.org
+Cc: Timur Tabi <timur@freescale.com>
+Message-ID: <s5hljz2jmmy.wl%tiwai@suse.de>
+
+
+From: Timur Tabi <timur@freescale.com>
+
+Upstream-commid-id: be41e941d5f1a48bde7f44d09d56e8d2605f98e1
+
+The Freescale MPC8610 SSI device has the option of using one clock for both
+transmit and receive (synchronous mode), or independent clocks (asynchronous).
+The SSI driver, however, programs the SSI into synchronous mode and then
+tries to program the clock registers independently. The result is that the wrong
+sample size is usually generated during recording.
+
+This patch fixes the discrepancy by restricting the sample rate and sample size
+of the playback and capture streams. The SSI driver remembers which stream
+is opened first. When a second stream is opened, that stream is constrained
+to the same sample rate and size as the first stream.
+
+A future version of this driver will lift the sample size restriction.
+Supporting independent sample rates is more difficult, because only certain
+codecs provide dual independent clocks.
+
+Signed-off-by: Timur Tabi <timur@freescale.com>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ sound/soc/fsl/fsl_dma.c | 7 +++-
+ sound/soc/fsl/fsl_ssi.c | 74 +++++++++++++++++++++++++++++++++++++++++-------
+ 2 files changed, 70 insertions(+), 11 deletions(-)
+
+--- a/sound/soc/fsl/fsl_dma.c
++++ b/sound/soc/fsl/fsl_dma.c
+@@ -132,12 +132,17 @@ struct fsl_dma_private {
+ * Since each link descriptor has a 32-bit byte count field, we set
+ * period_bytes_max to the largest 32-bit number. We also have no maximum
+ * number of periods.
++ *
++ * Note that we specify SNDRV_PCM_INFO_JOINT_DUPLEX here, but only because a
++ * limitation in the SSI driver requires the sample rates for playback and
++ * capture to be the same.
+ */
+ static const struct snd_pcm_hardware fsl_dma_hardware = {
+
+ .info = SNDRV_PCM_INFO_INTERLEAVED |
+ SNDRV_PCM_INFO_MMAP |
+- SNDRV_PCM_INFO_MMAP_VALID,
++ SNDRV_PCM_INFO_MMAP_VALID |
++ SNDRV_PCM_INFO_JOINT_DUPLEX,
+ .formats = FSLDMA_PCM_FORMATS,
+ .rates = FSLDMA_PCM_RATES,
+ .rate_min = 5512,
+--- a/sound/soc/fsl/fsl_ssi.c
++++ b/sound/soc/fsl/fsl_ssi.c
+@@ -67,6 +67,8 @@
+ * @ssi: pointer to the SSI's registers
+ * @ssi_phys: physical address of the SSI registers
+ * @irq: IRQ of this SSI
++ * @first_stream: pointer to the stream that was opened first
++ * @second_stream: pointer to second stream
+ * @dev: struct device pointer
+ * @playback: the number of playback streams opened
+ * @capture: the number of capture streams opened
+@@ -79,6 +81,8 @@ struct fsl_ssi_private {
+ struct ccsr_ssi __iomem *ssi;
+ dma_addr_t ssi_phys;
+ unsigned int irq;
++ struct snd_pcm_substream *first_stream;
++ struct snd_pcm_substream *second_stream;
+ struct device *dev;
+ unsigned int playback;
+ unsigned int capture;
+@@ -342,6 +346,49 @@ static int fsl_ssi_startup(struct snd_pc
+ */
+ }
+
++ if (!ssi_private->first_stream)
++ ssi_private->first_stream = substream;
++ else {
++ /* This is the second stream open, so we need to impose sample
++ * rate and maybe sample size constraints. Note that this can
++ * cause a race condition if the second stream is opened before
++ * the first stream is fully initialized.
++ *
++ * We provide some protection by checking to make sure the first
++ * stream is initialized, but it's not perfect. ALSA sometimes
++ * re-initializes the driver with a different sample rate or
++ * size. If the second stream is opened before the first stream
++ * has received its final parameters, then the second stream may
++ * be constrained to the wrong sample rate or size.
++ *
++ * FIXME: This code does not handle opening and closing streams
++ * repeatedly. If you open two streams and then close the first
++ * one, you may not be able to open another stream until you
++ * close the second one as well.
++ */
++ struct snd_pcm_runtime *first_runtime =
++ ssi_private->first_stream->runtime;
++
++ if (!first_runtime->rate || !first_runtime->sample_bits) {
++ dev_err(substream->pcm->card->dev,
++ "set sample rate and size in %s stream first\n",
++ substream->stream == SNDRV_PCM_STREAM_PLAYBACK
++ ? "capture" : "playback");
++ return -EAGAIN;
++ }
++
++ snd_pcm_hw_constraint_minmax(substream->runtime,
++ SNDRV_PCM_HW_PARAM_RATE,
++ first_runtime->rate, first_runtime->rate);
++
++ snd_pcm_hw_constraint_minmax(substream->runtime,
++ SNDRV_PCM_HW_PARAM_SAMPLE_BITS,
++ first_runtime->sample_bits,
++ first_runtime->sample_bits);
++
++ ssi_private->second_stream = substream;
++ }
++
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
+ ssi_private->playback++;
+
+@@ -371,18 +418,16 @@ static int fsl_ssi_prepare(struct snd_pc
+ struct fsl_ssi_private *ssi_private = rtd->dai->cpu_dai->private_data;
+
+ struct ccsr_ssi __iomem *ssi = ssi_private->ssi;
+- u32 wl;
+
+- wl = CCSR_SSI_SxCCR_WL(snd_pcm_format_width(runtime->format));
++ if (substream == ssi_private->first_stream) {
++ u32 wl;
+
+- clrbits32(&ssi->scr, CCSR_SSI_SCR_SSIEN);
++ /* The SSI should always be disabled at this points (SSIEN=0) */
++ wl = CCSR_SSI_SxCCR_WL(snd_pcm_format_width(runtime->format));
+
+- if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
++ /* In synchronous mode, the SSI uses STCCR for capture */
+ clrsetbits_be32(&ssi->stccr, CCSR_SSI_SxCCR_WL_MASK, wl);
+- else
+- clrsetbits_be32(&ssi->srccr, CCSR_SSI_SxCCR_WL_MASK, wl);
+-
+- setbits32(&ssi->scr, CCSR_SSI_SCR_SSIEN);
++ }
+
+ return 0;
+ }
+@@ -407,9 +452,13 @@ static int fsl_ssi_trigger(struct snd_pc
+ case SNDRV_PCM_TRIGGER_RESUME:
+ case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
+- setbits32(&ssi->scr, CCSR_SSI_SCR_TE);
++ clrbits32(&ssi->scr, CCSR_SSI_SCR_SSIEN);
++ setbits32(&ssi->scr,
++ CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE);
+ } else {
+- setbits32(&ssi->scr, CCSR_SSI_SCR_RE);
++ clrbits32(&ssi->scr, CCSR_SSI_SCR_SSIEN);
++ setbits32(&ssi->scr,
++ CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_RE);
+
+ /*
+ * I think we need this delay to allow time for the SSI
+@@ -452,6 +501,11 @@ static void fsl_ssi_shutdown(struct snd_
+ if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
+ ssi_private->capture--;
+
++ if (ssi_private->first_stream == substream)
++ ssi_private->first_stream = ssi_private->second_stream;
++
++ ssi_private->second_stream = NULL;
++
+ /*
+ * If this is the last active substream, disable the SSI and release
+ * the IRQ.
--- /dev/null
+From 04e1e0cccade330ab3715ce59234f7e3b087e246 Mon Sep 17 00:00:00 2001
+From: Jan Beulich <jbeulich@novell.com>
+Date: Tue, 22 Jul 2008 13:04:18 +0000
+Subject: CIFS: Fix compiler warning on 64-bit
+Message-ID: <489B8E32.3030703@redhat.com>
+
+From: Jan Beulich <jbeulich@novell.com>
+
+commit 04e1e0cccade330ab3715ce59234f7e3b087e246 upstream.
+
+Signed-off-by: Steve French <sfrench@us.ibm.com>
+Cc: Eugene Teo <eteo@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/cifs/asn1.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/cifs/asn1.c
++++ b/fs/cifs/asn1.c
+@@ -400,7 +400,7 @@ asn1_oid_decode(struct asn1_ctx *ctx,
+ size = eoc - ctx->pointer + 1;
+
+ /* first subid actually encodes first two subids */
+- if (size < 2 || size > ULONG_MAX/sizeof(unsigned long))
++ if (size < 2 || size > UINT_MAX/sizeof(unsigned long))
+ return 0;
+
+ *oid = kmalloc(size * sizeof(unsigned long), GFP_ATOMIC);
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 6 09:43:49 2008
+From: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
+Date: Wed, 6 Aug 2008 18:40:27 +0200
+Subject: cs5520: add enablebits checking
+To: stable@kernel.org
+Cc: TAKADA Yoshihito <takada@mbf.nifty.com>
+Message-ID: <200808061840.27701.bzolnier@gmail.com>
+Content-Disposition: inline
+
+From: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
+
+upstream commit is 24307ffabd5b39bad443641f54b12ee2ba7a38ac
+
+Based on sparse comments in OpenFirmware code
+(no Cx5510/Cx5520 datasheet here).
+
+This fixes 2.6.26 regression reported by TAKADA
+and caused by addition of warm-plug support.
+
+Tested-by: TAKADA Yoshihito <takada@mbf.nifty.com>
+Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/ide/pci/cs5520.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/drivers/ide/pci/cs5520.c
++++ b/drivers/ide/pci/cs5520.c
+@@ -123,6 +123,7 @@ static const struct ide_dma_ops cs5520_d
+ #define DECLARE_CS_DEV(name_str) \
+ { \
+ .name = name_str, \
++ .enablebits = { {0x60, 0x01, 0x01}, {0x60, 0x02, 0x02} }, \
+ .port_ops = &cs5520_port_ops, \
+ .dma_ops = &cs5520_dma_ops, \
+ .host_flags = IDE_HFLAG_ISA_PORTS | \
--- /dev/null
+From stable-bounces@linux.kernel.org Tue Aug 12 02:34:13 2008
+From: Hans Verkuil <hverkuil@xs4all.nl>
+Date: Tue, 12 Aug 2008 10:50:29 +0200
+Subject: i2c: Fix NULL pointer dereference in i2c_new_probed_device
+To: stable@kernel.org
+Cc: Hans Verkuil <hverkuil@xs4all.nl>
+Message-ID: <20080812105029.3d156597@hyperion.delvare>
+
+
+From: Hans Verkuil <hverkuil@xs4all.nl>
+
+Already in Linus' tree:
+http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=b25b791b13aaa336b56c4f9bd417ff126363f80b
+
+Fix a NULL pointer dereference that happened when calling
+i2c_new_probed_device on one of the addresses for which we use byte
+reads instead of quick write for detection purpose (that is: 0x30-0x37
+and 0x50-0x5f).
+
+Signed-off-by: Hans Verkuil <hverkuil@xs4all.nl>
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/i2c/i2c-core.c | 4 +++-
+ 1 file changed, 3 insertions(+), 1 deletion(-)
+
+--- a/drivers/i2c/i2c-core.c
++++ b/drivers/i2c/i2c-core.c
+@@ -1196,9 +1196,11 @@ i2c_new_probed_device(struct i2c_adapter
+ if ((addr_list[i] & ~0x07) == 0x30
+ || (addr_list[i] & ~0x0f) == 0x50
+ || !i2c_check_functionality(adap, I2C_FUNC_SMBUS_QUICK)) {
++ union i2c_smbus_data data;
++
+ if (i2c_smbus_xfer(adap, addr_list[i], 0,
+ I2C_SMBUS_READ, 0,
+- I2C_SMBUS_BYTE, NULL) >= 0)
++ I2C_SMBUS_BYTE, &data) >= 0)
+ break;
+ } else {
+ if (i2c_smbus_xfer(adap, addr_list[i], 0,
--- /dev/null
+From stable-bounces@linux.kernel.org Tue Aug 12 02:34:23 2008
+From: Jean Delvare <khali@linux-fr.org>
+Date: Tue, 12 Aug 2008 10:52:06 +0200
+Subject: i2c: Let users select algorithm drivers manually again
+To: stable@kernel.org
+Message-ID: <20080812105206.0ab76058@hyperion.delvare>
+
+From: Jean Delvare <khali@linux-fr.org>
+
+Already in Linus' tree:
+http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=8d24f8dcb7ead491704e274883b2c627062f6235
+
+In kernel 2.6.26, the ability to select I2C algorithm drivers manually
+was removed, as all in-kernel drivers do that automatically. However
+there were some complaints that it was a problem for out-of-tree I2C
+bus drivers. In order to address these complaints, let's allow manual
+selection of these drivers again, but still hide them by default for
+better general user experience.
+
+This closes bug #11140:
+http://bugzilla.kernel.org/show_bug.cgi?id=11140
+
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/i2c/Kconfig | 14 ++++++++++++++
+ drivers/i2c/algos/Kconfig | 11 ++++++++---
+ 2 files changed, 22 insertions(+), 3 deletions(-)
+
+--- a/drivers/i2c/algos/Kconfig
++++ b/drivers/i2c/algos/Kconfig
+@@ -2,15 +2,20 @@
+ # I2C algorithm drivers configuration
+ #
+
++menu "I2C Algorithms"
++ depends on !I2C_HELPER_AUTO
++
+ config I2C_ALGOBIT
+- tristate
++ tristate "I2C bit-banging interfaces"
+
+ config I2C_ALGOPCF
+- tristate
++ tristate "I2C PCF 8584 interfaces"
+
+ config I2C_ALGOPCA
+- tristate
++ tristate "I2C PCA 9564 interfaces"
+
+ config I2C_ALGO_SGI
+ tristate
+ depends on SGI_IP22 || SGI_IP32 || X86_VISWS
++
++endmenu
+--- a/drivers/i2c/Kconfig
++++ b/drivers/i2c/Kconfig
+@@ -38,6 +38,20 @@ config I2C_CHARDEV
+ This support is also available as a module. If so, the module
+ will be called i2c-dev.
+
++config I2C_HELPER_AUTO
++ bool "Autoselect pertinent helper modules"
++ default y
++ help
++ Some I2C bus drivers require so-called "I2C algorithm" modules
++ to work. These are basically software-only abstractions of generic
++ I2C interfaces. This option will autoselect them so that you don't
++ have to care.
++
++ Unselect this only if you need to enable additional helper
++ modules, for example for use with external I2C bus drivers.
++
++ In doubt, say Y.
++
+ source drivers/i2c/algos/Kconfig
+ source drivers/i2c/busses/Kconfig
+ source drivers/i2c/chips/Kconfig
--- /dev/null
+From 84e0f3f6c1e26588fdcb9f1b0f99d0275229bc99 Mon Sep 17 00:00:00 2001
+From: Dimitri Gorokhovik <dimitri.gorokhovik@free.fr>
+Date: Wed, 16 Jul 2008 20:33:34 +0200
+Subject: ide: it821x in pass-through mode segfaults in 2.6.26-stable
+Message-ID: <200808102332.38330.bzolnier@gmail.com>
+
+commit 84e0f3f6c1e26588fdcb9f1b0f99d0275229bc99 upstream
+
+The driver of ITE8212 in pass-through mode (it8212.noraid=1 on cmndline)
+attempts to use the field `.dma_host_set' of the struct ide_dma_ops in
+`ide_config_drive_speed' which is set to NULL by default.
+
+So give a value to all fields of the struct ide_dma_ops.
+
+Signed-off-by: Dimitri Gorokhovik <dimitri.gorokhovik@free.fr>
+Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/ide/pci/it821x.c | 6 ++++++
+ 1 file changed, 6 insertions(+)
+
+--- a/drivers/ide/pci/it821x.c
++++ b/drivers/ide/pci/it821x.c
+@@ -512,8 +512,14 @@ static void __devinit it821x_quirkproc(i
+ }
+
+ static struct ide_dma_ops it821x_pass_through_dma_ops = {
++ .dma_host_set = ide_dma_host_set,
++ .dma_setup = ide_dma_setup,
++ .dma_exec_cmd = ide_dma_exec_cmd,
+ .dma_start = it821x_dma_start,
+ .dma_end = it821x_dma_end,
++ .dma_test_irq = ide_dma_test_irq,
++ .dma_timeout = ide_dma_timeout,
++ .dma_lost_irq = ide_dma_lost_irq,
+ };
+
+ /**
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 13 08:00:55 2008
+From: Avi Kivity <avi@qumranet.com>
+Date: Wed, 13 Aug 2008 18:00:28 +0300
+Subject: KVM: Avoid instruction emulation when event delivery is pending
+To: stable@kernel.org
+Cc: Marcelo Tosatti <mtosatti@redhat.com>
+Message-ID: <1218639630-28692-4-git-send-email-avi@qumranet.com>
+
+From: Avi Kivity <avi@qumranet.com>
+
+(cherry-picked from commit 577bdc496614ced56d999bbb425e85adf2386490)
+
+When an event (such as an interrupt) is injected, and the stack is
+shadowed (and therefore write protected), the guest will exit. The
+current code will see that the stack is shadowed and emulate a few
+instructions, each time postponing the injection. Eventually the
+injection may succeed, but at that time the guest may be unwilling
+to accept the interrupt (for example, the TPR may have changed).
+
+This occurs every once in a while during a Windows 2008 boot.
+
+Fix by unshadowing the fault address if the fault was due to an event
+injection.
+
+Signed-off-by: Avi Kivity <avi@qumranet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kvm/mmu.c | 1 +
+ arch/x86/kvm/svm.c | 7 ++++++-
+ arch/x86/kvm/vmx.c | 2 ++
+ 3 files changed, 9 insertions(+), 1 deletion(-)
+
+--- a/arch/x86/kvm/mmu.c
++++ b/arch/x86/kvm/mmu.c
+@@ -1792,6 +1792,7 @@ int kvm_mmu_unprotect_page_virt(struct k
+ spin_unlock(&vcpu->kvm->mmu_lock);
+ return r;
+ }
++EXPORT_SYMBOL_GPL(kvm_mmu_unprotect_page_virt);
+
+ void __kvm_mmu_free_some_pages(struct kvm_vcpu *vcpu)
+ {
+--- a/arch/x86/kvm/svm.c
++++ b/arch/x86/kvm/svm.c
+@@ -1007,13 +1007,18 @@ static int pf_interception(struct vcpu_s
+ struct kvm *kvm = svm->vcpu.kvm;
+ u64 fault_address;
+ u32 error_code;
++ bool event_injection = false;
+
+ if (!irqchip_in_kernel(kvm) &&
+- is_external_interrupt(exit_int_info))
++ is_external_interrupt(exit_int_info)) {
++ event_injection = true;
+ push_irq(&svm->vcpu, exit_int_info & SVM_EVTINJ_VEC_MASK);
++ }
+
+ fault_address = svm->vmcb->control.exit_info_2;
+ error_code = svm->vmcb->control.exit_info_1;
++ if (event_injection)
++ kvm_mmu_unprotect_page_virt(&svm->vcpu, fault_address);
+ return kvm_mmu_page_fault(&svm->vcpu, fault_address, error_code);
+ }
+
+--- a/arch/x86/kvm/vmx.c
++++ b/arch/x86/kvm/vmx.c
+@@ -2258,6 +2258,8 @@ static int handle_exception(struct kvm_v
+ cr2 = vmcs_readl(EXIT_QUALIFICATION);
+ KVMTRACE_3D(PAGE_FAULT, vcpu, error_code, (u32)cr2,
+ (u32)((u64)cr2 >> 32), handler);
++ if (vect_info & VECTORING_INFO_VALID_MASK)
++ kvm_mmu_unprotect_page_virt(vcpu, cr2);
+ return kvm_mmu_page_fault(vcpu, cr2, error_code);
+ }
+
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 13 08:00:59 2008
+From: Julia Lawall <julia@diku.dk>
+Date: Wed, 13 Aug 2008 18:00:30 +0300
+Subject: KVM: ia64: Fix irq disabling leak in error handling code
+To: stable@kernel.org
+Cc: Marcelo Tosatti <mtosatti@redhat.com>, Julia Lawall <julia@diku.dk>
+Message-ID: <1218639630-28692-6-git-send-email-avi@qumranet.com>
+
+
+From: Julia Lawall <julia@diku.dk>
+
+(cherry picked from commit cab7a1eeeb007be309cd99cf14407261a72d2418)
+
+There is a call to local_irq_restore in the normal exit case, so it would
+seem that there should be one on an error return as well.
+
+The semantic patch that finds this problem is as follows:
+(http://www.emn.fr/x-info/coccinelle/)
+
+// <smpl>
+@@
+expression l;
+expression E,E1,E2;
+@@
+
+local_irq_save(l);
+... when != local_irq_restore(l)
+ when != spin_unlock_irqrestore(E,l)
+ when any
+ when strict
+(
+if (...) { ... when != local_irq_restore(l)
+ when != spin_unlock_irqrestore(E1,l)
++ local_irq_restore(l);
+ return ...;
+}
+|
+if (...)
++ {local_irq_restore(l);
+ return ...;
++ }
+|
+spin_unlock_irqrestore(E2,l);
+|
+local_irq_restore(l);
+)
+// </smpl>
+
+Signed-off-by: Julia Lawall <julia@diku.dk>
+Signed-off-by: Avi Kivity <avi@qumranet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/ia64/kvm/kvm-ia64.c | 5 +++--
+ 1 file changed, 3 insertions(+), 2 deletions(-)
+
+--- a/arch/ia64/kvm/kvm-ia64.c
++++ b/arch/ia64/kvm/kvm-ia64.c
+@@ -125,9 +125,9 @@ void kvm_arch_hardware_enable(void *garb
+ PAGE_KERNEL));
+ local_irq_save(saved_psr);
+ slot = ia64_itr_entry(0x3, KVM_VMM_BASE, pte, KVM_VMM_SHIFT);
++ local_irq_restore(saved_psr);
+ if (slot < 0)
+ return;
+- local_irq_restore(saved_psr);
+
+ spin_lock(&vp_lock);
+ status = ia64_pal_vp_init_env(kvm_vsa_base ?
+@@ -160,9 +160,9 @@ void kvm_arch_hardware_disable(void *gar
+
+ local_irq_save(saved_psr);
+ slot = ia64_itr_entry(0x3, KVM_VMM_BASE, pte, KVM_VMM_SHIFT);
++ local_irq_restore(saved_psr);
+ if (slot < 0)
+ return;
+- local_irq_restore(saved_psr);
+
+ status = ia64_pal_vp_exit_env(host_iva);
+ if (status)
+@@ -1258,6 +1258,7 @@ static int vti_vcpu_setup(struct kvm_vcp
+ uninit:
+ kvm_vcpu_uninit(vcpu);
+ fail:
++ local_irq_restore(psr);
+ return r;
+ }
+
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 13 08:00:51 2008
+From: Marcelo Tosatti <mtosatti@redhat.com>
+Date: Wed, 13 Aug 2008 18:00:26 +0300
+Subject: KVM: task switch: segment base is linear address
+To: stable@kernel.org
+Cc: Marcelo Tosatti <mtosatti@redhat.com>
+Message-ID: <1218639630-28692-2-git-send-email-avi@qumranet.com>
+
+
+From: Marcelo Tosatti <mtosatti@redhat.com>
+
+(cherry picked from commit 98899aa0e0bf5de05850082be0eb837058c09ea5)
+
+The segment base is always a linear address, so translate before
+accessing guest memory.
+
+Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com>
+Signed-off-by: Avi Kivity <avi@qumranet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kvm/x86.c | 12 +++++++++---
+ 1 file changed, 9 insertions(+), 3 deletions(-)
+
+--- a/arch/x86/kvm/x86.c
++++ b/arch/x86/kvm/x86.c
+@@ -3207,6 +3207,7 @@ static void get_segment_descritptor_dtab
+ static int load_guest_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector,
+ struct desc_struct *seg_desc)
+ {
++ gpa_t gpa;
+ struct descriptor_table dtable;
+ u16 index = selector >> 3;
+
+@@ -3216,13 +3217,16 @@ static int load_guest_segment_descriptor
+ kvm_queue_exception_e(vcpu, GP_VECTOR, selector & 0xfffc);
+ return 1;
+ }
+- return kvm_read_guest(vcpu->kvm, dtable.base + index * 8, seg_desc, 8);
++ gpa = vcpu->arch.mmu.gva_to_gpa(vcpu, dtable.base);
++ gpa += index * 8;
++ return kvm_read_guest(vcpu->kvm, gpa, seg_desc, 8);
+ }
+
+ /* allowed just for 8 bytes segments */
+ static int save_guest_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector,
+ struct desc_struct *seg_desc)
+ {
++ gpa_t gpa;
+ struct descriptor_table dtable;
+ u16 index = selector >> 3;
+
+@@ -3230,7 +3234,9 @@ static int save_guest_segment_descriptor
+
+ if (dtable.limit < index * 8 + 7)
+ return 1;
+- return kvm_write_guest(vcpu->kvm, dtable.base + index * 8, seg_desc, 8);
++ gpa = vcpu->arch.mmu.gva_to_gpa(vcpu, dtable.base);
++ gpa += index * 8;
++ return kvm_write_guest(vcpu->kvm, gpa, seg_desc, 8);
+ }
+
+ static u32 get_tss_base_addr(struct kvm_vcpu *vcpu,
+@@ -3242,7 +3248,7 @@ static u32 get_tss_base_addr(struct kvm_
+ base_addr |= (seg_desc->base1 << 16);
+ base_addr |= (seg_desc->base2 << 24);
+
+- return base_addr;
++ return vcpu->arch.mmu.gva_to_gpa(vcpu, base_addr);
+ }
+
+ static int load_tss_segment32(struct kvm_vcpu *vcpu,
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 13 08:00:47 2008
+From: Marcelo Tosatti <mtosatti@redhat.com>
+Date: Wed, 13 Aug 2008 18:00:29 +0300
+Subject: KVM: task switch: translate guest segment limit to virt-extension byte granular field
+To: stable@kernel.org
+Cc: Marcelo Tosatti <mtosatti@redhat.com>
+Message-ID: <1218639630-28692-5-git-send-email-avi@qumranet.com>
+
+
+From: Marcelo Tosatti <mtosatti@redhat.com>
+
+(cherry picked from commit c93cd3a58845012df2d658fecd0ac99f7008d753)
+
+If 'g' is one then limit is 4kb granular.
+
+Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com>
+Signed-off-by: Avi Kivity <avi@qumranet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kvm/x86.c | 4 ++++
+ 1 file changed, 4 insertions(+)
+
+--- a/arch/x86/kvm/x86.c
++++ b/arch/x86/kvm/x86.c
+@@ -3168,6 +3168,10 @@ static void seg_desct_to_kvm_desct(struc
+ kvm_desct->base |= seg_desc->base2 << 24;
+ kvm_desct->limit = seg_desc->limit0;
+ kvm_desct->limit |= seg_desc->limit << 16;
++ if (seg_desc->g) {
++ kvm_desct->limit <<= 12;
++ kvm_desct->limit |= 0xfff;
++ }
+ kvm_desct->selector = selector;
+ kvm_desct->type = seg_desc->type;
+ kvm_desct->present = seg_desc->p;
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 13 08:00:55 2008
+From: Marcelo Tosatti <mtosatti@redhat.com>
+Date: Wed, 13 Aug 2008 18:00:27 +0300
+Subject: KVM: task switch: use seg regs provided by subarch instead of reading from GDT
+To: stable@kernel.org
+Cc: Marcelo Tosatti <mtosatti@redhat.com>
+Message-ID: <1218639630-28692-3-git-send-email-avi@qumranet.com>
+
+
+From: Marcelo Tosatti <mtosatti@redhat.com>
+
+(cherry-picked from commit 34198bf8426276a2ce1e97056a0f02d43637e5ae)
+
+There is no guarantee that the old TSS descriptor in the GDT contains
+the proper base address. This is the case for Windows installation's
+reboot-via-triplefault.
+
+Use guest registers instead. Also translate the address properly.
+
+Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com>
+Signed-off-by: Avi Kivity <avi@qumranet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kvm/x86.c | 93 +++++++++++++++++------------------------------------
+ 1 file changed, 30 insertions(+), 63 deletions(-)
+
+--- a/arch/x86/kvm/x86.c
++++ b/arch/x86/kvm/x86.c
+@@ -3251,54 +3251,6 @@ static u32 get_tss_base_addr(struct kvm_
+ return vcpu->arch.mmu.gva_to_gpa(vcpu, base_addr);
+ }
+
+-static int load_tss_segment32(struct kvm_vcpu *vcpu,
+- struct desc_struct *seg_desc,
+- struct tss_segment_32 *tss)
+-{
+- u32 base_addr;
+-
+- base_addr = get_tss_base_addr(vcpu, seg_desc);
+-
+- return kvm_read_guest(vcpu->kvm, base_addr, tss,
+- sizeof(struct tss_segment_32));
+-}
+-
+-static int save_tss_segment32(struct kvm_vcpu *vcpu,
+- struct desc_struct *seg_desc,
+- struct tss_segment_32 *tss)
+-{
+- u32 base_addr;
+-
+- base_addr = get_tss_base_addr(vcpu, seg_desc);
+-
+- return kvm_write_guest(vcpu->kvm, base_addr, tss,
+- sizeof(struct tss_segment_32));
+-}
+-
+-static int load_tss_segment16(struct kvm_vcpu *vcpu,
+- struct desc_struct *seg_desc,
+- struct tss_segment_16 *tss)
+-{
+- u32 base_addr;
+-
+- base_addr = get_tss_base_addr(vcpu, seg_desc);
+-
+- return kvm_read_guest(vcpu->kvm, base_addr, tss,
+- sizeof(struct tss_segment_16));
+-}
+-
+-static int save_tss_segment16(struct kvm_vcpu *vcpu,
+- struct desc_struct *seg_desc,
+- struct tss_segment_16 *tss)
+-{
+- u32 base_addr;
+-
+- base_addr = get_tss_base_addr(vcpu, seg_desc);
+-
+- return kvm_write_guest(vcpu->kvm, base_addr, tss,
+- sizeof(struct tss_segment_16));
+-}
+-
+ static u16 get_segment_selector(struct kvm_vcpu *vcpu, int seg)
+ {
+ struct kvm_segment kvm_seg;
+@@ -3456,20 +3408,26 @@ static int load_state_from_tss16(struct
+ }
+
+ int kvm_task_switch_16(struct kvm_vcpu *vcpu, u16 tss_selector,
+- struct desc_struct *cseg_desc,
++ u32 old_tss_base,
+ struct desc_struct *nseg_desc)
+ {
+ struct tss_segment_16 tss_segment_16;
+ int ret = 0;
+
+- if (load_tss_segment16(vcpu, cseg_desc, &tss_segment_16))
++ if (kvm_read_guest(vcpu->kvm, old_tss_base, &tss_segment_16,
++ sizeof tss_segment_16))
+ goto out;
+
+ save_state_to_tss16(vcpu, &tss_segment_16);
+- save_tss_segment16(vcpu, cseg_desc, &tss_segment_16);
+
+- if (load_tss_segment16(vcpu, nseg_desc, &tss_segment_16))
++ if (kvm_write_guest(vcpu->kvm, old_tss_base, &tss_segment_16,
++ sizeof tss_segment_16))
++ goto out;
++
++ if (kvm_read_guest(vcpu->kvm, get_tss_base_addr(vcpu, nseg_desc),
++ &tss_segment_16, sizeof tss_segment_16))
+ goto out;
++
+ if (load_state_from_tss16(vcpu, &tss_segment_16))
+ goto out;
+
+@@ -3479,20 +3437,26 @@ out:
+ }
+
+ int kvm_task_switch_32(struct kvm_vcpu *vcpu, u16 tss_selector,
+- struct desc_struct *cseg_desc,
++ u32 old_tss_base,
+ struct desc_struct *nseg_desc)
+ {
+ struct tss_segment_32 tss_segment_32;
+ int ret = 0;
+
+- if (load_tss_segment32(vcpu, cseg_desc, &tss_segment_32))
++ if (kvm_read_guest(vcpu->kvm, old_tss_base, &tss_segment_32,
++ sizeof tss_segment_32))
+ goto out;
+
+ save_state_to_tss32(vcpu, &tss_segment_32);
+- save_tss_segment32(vcpu, cseg_desc, &tss_segment_32);
+
+- if (load_tss_segment32(vcpu, nseg_desc, &tss_segment_32))
++ if (kvm_write_guest(vcpu->kvm, old_tss_base, &tss_segment_32,
++ sizeof tss_segment_32))
++ goto out;
++
++ if (kvm_read_guest(vcpu->kvm, get_tss_base_addr(vcpu, nseg_desc),
++ &tss_segment_32, sizeof tss_segment_32))
+ goto out;
++
+ if (load_state_from_tss32(vcpu, &tss_segment_32))
+ goto out;
+
+@@ -3507,16 +3471,20 @@ int kvm_task_switch(struct kvm_vcpu *vcp
+ struct desc_struct cseg_desc;
+ struct desc_struct nseg_desc;
+ int ret = 0;
++ u32 old_tss_base = get_segment_base(vcpu, VCPU_SREG_TR);
++ u16 old_tss_sel = get_segment_selector(vcpu, VCPU_SREG_TR);
+
+- get_segment(vcpu, &tr_seg, VCPU_SREG_TR);
++ old_tss_base = vcpu->arch.mmu.gva_to_gpa(vcpu, old_tss_base);
+
++ /* FIXME: Handle errors. Failure to read either TSS or their
++ * descriptors should generate a pagefault.
++ */
+ if (load_guest_segment_descriptor(vcpu, tss_selector, &nseg_desc))
+ goto out;
+
+- if (load_guest_segment_descriptor(vcpu, tr_seg.selector, &cseg_desc))
++ if (load_guest_segment_descriptor(vcpu, old_tss_sel, &cseg_desc))
+ goto out;
+
+-
+ if (reason != TASK_SWITCH_IRET) {
+ int cpl;
+
+@@ -3534,8 +3502,7 @@ int kvm_task_switch(struct kvm_vcpu *vcp
+
+ if (reason == TASK_SWITCH_IRET || reason == TASK_SWITCH_JMP) {
+ cseg_desc.type &= ~(1 << 1); //clear the B flag
+- save_guest_segment_descriptor(vcpu, tr_seg.selector,
+- &cseg_desc);
++ save_guest_segment_descriptor(vcpu, old_tss_sel, &cseg_desc);
+ }
+
+ if (reason == TASK_SWITCH_IRET) {
+@@ -3547,10 +3514,10 @@ int kvm_task_switch(struct kvm_vcpu *vcp
+ kvm_x86_ops->cache_regs(vcpu);
+
+ if (nseg_desc.type & 8)
+- ret = kvm_task_switch_32(vcpu, tss_selector, &cseg_desc,
++ ret = kvm_task_switch_32(vcpu, tss_selector, old_tss_base,
+ &nseg_desc);
+ else
+- ret = kvm_task_switch_16(vcpu, tss_selector, &cseg_desc,
++ ret = kvm_task_switch_16(vcpu, tss_selector, old_tss_base,
+ &nseg_desc);
+
+ if (reason == TASK_SWITCH_CALL || reason == TASK_SWITCH_GATE) {
--- /dev/null
+From 77332894c21165404496c56763d7df6c15c4bb09 Mon Sep 17 00:00:00 2001
+From: Marcus Sundberg <marcus@ingate.com>
+Date: Thu, 10 Jul 2008 21:28:08 +0200
+Subject: r8169: avoid thrashing PCI conf space above RTL_GIGA_MAC_VER_06
+MIME-Version: 1.0
+Content-Type: text/plain; charset=utf-8
+Content-Transfer-Encoding: 8bit
+
+From: Marcus Sundberg <marcus@ingate.com>
+
+commit 77332894c21165404496c56763d7df6c15c4bb09 upstream
+
+The magic write to register 0x82 will often cause PCI config space on
+my 8168 (PCI ID 10ec:8168, revision 2. mounted in an LG P300 laptop)
+to be filled with ones during driver load, and thus breaking NIC
+operation until reboot. If it does not happen on first driver load it
+can easily be reproduced by unloading and loading the driver a few
+times.
+
+The magic write was added long ago by this commit:
+
+Author: François Romieu <romieu@fr.zoreil.com>
+Date: Sat Jan 10 06:00:46 2004 -0500
+
+ [netdrvr r8169] Merge of changes done by Realtek to rtl8169_init_one():
+ - phy capability settings allows lower or equal capability as suggested
+ in Realtek's changes;
+ - I/O voodoo;
+ - no need to s/mdio_write/RTL8169_WRITE_GMII_REG/;
+ - s/rtl8169_hw_PHY_config/rtl8169_hw_phy_config/;
+ - rtl8169_hw_phy_config(): ad-hoc struct "phy_magic" to limit duplication
+ of code (yep, the u16 -> int conversions should work as expected);
+ - variable renames and whitepace changes ignored.
+
+As the 8168 wasn't supported by that version this patch simply removes
+the bogus write from mac versions <= RTL_GIGA_MAC_VER_06.
+
+[The change above makes sense for the 8101/8102 too -- Ueimor]
+
+Signed-off-by: Marcus Sundberg <marcus@ingate.com>
+Signed-off-by: Francois Romieu <romieu@fr.zoreil.com>
+Cc: Karsten Keil <kkeil@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/net/r8169.c | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/net/r8169.c
++++ b/drivers/net/r8169.c
+@@ -1438,8 +1438,10 @@ static void rtl8169_init_phy(struct net_
+
+ rtl_hw_phy_config(dev);
+
+- dprintk("Set MAC Reg C+CR Offset 0x82h = 0x01h\n");
+- RTL_W8(0x82, 0x01);
++ if (tp->mac_version <= RTL_GIGA_MAC_VER_06) {
++ dprintk("Set MAC Reg C+CR Offset 0x82h = 0x01h\n");
++ RTL_W8(0x82, 0x01);
++ }
+
+ pci_write_config_byte(tp->pci_dev, PCI_LATENCY_TIMER, 0x40);
+
--- /dev/null
+From stable-bounces@linux.kernel.org Wed Aug 6 15:28:59 2008
+From: David Miller <davem@davemloft.net>
+Date: Wed, 6 Aug 2008 15:28:12 -0700
+Subject: radeon: misc corrections
+To: stable@kernel.org
+Cc: Benjamin Herrenschmidt <benh@kernel.crashing.org>, "David S. Miller" <davem@davemloft.net>
+Message-ID: <20080806152812.51242c18.akpm@linux-foundation.org>
+
+From: David Miller <davem@davemloft.net>
+
+Commit efc491814308f89d5ef6c4fe19ae4552a67d4132 upstream
+
+radeon: misc corrections
+
+I have a new PCI-E radeon RV380 series card (PCI device ID 5b64) that
+hangs in my sparc64 boxes when the init scripts set the font. The problem
+goes away if I disable acceleration.
+
+I haven't figured out that bug yet, but along the way I found some
+corrections to make based upon some auditing.
+
+1) The RB2D_DC_FLUSH_ALL value used by the kernel fb driver
+ and the XORG video driver differ. I've made the kernel
+ match what XORG is using.
+
+2) In radeonfb_engine_reset() we have top-level code structure
+ that roughly looks like:
+
+ if (family is 300, 350, or V350)
+ do this;
+ else
+ do that;
+ ...
+ if (family is NOT 300, OR
+ family is NOT 350, OR
+ family is NOT V350)
+ do another thing;
+
+ this last conditional makes no sense, is always true,
+ and obviously was likely meant to be "family is NOT
+ 300, 350, or V350". So I've made the code match the
+ intent.
+
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
+Tested-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/video/aty/radeon_accel.c | 4 ++--
+ include/video/radeon.h | 5 +++--
+ 2 files changed, 5 insertions(+), 4 deletions(-)
+
+--- a/drivers/video/aty/radeon_accel.c
++++ b/drivers/video/aty/radeon_accel.c
+@@ -249,8 +249,8 @@ void radeonfb_engine_reset(struct radeon
+ INREG(HOST_PATH_CNTL);
+ OUTREG(HOST_PATH_CNTL, host_path_cntl);
+
+- if (rinfo->family != CHIP_FAMILY_R300 ||
+- rinfo->family != CHIP_FAMILY_R350 ||
++ if (rinfo->family != CHIP_FAMILY_R300 &&
++ rinfo->family != CHIP_FAMILY_R350 &&
+ rinfo->family != CHIP_FAMILY_RV350)
+ OUTREG(RBBM_SOFT_RESET, rbbm_soft_reset);
+
+--- a/include/video/radeon.h
++++ b/include/video/radeon.h
+@@ -527,8 +527,9 @@
+
+
+ /* DSTCACHE_CTLSTAT bit constants */
+-#define RB2D_DC_FLUSH (3 << 0)
+-#define RB2D_DC_FLUSH_ALL 0xf
++#define RB2D_DC_FLUSH_2D (1 << 0)
++#define RB2D_DC_FREE_2D (1 << 2)
++#define RB2D_DC_FLUSH_ALL (RB2D_DC_FLUSH_2D | RB2D_DC_FREE_2D)
+ #define RB2D_DC_BUSY (1 << 31)
+
+
--- /dev/null
+From stable-bounces@linux.kernel.org Tue Aug 5 21:22:47 2008
+From: Larry Finger <Larry.Finger@lwfinger.net>
+Date: Tue, 05 Aug 2008 23:20:56 -0500
+Subject: [stable] [PATCH] rtl8187: Fix lockups due to concurrent access to config routine
+To: stable@kernel.org
+Message-ID: <489926a8.Tmk8qWQZeTkY9DVD%Larry.Finger@lwfinger.net>
+
+From: Larry Finger <Larry.Finger@lwfinger.net>
+
+With the rtl8187 driver, the config routine is not protected against
+access before a previous call has completed. When this happens, the
+TX loopback that is needed to change channels may cause the chip to
+be locked with a reset needed to restore communications. This patch
+entered mainline as commit 7dcdd073bf78bb6958bbc12a1a47754a0f3c4721.
+
+The problem was found by Herton Ronaldo Krzesinski <herton@mandriva.com.br>,
+who also suggested this type of fix.
+
+Signed-off-by: Larry Finger <Larry.Finger@lwfinger.net>
+Acked-by: Herton Ronaldo Krzesinski <herton@mandriva.com.br>
+Acked-by: Hin-Tak Leung <htl10@users.sourceforge.net>
+Signed-off-by: John W. Linville <linville@tuxdriver.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+
+---
+ drivers/net/wireless/rtl8187.h | 4 ++++
+ drivers/net/wireless/rtl8187_dev.c | 3 +++
+ 2 files changed, 7 insertions(+)
+
+--- a/drivers/net/wireless/rtl8187_dev.c
++++ b/drivers/net/wireless/rtl8187_dev.c
+@@ -580,6 +580,7 @@ static int rtl8187_config(struct ieee802
+ struct rtl8187_priv *priv = dev->priv;
+ u32 reg;
+
++ mutex_lock(&priv->conf_mutex);
+ reg = rtl818x_ioread32(priv, &priv->map->TX_CONF);
+ /* Enable TX loopback on MAC level to avoid TX during channel
+ * changes, as this has be seen to causes problems and the
+@@ -610,6 +611,7 @@ static int rtl8187_config(struct ieee802
+ rtl818x_iowrite16(priv, &priv->map->ATIMTR_INTERVAL, 100);
+ rtl818x_iowrite16(priv, &priv->map->BEACON_INTERVAL, 100);
+ rtl818x_iowrite16(priv, &priv->map->BEACON_INTERVAL_TIME, 100);
++ mutex_unlock(&priv->conf_mutex);
+ return 0;
+ }
+
+@@ -814,6 +816,7 @@ static int __devinit rtl8187_probe(struc
+ printk(KERN_ERR "rtl8187: Cannot register device\n");
+ goto err_free_dev;
+ }
++ mutex_init(&priv->conf_mutex);
+
+ printk(KERN_INFO "%s: hwaddr %s, rtl8187 V%d + %s\n",
+ wiphy_name(dev->wiphy), print_mac(mac, dev->wiphy->perm_addr),
+--- a/drivers/net/wireless/rtl8187.h
++++ b/drivers/net/wireless/rtl8187.h
+@@ -67,6 +67,10 @@ struct rtl8187_priv {
+ const struct rtl818x_rf_ops *rf;
+ struct ieee80211_vif *vif;
+ int mode;
++ /* The mutex protects the TX loopback state.
++ * Any attempt to set channels concurrently locks the device.
++ */
++ struct mutex conf_mutex;
+
+ /* rtl8187 specific */
+ struct ieee80211_channel channels[14];
sparc64-futex_op_andn-fix.patch
sparc64-fix-global-reg-snapshotting-on-self-cpu.patch
sparc64-do-not-clobber-g7-in-setcontext-trap.patch
+kvm-task-switch-segment-base-is-linear-address.patch
+kvm-task-switch-use-seg-regs-provided-by-subarch-instead-of-reading-from-gdt.patch
+kvm-avoid-instruction-emulation-when-event-delivery-is-pending.patch
+kvm-task-switch-translate-guest-segment-limit-to-virt-extension-byte-granular-field.patch
+kvm-ia64-fix-irq-disabling-leak-in-error-handling-code.patch
+r8169-avoid-thrashing-pci-conf-space-above-rtl_giga_mac_ver_06.patch
+alsa-asoc-restrict-sample-rate-and-size-in-freescale-mpc8610-sound-drivers.patch
+i2c-fix-null-pointer-dereference-in-i2c_new_probed_device.patch
+i2c-let-users-select-algorithm-drivers-manually-again.patch
+alsa-asoc-fix-sndctl_dsp_sync-support-in-freescale-8610-sound-drivers.patch
+x86-amd-opteron-tom2-mask-val-fix.patch
+ide-it821x-in-pass-through-mode-segfaults-in-2.6.26-stable.patch
+cifs-fix-compiler-warning-on-64-bit.patch
+radeon-misc-corrections.patch
+cs5520-add-enablebits-checking.patch
+rtl8187-fix-lockups-due-to-concurrent-access-to-config-routine.patch
--- /dev/null
+From 8004dd965b13b01a96def054d420f6df7ff22d53 Mon Sep 17 00:00:00 2001
+From: Yinghai Lu <yhlu.kernel@gmail.com>
+Date: Mon, 12 May 2008 17:40:39 -0700
+Subject: x86: amd opteron TOM2 mask val fix
+
+From: Yinghai Lu <yhlu.kernel@gmail.com>
+
+commit 8004dd965b13b01a96def054d420f6df7ff22d53 upstream.
+
+there is a typo in the mask value, need to remove that extra 0,
+to avoid 4bit clearing.
+
+Signed-off-by: Yinghal Lu <yhlu.kernel@gmail.com>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Cc: maximilian attems <max@stro.at>
+Cc: Peter Palfrader <weasel@debian.org>
+Cc: dann frazier <dannf@debian.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+
+---
+ arch/x86/kernel/cpu/mtrr/generic.c | 2 +-
+ arch/x86/pci/k8-bus_64.c | 4 ++--
+ 2 files changed, 3 insertions(+), 3 deletions(-)
+
+--- a/arch/x86/kernel/cpu/mtrr/generic.c
++++ b/arch/x86/kernel/cpu/mtrr/generic.c
+@@ -219,7 +219,7 @@ void __init get_mtrr_state(void)
+ tom2 = hi;
+ tom2 <<= 32;
+ tom2 |= lo;
+- tom2 &= 0xffffff8000000ULL;
++ tom2 &= 0xffffff800000ULL;
+ }
+ if (mtrr_show) {
+ int high_width;
+--- a/arch/x86/pci/k8-bus_64.c
++++ b/arch/x86/pci/k8-bus_64.c
+@@ -384,7 +384,7 @@ static int __init early_fill_mp_bus_info
+ /* need to take out [0, TOM) for RAM*/
+ address = MSR_K8_TOP_MEM1;
+ rdmsrl(address, val);
+- end = (val & 0xffffff8000000ULL);
++ end = (val & 0xffffff800000ULL);
+ printk(KERN_INFO "TOM: %016lx aka %ldM\n", end, end>>20);
+ if (end < (1ULL<<32))
+ update_range(range, 0, end - 1);
+@@ -478,7 +478,7 @@ static int __init early_fill_mp_bus_info
+ /* TOP_MEM2 */
+ address = MSR_K8_TOP_MEM2;
+ rdmsrl(address, val);
+- end = (val & 0xffffff8000000ULL);
++ end = (val & 0xffffff800000ULL);
+ printk(KERN_INFO "TOM2: %016lx aka %ldM\n", end, end>>20);
+ update_range(range, 1ULL<<32, end - 1);
+ }