--- /dev/null
+From 40088dc4e1ead7df31728c73f5b51d71da18831d Mon Sep 17 00:00:00 2001
+From: Takashi Iwai <tiwai@suse.de>
+Date: Mon, 12 Mar 2018 13:55:48 +0100
+Subject: ALSA: hda - Revert power_save option default value
+
+From: Takashi Iwai <tiwai@suse.de>
+
+commit 40088dc4e1ead7df31728c73f5b51d71da18831d upstream.
+
+With the commit 1ba8f9d30817 ("ALSA: hda: Add a power_save
+blacklist"), we changed the default value of power_save option to -1
+for processing the power-save blacklist.
+Unfortunately, this seems breaking user-space applications that
+actually read the power_save parameter value via sysfs and judge /
+adjust the power-saving status. They see the value -1 as if the
+power-save is turned off, although the actual value is taken from
+CONFIG_SND_HDA_POWER_SAVE_DEFAULT and it can be a positive.
+
+So, overall, passing -1 there was no good idea. Let's partially
+revert it -- at least for power_save option default value is restored
+again to CONFIG_SND_HDA_POWER_SAVE_DEFAULT. Meanwhile, in this patch,
+we keep the blacklist behavior and make is adjustable via the new
+option, pm_blacklist.
+
+Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=199073
+Fixes: 1ba8f9d30817 ("ALSA: hda: Add a power_save blacklist")
+Acked-by: Hans de Goede <hdegoede@redhat.com>
+Cc: <stable@vger.kernel.org>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ sound/pci/hda/hda_intel.c | 9 ++++++---
+ 1 file changed, 6 insertions(+), 3 deletions(-)
+
+--- a/sound/pci/hda/hda_intel.c
++++ b/sound/pci/hda/hda_intel.c
+@@ -179,11 +179,15 @@ static const struct kernel_param_ops par
+ };
+ #define param_check_xint param_check_int
+
+-static int power_save = -1;
++static int power_save = CONFIG_SND_HDA_POWER_SAVE_DEFAULT;
+ module_param(power_save, xint, 0644);
+ MODULE_PARM_DESC(power_save, "Automatic power-saving timeout "
+ "(in second, 0 = disable).");
+
++static bool pm_blacklist = true;
++module_param(pm_blacklist, bool, 0644);
++MODULE_PARM_DESC(pm_blacklist, "Enable power-management blacklist");
++
+ /* reset the HD-audio controller in power save mode.
+ * this may give more power-saving, but will take longer time to
+ * wake up.
+@@ -2164,10 +2168,9 @@ static int azx_probe_continue(struct azx
+
+ val = power_save;
+ #ifdef CONFIG_PM
+- if (val == -1) {
++ if (pm_blacklist) {
+ const struct snd_pci_quirk *q;
+
+- val = CONFIG_SND_HDA_POWER_SAVE_DEFAULT;
+ q = snd_pci_quirk_lookup(chip->pci, power_save_blacklist);
+ if (q && val) {
+ dev_info(chip->card->dev, "device %04x:%04x is on the power_save blacklist, forcing power_save to 0\n",
--- /dev/null
+From 01c0b4265cc16bc1f43f475c5944c55c10d5768f Mon Sep 17 00:00:00 2001
+From: Takashi Iwai <tiwai@suse.de>
+Date: Sat, 10 Mar 2018 23:04:23 +0100
+Subject: ALSA: pcm: Fix UAF in snd_pcm_oss_get_formats()
+
+From: Takashi Iwai <tiwai@suse.de>
+
+commit 01c0b4265cc16bc1f43f475c5944c55c10d5768f upstream.
+
+snd_pcm_oss_get_formats() has an obvious use-after-free around
+snd_mask_test() calls, as spotted by syzbot. The passed format_mask
+argument is a pointer to the hw_params object that is freed before the
+loop. What a surprise that it has been present since the original
+code of decades ago...
+
+Reported-by: syzbot+4090700a4f13fccaf648@syzkaller.appspotmail.com
+Cc: <stable@vger.kernel.org>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ sound/core/oss/pcm_oss.c | 10 ++++++----
+ 1 file changed, 6 insertions(+), 4 deletions(-)
+
+--- a/sound/core/oss/pcm_oss.c
++++ b/sound/core/oss/pcm_oss.c
+@@ -1814,10 +1814,9 @@ static int snd_pcm_oss_get_formats(struc
+ return -ENOMEM;
+ _snd_pcm_hw_params_any(params);
+ err = snd_pcm_hw_refine(substream, params);
+- format_mask = *hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT);
+- kfree(params);
+ if (err < 0)
+- return err;
++ goto error;
++ format_mask = hw_param_mask_c(params, SNDRV_PCM_HW_PARAM_FORMAT);
+ for (fmt = 0; fmt < 32; ++fmt) {
+ if (snd_mask_test(&format_mask, fmt)) {
+ int f = snd_pcm_oss_format_to(fmt);
+@@ -1825,7 +1824,10 @@ static int snd_pcm_oss_get_formats(struc
+ formats |= f;
+ }
+ }
+- return formats;
++
++ error:
++ kfree(params);
++ return err < 0 ? err : formats;
+ }
+
+ static int snd_pcm_oss_set_format(struct snd_pcm_oss_file *pcm_oss_file, int format)
--- /dev/null
+From a2ff19f7b70118ced291a28d5313469914de451b Mon Sep 17 00:00:00 2001
+From: Takashi Iwai <tiwai@suse.de>
+Date: Fri, 9 Mar 2018 22:23:31 +0100
+Subject: ALSA: seq: Clear client entry before deleting else at closing
+
+From: Takashi Iwai <tiwai@suse.de>
+
+commit a2ff19f7b70118ced291a28d5313469914de451b upstream.
+
+When releasing a client, we need to clear the clienttab[] entry at
+first, then call snd_seq_queue_client_leave(). Otherwise, the
+in-flight cell in the queue might be picked up by the timer interrupt
+via snd_seq_check_queue() before calling snd_seq_queue_client_leave(),
+and it's delivered to another queue while the client is clearing
+queues. This may eventually result in an uncleared cell remaining in
+a queue, and the later snd_seq_pool_delete() may need to wait for a
+long time until the event gets really processed.
+
+By moving the clienttab[] clearance at the beginning of release, any
+event delivery of a cell belonging to this client will fail at a later
+point, since snd_seq_client_ptr() returns NULL. Thus the cell that
+was picked up by the timer interrupt will be returned immediately
+without further delivery, and the long stall of snd_seq_delete_pool()
+can be avoided, too.
+
+Cc: <stable@vger.kernel.org>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ sound/core/seq/seq_clientmgr.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+--- a/sound/core/seq/seq_clientmgr.c
++++ b/sound/core/seq/seq_clientmgr.c
+@@ -270,12 +270,12 @@ static int seq_free_client1(struct snd_s
+
+ if (!client)
+ return 0;
+- snd_seq_delete_all_ports(client);
+- snd_seq_queue_client_leave(client->number);
+ spin_lock_irqsave(&clients_lock, flags);
+ clienttablock[client->number] = 1;
+ clienttab[client->number] = NULL;
+ spin_unlock_irqrestore(&clients_lock, flags);
++ snd_seq_delete_all_ports(client);
++ snd_seq_queue_client_leave(client->number);
+ snd_use_lock_sync(&client->use_lock);
+ snd_seq_queue_client_termination(client->number);
+ if (client->pool)
--- /dev/null
+From d0f833065221cbfcbadf19fd4102bcfa9330006a Mon Sep 17 00:00:00 2001
+From: Takashi Iwai <tiwai@suse.de>
+Date: Fri, 9 Mar 2018 21:58:28 +0100
+Subject: ALSA: seq: Fix possible UAF in snd_seq_check_queue()
+
+From: Takashi Iwai <tiwai@suse.de>
+
+commit d0f833065221cbfcbadf19fd4102bcfa9330006a upstream.
+
+Although we've covered the races between concurrent write() and
+ioctl() in the previous patch series, there is still a possible UAF in
+the following scenario:
+
+A: user client closed B: timer irq
+ -> snd_seq_release() -> snd_seq_timer_interrupt()
+ -> snd_seq_free_client() -> snd_seq_check_queue()
+ -> cell = snd_seq_prioq_cell_peek()
+ -> snd_seq_prioq_leave()
+ .... removing all cells
+ -> snd_seq_pool_done()
+ .... vfree()
+ -> snd_seq_compare_tick_time(cell)
+ ... Oops
+
+So the problem is that a cell is peeked and accessed without any
+protection until it's retrieved from the queue again via
+snd_seq_prioq_cell_out().
+
+This patch tries to address it, also cleans up the code by a slight
+refactoring. snd_seq_prioq_cell_out() now receives an extra pointer
+argument. When it's non-NULL, the function checks the event timestamp
+with the given pointer. The caller needs to pass the right reference
+either to snd_seq_tick or snd_seq_realtime depending on the event
+timestamp type.
+
+A good news is that the above change allows us to remove the
+snd_seq_prioq_cell_peek(), too, thus the patch actually reduces the
+code size.
+
+Reviewed-by: Nicolai Stange <nstange@suse.de>
+Cc: <stable@vger.kernel.org>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ sound/core/seq/seq_prioq.c | 28 ++++++++++++++--------------
+ sound/core/seq/seq_prioq.h | 6 ++----
+ sound/core/seq/seq_queue.c | 28 +++++++++-------------------
+ 3 files changed, 25 insertions(+), 37 deletions(-)
+
+--- a/sound/core/seq/seq_prioq.c
++++ b/sound/core/seq/seq_prioq.c
+@@ -87,7 +87,7 @@ void snd_seq_prioq_delete(struct snd_seq
+ if (f->cells > 0) {
+ /* drain prioQ */
+ while (f->cells > 0)
+- snd_seq_cell_free(snd_seq_prioq_cell_out(f));
++ snd_seq_cell_free(snd_seq_prioq_cell_out(f, NULL));
+ }
+
+ kfree(f);
+@@ -214,8 +214,18 @@ int snd_seq_prioq_cell_in(struct snd_seq
+ return 0;
+ }
+
++/* return 1 if the current time >= event timestamp */
++static int event_is_ready(struct snd_seq_event *ev, void *current_time)
++{
++ if ((ev->flags & SNDRV_SEQ_TIME_STAMP_MASK) == SNDRV_SEQ_TIME_STAMP_TICK)
++ return snd_seq_compare_tick_time(current_time, &ev->time.tick);
++ else
++ return snd_seq_compare_real_time(current_time, &ev->time.time);
++}
++
+ /* dequeue cell from prioq */
+-struct snd_seq_event_cell *snd_seq_prioq_cell_out(struct snd_seq_prioq *f)
++struct snd_seq_event_cell *snd_seq_prioq_cell_out(struct snd_seq_prioq *f,
++ void *current_time)
+ {
+ struct snd_seq_event_cell *cell;
+ unsigned long flags;
+@@ -227,6 +237,8 @@ struct snd_seq_event_cell *snd_seq_prioq
+ spin_lock_irqsave(&f->lock, flags);
+
+ cell = f->head;
++ if (cell && current_time && !event_is_ready(&cell->event, current_time))
++ cell = NULL;
+ if (cell) {
+ f->head = cell->next;
+
+@@ -252,18 +264,6 @@ int snd_seq_prioq_avail(struct snd_seq_p
+ return f->cells;
+ }
+
+-
+-/* peek at cell at the head of the prioq */
+-struct snd_seq_event_cell *snd_seq_prioq_cell_peek(struct snd_seq_prioq * f)
+-{
+- if (f == NULL) {
+- pr_debug("ALSA: seq: snd_seq_prioq_cell_in() called with NULL prioq\n");
+- return NULL;
+- }
+- return f->head;
+-}
+-
+-
+ static inline int prioq_match(struct snd_seq_event_cell *cell,
+ int client, int timestamp)
+ {
+--- a/sound/core/seq/seq_prioq.h
++++ b/sound/core/seq/seq_prioq.h
+@@ -44,14 +44,12 @@ void snd_seq_prioq_delete(struct snd_seq
+ int snd_seq_prioq_cell_in(struct snd_seq_prioq *f, struct snd_seq_event_cell *cell);
+
+ /* dequeue cell from prioq */
+-struct snd_seq_event_cell *snd_seq_prioq_cell_out(struct snd_seq_prioq *f);
++struct snd_seq_event_cell *snd_seq_prioq_cell_out(struct snd_seq_prioq *f,
++ void *current_time);
+
+ /* return number of events available in prioq */
+ int snd_seq_prioq_avail(struct snd_seq_prioq *f);
+
+-/* peek at cell at the head of the prioq */
+-struct snd_seq_event_cell *snd_seq_prioq_cell_peek(struct snd_seq_prioq *f);
+-
+ /* client left queue */
+ void snd_seq_prioq_leave(struct snd_seq_prioq *f, int client, int timestamp);
+
+--- a/sound/core/seq/seq_queue.c
++++ b/sound/core/seq/seq_queue.c
+@@ -277,30 +277,20 @@ void snd_seq_check_queue(struct snd_seq_
+
+ __again:
+ /* Process tick queue... */
+- while ((cell = snd_seq_prioq_cell_peek(q->tickq)) != NULL) {
+- if (snd_seq_compare_tick_time(&q->timer->tick.cur_tick,
+- &cell->event.time.tick)) {
+- cell = snd_seq_prioq_cell_out(q->tickq);
+- if (cell)
+- snd_seq_dispatch_event(cell, atomic, hop);
+- } else {
+- /* event remains in the queue */
++ for (;;) {
++ cell = snd_seq_prioq_cell_out(q->tickq,
++ &q->timer->tick.cur_tick);
++ if (!cell)
+ break;
+- }
++ snd_seq_dispatch_event(cell, atomic, hop);
+ }
+
+-
+ /* Process time queue... */
+- while ((cell = snd_seq_prioq_cell_peek(q->timeq)) != NULL) {
+- if (snd_seq_compare_real_time(&q->timer->cur_time,
+- &cell->event.time.time)) {
+- cell = snd_seq_prioq_cell_out(q->timeq);
+- if (cell)
+- snd_seq_dispatch_event(cell, atomic, hop);
+- } else {
+- /* event remains in the queue */
++ for (;;) {
++ cell = snd_seq_prioq_cell_out(q->timeq, &q->timer->cur_time);
++ if (!cell)
+ break;
+- }
++ snd_seq_dispatch_event(cell, atomic, hop);
+ }
+
+ /* free lock */
--- /dev/null
+From 7d617264eb22b18d979eac6e85877a141253034e Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Michel=20D=C3=A4nzer?= <michel.daenzer@amd.com>
+Date: Fri, 9 Mar 2018 18:26:18 +0100
+Subject: drm/amdgpu/dce: Don't turn off DP sink when disconnected
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Michel Dänzer <michel.daenzer@amd.com>
+
+commit 7d617264eb22b18d979eac6e85877a141253034e upstream.
+
+Turning off the sink in this case causes various issues, because
+userspace expects it to stay on until it turns it off explicitly.
+
+Instead, turn the sink off and back on when a display is connected
+again. This dance seems necessary for link training to work correctly.
+
+Bugzilla: https://bugs.freedesktop.org/105308
+Cc: stable@vger.kernel.org
+Reviewed-by: Alex Deucher <alexander.deucher@amd.com>
+Signed-off-by: Michel Dänzer <michel.daenzer@amd.com>
+Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c | 29 +++++++++----------------
+ 1 file changed, 11 insertions(+), 18 deletions(-)
+
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c
+@@ -69,25 +69,18 @@ void amdgpu_connector_hotplug(struct drm
+ /* don't do anything if sink is not display port, i.e.,
+ * passive dp->(dvi|hdmi) adaptor
+ */
+- if (dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT) {
+- int saved_dpms = connector->dpms;
+- /* Only turn off the display if it's physically disconnected */
+- if (!amdgpu_display_hpd_sense(adev, amdgpu_connector->hpd.hpd)) {
+- drm_helper_connector_dpms(connector, DRM_MODE_DPMS_OFF);
+- } else if (amdgpu_atombios_dp_needs_link_train(amdgpu_connector)) {
+- /* Don't try to start link training before we
+- * have the dpcd */
+- if (amdgpu_atombios_dp_get_dpcd(amdgpu_connector))
+- return;
++ if (dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT &&
++ amdgpu_display_hpd_sense(adev, amdgpu_connector->hpd.hpd) &&
++ amdgpu_atombios_dp_needs_link_train(amdgpu_connector)) {
++ /* Don't start link training before we have the DPCD */
++ if (amdgpu_atombios_dp_get_dpcd(amdgpu_connector))
++ return;
+
+- /* set it to OFF so that drm_helper_connector_dpms()
+- * won't return immediately since the current state
+- * is ON at this point.
+- */
+- connector->dpms = DRM_MODE_DPMS_OFF;
+- drm_helper_connector_dpms(connector, DRM_MODE_DPMS_ON);
+- }
+- connector->dpms = saved_dpms;
++ /* Turn the connector off and back on immediately, which
++ * will trigger link training
++ */
++ drm_helper_connector_dpms(connector, DRM_MODE_DPMS_OFF);
++ drm_helper_connector_dpms(connector, DRM_MODE_DPMS_ON);
+ }
+ }
+ }
--- /dev/null
+From a6d7cff472eea87d96899a20fa718d2bab7109f3 Mon Sep 17 00:00:00 2001
+From: Tejun Heo <tj@kernel.org>
+Date: Wed, 14 Mar 2018 12:10:17 -0700
+Subject: fs/aio: Add explicit RCU grace period when freeing kioctx
+
+From: Tejun Heo <tj@kernel.org>
+
+commit a6d7cff472eea87d96899a20fa718d2bab7109f3 upstream.
+
+While fixing refcounting, e34ecee2ae79 ("aio: Fix a trinity splat")
+incorrectly removed explicit RCU grace period before freeing kioctx.
+The intention seems to be depending on the internal RCU grace periods
+of percpu_ref; however, percpu_ref uses a different flavor of RCU,
+sched-RCU. This can lead to kioctx being freed while RCU read
+protected dereferences are still in progress.
+
+Fix it by updating free_ioctx() to go through call_rcu() explicitly.
+
+v2: Comment added to explain double bouncing.
+
+Signed-off-by: Tejun Heo <tj@kernel.org>
+Reported-by: Jann Horn <jannh@google.com>
+Fixes: e34ecee2ae79 ("aio: Fix a trinity splat")
+Cc: Kent Overstreet <kent.overstreet@gmail.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: stable@vger.kernel.org # v3.13+
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/aio.c | 23 +++++++++++++++++++----
+ 1 file changed, 19 insertions(+), 4 deletions(-)
+
+--- a/fs/aio.c
++++ b/fs/aio.c
+@@ -115,7 +115,8 @@ struct kioctx {
+ struct page **ring_pages;
+ long nr_pages;
+
+- struct work_struct free_work;
++ struct rcu_head free_rcu;
++ struct work_struct free_work; /* see free_ioctx() */
+
+ /*
+ * signals when all in-flight requests are done
+@@ -573,6 +574,12 @@ static int kiocb_cancel(struct aio_kiocb
+ return cancel(&kiocb->common);
+ }
+
++/*
++ * free_ioctx() should be RCU delayed to synchronize against the RCU
++ * protected lookup_ioctx() and also needs process context to call
++ * aio_free_ring(), so the double bouncing through kioctx->free_rcu and
++ * ->free_work.
++ */
+ static void free_ioctx(struct work_struct *work)
+ {
+ struct kioctx *ctx = container_of(work, struct kioctx, free_work);
+@@ -586,6 +593,14 @@ static void free_ioctx(struct work_struc
+ kmem_cache_free(kioctx_cachep, ctx);
+ }
+
++static void free_ioctx_rcufn(struct rcu_head *head)
++{
++ struct kioctx *ctx = container_of(head, struct kioctx, free_rcu);
++
++ INIT_WORK(&ctx->free_work, free_ioctx);
++ schedule_work(&ctx->free_work);
++}
++
+ static void free_ioctx_reqs(struct percpu_ref *ref)
+ {
+ struct kioctx *ctx = container_of(ref, struct kioctx, reqs);
+@@ -594,8 +609,8 @@ static void free_ioctx_reqs(struct percp
+ if (ctx->rq_wait && atomic_dec_and_test(&ctx->rq_wait->count))
+ complete(&ctx->rq_wait->comp);
+
+- INIT_WORK(&ctx->free_work, free_ioctx);
+- schedule_work(&ctx->free_work);
++ /* Synchronize against RCU protected table->table[] dereferences */
++ call_rcu(&ctx->free_rcu, free_ioctx_rcufn);
+ }
+
+ /*
+@@ -817,7 +832,7 @@ static int kill_ioctx(struct mm_struct *
+ table->table[ctx->id] = NULL;
+ spin_unlock(&mm->ioctx_lock);
+
+- /* percpu_ref_kill() will do the necessary call_rcu() */
++ /* free_ioctx_reqs() will do the necessary RCU synchronization */
+ wake_up_all(&ctx->wait);
+
+ /*
--- /dev/null
+From d0264c01e7587001a8c4608a5d1818dba9a4c11a Mon Sep 17 00:00:00 2001
+From: Tejun Heo <tj@kernel.org>
+Date: Wed, 14 Mar 2018 12:10:17 -0700
+Subject: fs/aio: Use RCU accessors for kioctx_table->table[]
+
+From: Tejun Heo <tj@kernel.org>
+
+commit d0264c01e7587001a8c4608a5d1818dba9a4c11a upstream.
+
+While converting ioctx index from a list to a table, db446a08c23d
+("aio: convert the ioctx list to table lookup v3") missed tagging
+kioctx_table->table[] as an array of RCU pointers and using the
+appropriate RCU accessors. This introduces a small window in the
+lookup path where init and access may race.
+
+Mark kioctx_table->table[] with __rcu and use the approriate RCU
+accessors when using the field.
+
+Signed-off-by: Tejun Heo <tj@kernel.org>
+Reported-by: Jann Horn <jannh@google.com>
+Fixes: db446a08c23d ("aio: convert the ioctx list to table lookup v3")
+Cc: Benjamin LaHaise <bcrl@kvack.org>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: stable@vger.kernel.org # v3.12+
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/aio.c | 21 +++++++++++----------
+ 1 file changed, 11 insertions(+), 10 deletions(-)
+
+--- a/fs/aio.c
++++ b/fs/aio.c
+@@ -68,9 +68,9 @@ struct aio_ring {
+ #define AIO_RING_PAGES 8
+
+ struct kioctx_table {
+- struct rcu_head rcu;
+- unsigned nr;
+- struct kioctx *table[];
++ struct rcu_head rcu;
++ unsigned nr;
++ struct kioctx __rcu *table[];
+ };
+
+ struct kioctx_cpu {
+@@ -327,7 +327,7 @@ static int aio_ring_mremap(struct vm_are
+ for (i = 0; i < table->nr; i++) {
+ struct kioctx *ctx;
+
+- ctx = table->table[i];
++ ctx = rcu_dereference(table->table[i]);
+ if (ctx && ctx->aio_ring_file == file) {
+ if (!atomic_read(&ctx->dead)) {
+ ctx->user_id = ctx->mmap_base = vma->vm_start;
+@@ -651,9 +651,9 @@ static int ioctx_add_table(struct kioctx
+ while (1) {
+ if (table)
+ for (i = 0; i < table->nr; i++)
+- if (!table->table[i]) {
++ if (!rcu_access_pointer(table->table[i])) {
+ ctx->id = i;
+- table->table[i] = ctx;
++ rcu_assign_pointer(table->table[i], ctx);
+ spin_unlock(&mm->ioctx_lock);
+
+ /* While kioctx setup is in progress,
+@@ -828,8 +828,8 @@ static int kill_ioctx(struct mm_struct *
+ }
+
+ table = rcu_dereference_raw(mm->ioctx_table);
+- WARN_ON(ctx != table->table[ctx->id]);
+- table->table[ctx->id] = NULL;
++ WARN_ON(ctx != rcu_access_pointer(table->table[ctx->id]));
++ RCU_INIT_POINTER(table->table[ctx->id], NULL);
+ spin_unlock(&mm->ioctx_lock);
+
+ /* free_ioctx_reqs() will do the necessary RCU synchronization */
+@@ -874,7 +874,8 @@ void exit_aio(struct mm_struct *mm)
+
+ skipped = 0;
+ for (i = 0; i < table->nr; ++i) {
+- struct kioctx *ctx = table->table[i];
++ struct kioctx *ctx =
++ rcu_dereference_protected(table->table[i], true);
+
+ if (!ctx) {
+ skipped++;
+@@ -1063,7 +1064,7 @@ static struct kioctx *lookup_ioctx(unsig
+ if (!table || id >= table->nr)
+ goto out;
+
+- ctx = table->table[id];
++ ctx = rcu_dereference(table->table[id]);
+ if (ctx && ctx->user_id == ctx_id) {
+ percpu_ref_get(&ctx->users);
+ ret = ctx;
--- /dev/null
+From 95dd77580ccd66a0da96e6d4696945b8cea39431 Mon Sep 17 00:00:00 2001
+From: "Eric W. Biederman" <ebiederm@xmission.com>
+Date: Wed, 14 Mar 2018 18:20:29 -0500
+Subject: fs: Teach path_connected to handle nfs filesystems with multiple roots.
+
+From: Eric W. Biederman <ebiederm@xmission.com>
+
+commit 95dd77580ccd66a0da96e6d4696945b8cea39431 upstream.
+
+On nfsv2 and nfsv3 the nfs server can export subsets of the same
+filesystem and report the same filesystem identifier, so that the nfs
+client can know they are the same filesystem. The subsets can be from
+disjoint directory trees. The nfsv2 and nfsv3 filesystems provides no
+way to find the common root of all directory trees exported form the
+server with the same filesystem identifier.
+
+The practical result is that in struct super s_root for nfs s_root is
+not necessarily the root of the filesystem. The nfs mount code sets
+s_root to the root of the first subset of the nfs filesystem that the
+kernel mounts.
+
+This effects the dcache invalidation code in generic_shutdown_super
+currently called shrunk_dcache_for_umount and that code for years
+has gone through an additional list of dentries that might be dentry
+trees that need to be freed to accomodate nfs.
+
+When I wrote path_connected I did not realize nfs was so special, and
+it's hueristic for avoiding calling is_subdir can fail.
+
+The practical case where this fails is when there is a move of a
+directory from the subtree exposed by one nfs mount to the subtree
+exposed by another nfs mount. This move can happen either locally or
+remotely. With the remote case requiring that the move directory be cached
+before the move and that after the move someone walks the path
+to where the move directory now exists and in so doing causes the
+already cached directory to be moved in the dcache through the magic
+of d_splice_alias.
+
+If someone whose working directory is in the move directory or a
+subdirectory and now starts calling .. from the initial mount of nfs
+(where s_root == mnt_root), then path_connected as a heuristic will
+not bother with the is_subdir check. As s_root really is not the root
+of the nfs filesystem this heuristic is wrong, and the path may
+actually not be connected and path_connected can fail.
+
+The is_subdir function might be cheap enough that we can call it
+unconditionally. Verifying that will take some benchmarking and
+the result may not be the same on all kernels this fix needs
+to be backported to. So I am avoiding that for now.
+
+Filesystems with snapshots such as nilfs and btrfs do something
+similar. But as the directory tree of the snapshots are disjoint
+from one another and from the main directory tree rename won't move
+things between them and this problem will not occur.
+
+Cc: stable@vger.kernel.org
+Reported-by: Al Viro <viro@ZenIV.linux.org.uk>
+Fixes: 397d425dc26d ("vfs: Test for and handle paths that are unreachable from their mnt_root")
+Signed-off-by: "Eric W. Biederman" <ebiederm@xmission.com>
+Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/namei.c | 5 +++--
+ fs/nfs/super.c | 2 ++
+ include/linux/fs.h | 1 +
+ 3 files changed, 6 insertions(+), 2 deletions(-)
+
+--- a/fs/namei.c
++++ b/fs/namei.c
+@@ -570,9 +570,10 @@ static int __nd_alloc_stack(struct namei
+ static bool path_connected(const struct path *path)
+ {
+ struct vfsmount *mnt = path->mnt;
++ struct super_block *sb = mnt->mnt_sb;
+
+- /* Only bind mounts can have disconnected paths */
+- if (mnt->mnt_root == mnt->mnt_sb->s_root)
++ /* Bind mounts and multi-root filesystems can have disconnected paths */
++ if (!(sb->s_iflags & SB_I_MULTIROOT) && (mnt->mnt_root == sb->s_root))
+ return true;
+
+ return is_subdir(path->dentry, mnt->mnt_root);
+--- a/fs/nfs/super.c
++++ b/fs/nfs/super.c
+@@ -2581,6 +2581,8 @@ struct dentry *nfs_fs_mount_common(struc
+ /* initial superblock/root creation */
+ mount_info->fill_super(s, mount_info);
+ nfs_get_cache_cookie(s, mount_info->parsed, mount_info->cloned);
++ if (!(server->flags & NFS_MOUNT_UNSHARED))
++ s->s_iflags |= SB_I_MULTIROOT;
+ }
+
+ mntroot = nfs_get_root(s, mount_info->mntfh, dev_name);
+--- a/include/linux/fs.h
++++ b/include/linux/fs.h
+@@ -1295,6 +1295,7 @@ struct mm_struct;
+ /* sb->s_iflags */
+ #define SB_I_CGROUPWB 0x00000001 /* cgroup-aware writeback enabled */
+ #define SB_I_NOEXEC 0x00000002 /* Ignore executables on this fs */
++#define SB_I_MULTIROOT 0x00000008 /* Multiple roots to the dentry tree */
+
+ /* Possible states of 'frozen' field */
+ enum {
--- /dev/null
+From 3b821409632ab778d46e807516b457dfa72736ed Mon Sep 17 00:00:00 2001
+From: Al Viro <viro@zeniv.linux.org.uk>
+Date: Fri, 23 Feb 2018 20:47:17 -0500
+Subject: lock_parent() needs to recheck if dentry got __dentry_kill'ed under it
+
+From: Al Viro <viro@zeniv.linux.org.uk>
+
+commit 3b821409632ab778d46e807516b457dfa72736ed upstream.
+
+In case when dentry passed to lock_parent() is protected from freeing only
+by the fact that it's on a shrink list and trylock of parent fails, we
+could get hit by __dentry_kill() (and subsequent dentry_kill(parent))
+between unlocking dentry and locking presumed parent. We need to recheck
+that dentry is alive once we lock both it and parent *and* postpone
+rcu_read_unlock() until after that point. Otherwise we could return
+a pointer to struct dentry that already is rcu-scheduled for freeing, with
+->d_lock held on it; caller's subsequent attempt to unlock it can end
+up with memory corruption.
+
+Cc: stable@vger.kernel.org # 3.12+, counting backports
+Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/dcache.c | 11 ++++++++---
+ 1 file changed, 8 insertions(+), 3 deletions(-)
+
+--- a/fs/dcache.c
++++ b/fs/dcache.c
+@@ -634,11 +634,16 @@ again:
+ spin_unlock(&parent->d_lock);
+ goto again;
+ }
+- rcu_read_unlock();
+- if (parent != dentry)
++ if (parent != dentry) {
+ spin_lock_nested(&dentry->d_lock, DENTRY_D_LOCK_NESTED);
+- else
++ if (unlikely(dentry->d_lockref.count < 0)) {
++ spin_unlock(&parent->d_lock);
++ parent = NULL;
++ }
++ } else {
+ parent = NULL;
++ }
++ rcu_read_unlock();
+ return parent;
+ }
+
--- /dev/null
+From a9e017d5619eb371460c8e516f4684def62bef3a Mon Sep 17 00:00:00 2001
+From: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+Date: Sun, 5 Nov 2017 18:27:57 -0800
+Subject: selftests/x86: Add tests for the STR and SLDT instructions
+
+From: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+
+commit a9e017d5619eb371460c8e516f4684def62bef3a upstream.
+
+The STR and SLDT instructions are not valid when running on virtual-8086
+mode and generate an invalid operand exception. These two instructions are
+protected by the Intel User-Mode Instruction Prevention (UMIP) security
+feature. In protected mode, if UMIP is enabled, these instructions generate
+a general protection fault if called from CPL > 0. Linux traps the general
+protection fault and emulates the instructions sgdt, sidt and smsw; but not
+str and sldt.
+
+These tests are added to verify that the emulation code does not emulate
+these two instructions but the expected invalid operand exception is
+seen.
+
+Tests fallback to exit with INT3 in case emulation does happen.
+
+Signed-off-by: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+Reviewed-by: Thomas Gleixner <tglx@linutronix.de>
+Cc: Andrew Morton <akpm@linux-foundation.org>
+Cc: Andy Lutomirski <luto@kernel.org>
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Borislav Petkov <bp@suse.de>
+Cc: Brian Gerst <brgerst@gmail.com>
+Cc: Chen Yucong <slaoub@gmail.com>
+Cc: Chris Metcalf <cmetcalf@mellanox.com>
+Cc: Dave Hansen <dave.hansen@linux.intel.com>
+Cc: Denys Vlasenko <dvlasenk@redhat.com>
+Cc: Fenghua Yu <fenghua.yu@intel.com>
+Cc: H. Peter Anvin <hpa@zytor.com>
+Cc: Huang Rui <ray.huang@amd.com>
+Cc: Jiri Slaby <jslaby@suse.cz>
+Cc: Jonathan Corbet <corbet@lwn.net>
+Cc: Josh Poimboeuf <jpoimboe@redhat.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Masami Hiramatsu <mhiramat@kernel.org>
+Cc: Michael S. Tsirkin <mst@redhat.com>
+Cc: Paolo Bonzini <pbonzini@redhat.com>
+Cc: Paul Gortmaker <paul.gortmaker@windriver.com>
+Cc: Peter Zijlstra <peterz@infradead.org>
+Cc: Ravi V. Shankar <ravi.v.shankar@intel.com>
+Cc: Shuah Khan <shuah@kernel.org>
+Cc: Tony Luck <tony.luck@intel.com>
+Cc: Vlastimil Babka <vbabka@suse.cz>
+Cc: ricardo.neri@intel.com
+Link: http://lkml.kernel.org/r/1509935277-22138-13-git-send-email-ricardo.neri-calderon@linux.intel.com
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ tools/testing/selftests/x86/entry_from_vm86.c | 18 +++++++++++++++++-
+ 1 file changed, 17 insertions(+), 1 deletion(-)
+
+--- a/tools/testing/selftests/x86/entry_from_vm86.c
++++ b/tools/testing/selftests/x86/entry_from_vm86.c
+@@ -111,6 +111,11 @@ asm (
+ "smsw %ax\n\t"
+ "mov %ax, (2080)\n\t"
+ "int3\n\t"
++ "vmcode_umip_str:\n\t"
++ "str %eax\n\t"
++ "vmcode_umip_sldt:\n\t"
++ "sldt %eax\n\t"
++ "int3\n\t"
+ ".size vmcode, . - vmcode\n\t"
+ "end_vmcode:\n\t"
+ ".code32\n\t"
+@@ -119,7 +124,8 @@ asm (
+
+ extern unsigned char vmcode[], end_vmcode[];
+ extern unsigned char vmcode_bound[], vmcode_sysenter[], vmcode_syscall[],
+- vmcode_sti[], vmcode_int3[], vmcode_int80[], vmcode_umip[];
++ vmcode_sti[], vmcode_int3[], vmcode_int80[], vmcode_umip[],
++ vmcode_umip_str[], vmcode_umip_sldt[];
+
+ /* Returns false if the test was skipped. */
+ static bool do_test(struct vm86plus_struct *v86, unsigned long eip,
+@@ -226,6 +232,16 @@ void do_umip_tests(struct vm86plus_struc
+ printf("[FAIL]\tAll the results of SIDT should be the same.\n");
+ else
+ printf("[PASS]\tAll the results from SIDT are identical.\n");
++
++ sethandler(SIGILL, sighandler, 0);
++ do_test(vm86, vmcode_umip_str - vmcode, VM86_SIGNAL, 0,
++ "STR instruction");
++ clearhandler(SIGILL);
++
++ sethandler(SIGILL, sighandler, 0);
++ do_test(vm86, vmcode_umip_sldt - vmcode, VM86_SIGNAL, 0,
++ "SLDT instruction");
++ clearhandler(SIGILL);
+ }
+
+ int main(void)
--- /dev/null
+From 9390afebe1d3f5a0be18b1afdd0ce09d67cebf9e Mon Sep 17 00:00:00 2001
+From: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+Date: Sun, 5 Nov 2017 18:27:56 -0800
+Subject: selftests/x86: Add tests for User-Mode Instruction Prevention
+
+From: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+
+commit 9390afebe1d3f5a0be18b1afdd0ce09d67cebf9e upstream.
+
+Certain user space programs that run on virtual-8086 mode may utilize
+instructions protected by the User-Mode Instruction Prevention (UMIP)
+security feature present in new Intel processors: SGDT, SIDT and SMSW. In
+such a case, a general protection fault is issued if UMIP is enabled. When
+such a fault happens, the kernel traps it and emulates the results of
+these instructions with dummy values. The purpose of this new
+test is to verify whether the impacted instructions can be executed
+without causing such #GP. If no #GP exceptions occur, we expect to exit
+virtual-8086 mode from INT3.
+
+The instructions protected by UMIP are executed in representative use
+cases:
+
+ a) displacement-only memory addressing
+ b) register-indirect memory addressing
+ c) results stored directly in operands
+
+Unfortunately, it is not possible to check the results against a set of
+expected values because no emulation will occur in systems that do not
+have the UMIP feature. Instead, results are printed for verification. A
+simple verification is done to ensure that results of all tests are
+identical.
+
+Signed-off-by: Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
+Reviewed-by: Thomas Gleixner <tglx@linutronix.de>
+Cc: Andrew Morton <akpm@linux-foundation.org>
+Cc: Andy Lutomirski <luto@kernel.org>
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Borislav Petkov <bp@suse.de>
+Cc: Brian Gerst <brgerst@gmail.com>
+Cc: Chen Yucong <slaoub@gmail.com>
+Cc: Chris Metcalf <cmetcalf@mellanox.com>
+Cc: Dave Hansen <dave.hansen@linux.intel.com>
+Cc: Denys Vlasenko <dvlasenk@redhat.com>
+Cc: Fenghua Yu <fenghua.yu@intel.com>
+Cc: H. Peter Anvin <hpa@zytor.com>
+Cc: Huang Rui <ray.huang@amd.com>
+Cc: Jiri Slaby <jslaby@suse.cz>
+Cc: Jonathan Corbet <corbet@lwn.net>
+Cc: Josh Poimboeuf <jpoimboe@redhat.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Masami Hiramatsu <mhiramat@kernel.org>
+Cc: Michael S. Tsirkin <mst@redhat.com>
+Cc: Paolo Bonzini <pbonzini@redhat.com>
+Cc: Paul Gortmaker <paul.gortmaker@windriver.com>
+Cc: Peter Zijlstra <peterz@infradead.org>
+Cc: Ravi V. Shankar <ravi.v.shankar@intel.com>
+Cc: Shuah Khan <shuah@kernel.org>
+Cc: Tony Luck <tony.luck@intel.com>
+Cc: Vlastimil Babka <vbabka@suse.cz>
+Cc: ricardo.neri@intel.com
+Link: http://lkml.kernel.org/r/1509935277-22138-12-git-send-email-ricardo.neri-calderon@linux.intel.com
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ tools/testing/selftests/x86/entry_from_vm86.c | 73 +++++++++++++++++++++++++-
+ 1 file changed, 72 insertions(+), 1 deletion(-)
+
+--- a/tools/testing/selftests/x86/entry_from_vm86.c
++++ b/tools/testing/selftests/x86/entry_from_vm86.c
+@@ -95,6 +95,22 @@ asm (
+ "int3\n\t"
+ "vmcode_int80:\n\t"
+ "int $0x80\n\t"
++ "vmcode_umip:\n\t"
++ /* addressing via displacements */
++ "smsw (2052)\n\t"
++ "sidt (2054)\n\t"
++ "sgdt (2060)\n\t"
++ /* addressing via registers */
++ "mov $2066, %bx\n\t"
++ "smsw (%bx)\n\t"
++ "mov $2068, %bx\n\t"
++ "sidt (%bx)\n\t"
++ "mov $2074, %bx\n\t"
++ "sgdt (%bx)\n\t"
++ /* register operands, only for smsw */
++ "smsw %ax\n\t"
++ "mov %ax, (2080)\n\t"
++ "int3\n\t"
+ ".size vmcode, . - vmcode\n\t"
+ "end_vmcode:\n\t"
+ ".code32\n\t"
+@@ -103,7 +119,7 @@ asm (
+
+ extern unsigned char vmcode[], end_vmcode[];
+ extern unsigned char vmcode_bound[], vmcode_sysenter[], vmcode_syscall[],
+- vmcode_sti[], vmcode_int3[], vmcode_int80[];
++ vmcode_sti[], vmcode_int3[], vmcode_int80[], vmcode_umip[];
+
+ /* Returns false if the test was skipped. */
+ static bool do_test(struct vm86plus_struct *v86, unsigned long eip,
+@@ -160,6 +176,58 @@ static bool do_test(struct vm86plus_stru
+ return true;
+ }
+
++void do_umip_tests(struct vm86plus_struct *vm86, unsigned char *test_mem)
++{
++ struct table_desc {
++ unsigned short limit;
++ unsigned long base;
++ } __attribute__((packed));
++
++ /* Initialize variables with arbitrary values */
++ struct table_desc gdt1 = { .base = 0x3c3c3c3c, .limit = 0x9999 };
++ struct table_desc gdt2 = { .base = 0x1a1a1a1a, .limit = 0xaeae };
++ struct table_desc idt1 = { .base = 0x7b7b7b7b, .limit = 0xf1f1 };
++ struct table_desc idt2 = { .base = 0x89898989, .limit = 0x1313 };
++ unsigned short msw1 = 0x1414, msw2 = 0x2525, msw3 = 3737;
++
++ /* UMIP -- exit with INT3 unless kernel emulation did not trap #GP */
++ do_test(vm86, vmcode_umip - vmcode, VM86_TRAP, 3, "UMIP tests");
++
++ /* Results from displacement-only addressing */
++ msw1 = *(unsigned short *)(test_mem + 2052);
++ memcpy(&idt1, test_mem + 2054, sizeof(idt1));
++ memcpy(&gdt1, test_mem + 2060, sizeof(gdt1));
++
++ /* Results from register-indirect addressing */
++ msw2 = *(unsigned short *)(test_mem + 2066);
++ memcpy(&idt2, test_mem + 2068, sizeof(idt2));
++ memcpy(&gdt2, test_mem + 2074, sizeof(gdt2));
++
++ /* Results when using register operands */
++ msw3 = *(unsigned short *)(test_mem + 2080);
++
++ printf("[INFO]\tResult from SMSW:[0x%04x]\n", msw1);
++ printf("[INFO]\tResult from SIDT: limit[0x%04x]base[0x%08lx]\n",
++ idt1.limit, idt1.base);
++ printf("[INFO]\tResult from SGDT: limit[0x%04x]base[0x%08lx]\n",
++ gdt1.limit, gdt1.base);
++
++ if (msw1 != msw2 || msw1 != msw3)
++ printf("[FAIL]\tAll the results of SMSW should be the same.\n");
++ else
++ printf("[PASS]\tAll the results from SMSW are identical.\n");
++
++ if (memcmp(&gdt1, &gdt2, sizeof(gdt1)))
++ printf("[FAIL]\tAll the results of SGDT should be the same.\n");
++ else
++ printf("[PASS]\tAll the results from SGDT are identical.\n");
++
++ if (memcmp(&idt1, &idt2, sizeof(idt1)))
++ printf("[FAIL]\tAll the results of SIDT should be the same.\n");
++ else
++ printf("[PASS]\tAll the results from SIDT are identical.\n");
++}
++
+ int main(void)
+ {
+ struct vm86plus_struct v86;
+@@ -218,6 +286,9 @@ int main(void)
+ v86.regs.eax = (unsigned int)-1;
+ do_test(&v86, vmcode_int80 - vmcode, VM86_INTx, 0x80, "int80");
+
++ /* UMIP -- should exit with INTx 0x80 unless UMIP was not disabled */
++ do_umip_tests(&v86, addr);
++
+ /* Execute a null pointer */
+ v86.regs.cs = 0;
+ v86.regs.ss = 0;
--- /dev/null
+From 78393fdde2a456cafa414b171c90f26a3df98b20 Mon Sep 17 00:00:00 2001
+From: Andy Lutomirski <luto@kernel.org>
+Date: Tue, 13 Mar 2018 22:03:11 -0700
+Subject: selftests/x86/entry_from_vm86: Add test cases for POPF
+
+From: Andy Lutomirski <luto@kernel.org>
+
+commit 78393fdde2a456cafa414b171c90f26a3df98b20 upstream.
+
+POPF is currently broken -- add tests to catch the error. This
+results in:
+
+ [RUN] POPF with VIP set and IF clear from vm86 mode
+ [INFO] Exited vm86 mode due to STI
+ [FAIL] Incorrect return reason (started at eip = 0xd, ended at eip = 0xf)
+
+because POPF currently fails to check IF before reporting a pending
+interrupt.
+
+This patch also makes the FAIL message a bit more informative.
+
+Reported-by: Bart Oldeman <bartoldeman@gmail.com>
+Signed-off-by: Andy Lutomirski <luto@kernel.org>
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Brian Gerst <brgerst@gmail.com>
+Cc: Denys Vlasenko <dvlasenk@redhat.com>
+Cc: H. Peter Anvin <hpa@zytor.com>
+Cc: Josh Poimboeuf <jpoimboe@redhat.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Peter Zijlstra <peterz@infradead.org>
+Cc: Stas Sergeev <stsp@list.ru>
+Cc: Thomas Gleixner <tglx@linutronix.de>
+Cc: stable@vger.kernel.org
+Link: http://lkml.kernel.org/r/a16270b5cfe7832d6d00c479d0f871066cbdb52b.1521003603.git.luto@kernel.org
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ tools/testing/selftests/x86/entry_from_vm86.c | 30 +++++++++++++++++++++++---
+ 1 file changed, 27 insertions(+), 3 deletions(-)
+
+--- a/tools/testing/selftests/x86/entry_from_vm86.c
++++ b/tools/testing/selftests/x86/entry_from_vm86.c
+@@ -95,6 +95,10 @@ asm (
+ "int3\n\t"
+ "vmcode_int80:\n\t"
+ "int $0x80\n\t"
++ "vmcode_popf_hlt:\n\t"
++ "push %ax\n\t"
++ "popf\n\t"
++ "hlt\n\t"
+ "vmcode_umip:\n\t"
+ /* addressing via displacements */
+ "smsw (2052)\n\t"
+@@ -124,8 +128,8 @@ asm (
+
+ extern unsigned char vmcode[], end_vmcode[];
+ extern unsigned char vmcode_bound[], vmcode_sysenter[], vmcode_syscall[],
+- vmcode_sti[], vmcode_int3[], vmcode_int80[], vmcode_umip[],
+- vmcode_umip_str[], vmcode_umip_sldt[];
++ vmcode_sti[], vmcode_int3[], vmcode_int80[], vmcode_popf_hlt[],
++ vmcode_umip[], vmcode_umip_str[], vmcode_umip_sldt[];
+
+ /* Returns false if the test was skipped. */
+ static bool do_test(struct vm86plus_struct *v86, unsigned long eip,
+@@ -175,7 +179,7 @@ static bool do_test(struct vm86plus_stru
+ (VM86_TYPE(ret) == rettype && VM86_ARG(ret) == retarg)) {
+ printf("[OK]\tReturned correctly\n");
+ } else {
+- printf("[FAIL]\tIncorrect return reason\n");
++ printf("[FAIL]\tIncorrect return reason (started at eip = 0x%lx, ended at eip = 0x%lx)\n", eip, v86->regs.eip);
+ nerrs++;
+ }
+
+@@ -264,6 +268,9 @@ int main(void)
+ v86.regs.ds = load_addr / 16;
+ v86.regs.es = load_addr / 16;
+
++ /* Use the end of the page as our stack. */
++ v86.regs.esp = 4096;
++
+ assert((v86.regs.cs & 3) == 0); /* Looks like RPL = 0 */
+
+ /* #BR -- should deliver SIG??? */
+@@ -295,6 +302,23 @@ int main(void)
+ v86.regs.eflags &= ~X86_EFLAGS_IF;
+ do_test(&v86, vmcode_sti - vmcode, VM86_STI, 0, "STI with VIP set");
+
++ /* POPF with VIP set but IF clear: should not trap */
++ v86.regs.eflags = X86_EFLAGS_VIP;
++ v86.regs.eax = 0;
++ do_test(&v86, vmcode_popf_hlt - vmcode, VM86_UNKNOWN, 0, "POPF with VIP set and IF clear");
++
++ /* POPF with VIP set and IF set: should trap */
++ v86.regs.eflags = X86_EFLAGS_VIP;
++ v86.regs.eax = X86_EFLAGS_IF;
++ do_test(&v86, vmcode_popf_hlt - vmcode, VM86_STI, 0, "POPF with VIP and IF set");
++
++ /* POPF with VIP clear and IF set: should not trap */
++ v86.regs.eflags = 0;
++ v86.regs.eax = X86_EFLAGS_IF;
++ do_test(&v86, vmcode_popf_hlt - vmcode, VM86_UNKNOWN, 0, "POPF with VIP clear and IF set");
++
++ v86.regs.eflags = 0;
++
+ /* INT3 -- should cause #BP */
+ do_test(&v86, vmcode_int3 - vmcode, VM86_TRAP, 3, "INT3");
+
--- /dev/null
+From 327d53d005ca47b10eae940616ed11c569f75a9b Mon Sep 17 00:00:00 2001
+From: Andy Lutomirski <luto@kernel.org>
+Date: Tue, 13 Mar 2018 22:03:10 -0700
+Subject: selftests/x86/entry_from_vm86: Exit with 1 if we fail
+
+From: Andy Lutomirski <luto@kernel.org>
+
+commit 327d53d005ca47b10eae940616ed11c569f75a9b upstream.
+
+Fix a logic error that caused the test to exit with 0 even if test
+cases failed.
+
+Signed-off-by: Andy Lutomirski <luto@kernel.org>
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Brian Gerst <brgerst@gmail.com>
+Cc: Denys Vlasenko <dvlasenk@redhat.com>
+Cc: H. Peter Anvin <hpa@zytor.com>
+Cc: Josh Poimboeuf <jpoimboe@redhat.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Peter Zijlstra <peterz@infradead.org>
+Cc: Stas Sergeev <stsp@list.ru>
+Cc: Thomas Gleixner <tglx@linutronix.de>
+Cc: bartoldeman@gmail.com
+Cc: stable@vger.kernel.org
+Link: http://lkml.kernel.org/r/b1cc37144038958a469c8f70a5f47a6a5638636a.1521003603.git.luto@kernel.org
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ tools/testing/selftests/x86/entry_from_vm86.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/tools/testing/selftests/x86/entry_from_vm86.c
++++ b/tools/testing/selftests/x86/entry_from_vm86.c
+@@ -231,7 +231,7 @@ int main(void)
+ clearhandler(SIGSEGV);
+
+ /* Make sure nothing explodes if we fork. */
+- if (fork() > 0)
++ if (fork() == 0)
+ return 0;
+
+ return (nerrs == 0 ? 0 : 1);
ipvlan-add-l2-check-for-packets-arriving-via-virtual-devices.patch
rcutorture-configinit-fix-build-directory-error-message.patch
ima-relax-requiring-a-file-signature-for-new-files-with-zero-length.patch
+selftests-x86-entry_from_vm86-exit-with-1-if-we-fail.patch
+selftests-x86-add-tests-for-user-mode-instruction-prevention.patch
+selftests-x86-add-tests-for-the-str-and-sldt-instructions.patch
+selftests-x86-entry_from_vm86-add-test-cases-for-popf.patch
+x86-vm86-32-fix-popf-emulation.patch
+x86-mm-fix-vmalloc_fault-to-use-pxd_large.patch
+alsa-pcm-fix-uaf-in-snd_pcm_oss_get_formats.patch
+alsa-hda-revert-power_save-option-default-value.patch
+alsa-seq-fix-possible-uaf-in-snd_seq_check_queue.patch
+alsa-seq-clear-client-entry-before-deleting-else-at-closing.patch
+drm-amdgpu-dce-don-t-turn-off-dp-sink-when-disconnected.patch
+fs-teach-path_connected-to-handle-nfs-filesystems-with-multiple-roots.patch
+lock_parent-needs-to-recheck-if-dentry-got-__dentry_kill-ed-under-it.patch
+fs-aio-add-explicit-rcu-grace-period-when-freeing-kioctx.patch
+fs-aio-use-rcu-accessors-for-kioctx_table-table.patch
--- /dev/null
+From 18a955219bf7d9008ce480d4451b6b8bf4483a22 Mon Sep 17 00:00:00 2001
+From: Toshi Kani <toshi.kani@hpe.com>
+Date: Tue, 13 Mar 2018 11:03:46 -0600
+Subject: x86/mm: Fix vmalloc_fault to use pXd_large
+
+From: Toshi Kani <toshi.kani@hpe.com>
+
+commit 18a955219bf7d9008ce480d4451b6b8bf4483a22 upstream.
+
+Gratian Crisan reported that vmalloc_fault() crashes when CONFIG_HUGETLBFS
+is not set since the function inadvertently uses pXn_huge(), which always
+return 0 in this case. ioremap() does not depend on CONFIG_HUGETLBFS.
+
+Fix vmalloc_fault() to call pXd_large() instead.
+
+Fixes: f4eafd8bcd52 ("x86/mm: Fix vmalloc_fault() to handle large pages properly")
+Reported-by: Gratian Crisan <gratian.crisan@ni.com>
+Signed-off-by: Toshi Kani <toshi.kani@hpe.com>
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Cc: stable@vger.kernel.org
+Cc: linux-mm@kvack.org
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Andy Lutomirski <luto@kernel.org>
+Link: https://lkml.kernel.org/r/20180313170347.3829-2-toshi.kani@hpe.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/mm/fault.c | 6 +++---
+ 1 file changed, 3 insertions(+), 3 deletions(-)
+
+--- a/arch/x86/mm/fault.c
++++ b/arch/x86/mm/fault.c
+@@ -287,7 +287,7 @@ static noinline int vmalloc_fault(unsign
+ if (!pmd_k)
+ return -1;
+
+- if (pmd_huge(*pmd_k))
++ if (pmd_large(*pmd_k))
+ return 0;
+
+ pte_k = pte_offset_kernel(pmd_k, address);
+@@ -407,7 +407,7 @@ static noinline int vmalloc_fault(unsign
+ if (pud_none(*pud) || pud_pfn(*pud) != pud_pfn(*pud_ref))
+ BUG();
+
+- if (pud_huge(*pud))
++ if (pud_large(*pud))
+ return 0;
+
+ pmd = pmd_offset(pud, address);
+@@ -418,7 +418,7 @@ static noinline int vmalloc_fault(unsign
+ if (pmd_none(*pmd) || pmd_pfn(*pmd) != pmd_pfn(*pmd_ref))
+ BUG();
+
+- if (pmd_huge(*pmd))
++ if (pmd_large(*pmd))
+ return 0;
+
+ pte_ref = pte_offset_kernel(pmd_ref, address);
--- /dev/null
+From b5069782453459f6ec1fdeb495d9901a4545fcb5 Mon Sep 17 00:00:00 2001
+From: Andy Lutomirski <luto@kernel.org>
+Date: Tue, 13 Mar 2018 22:03:12 -0700
+Subject: x86/vm86/32: Fix POPF emulation
+
+From: Andy Lutomirski <luto@kernel.org>
+
+commit b5069782453459f6ec1fdeb495d9901a4545fcb5 upstream.
+
+POPF would trap if VIP was set regardless of whether IF was set. Fix it.
+
+Suggested-by: Stas Sergeev <stsp@list.ru>
+Reported-by: Bart Oldeman <bartoldeman@gmail.com>
+Signed-off-by: Andy Lutomirski <luto@kernel.org>
+Cc: Borislav Petkov <bp@alien8.de>
+Cc: Brian Gerst <brgerst@gmail.com>
+Cc: Denys Vlasenko <dvlasenk@redhat.com>
+Cc: H. Peter Anvin <hpa@zytor.com>
+Cc: Josh Poimboeuf <jpoimboe@redhat.com>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Peter Zijlstra <peterz@infradead.org>
+Cc: Thomas Gleixner <tglx@linutronix.de>
+Cc: stable@vger.kernel.org
+Fixes: 5ed92a8ab71f ("x86/vm86: Use the normal pt_regs area for vm86")
+Link: http://lkml.kernel.org/r/ce95f40556e7b2178b6bc06ee9557827ff94bd28.1521003603.git.luto@kernel.org
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/kernel/vm86_32.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/arch/x86/kernel/vm86_32.c
++++ b/arch/x86/kernel/vm86_32.c
+@@ -715,7 +715,8 @@ void handle_vm86_fault(struct kernel_vm8
+ return;
+
+ check_vip:
+- if (VEFLAGS & X86_EFLAGS_VIP) {
++ if ((VEFLAGS & (X86_EFLAGS_VIP | X86_EFLAGS_VIF)) ==
++ (X86_EFLAGS_VIP | X86_EFLAGS_VIF)) {
+ save_v86_state(regs, VM86_STI);
+ return;
+ }