Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8394a1b7 authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge branch 'akpm' (patches from Andrew)

Merge fixes from Andrew Morton:
 "11 fixes"

* emailed patches from Andrew Morton <akpm@linux-foundation.org>:
  Update maintainers for DRM STI driver
  mm: cma: mark cma_bitmap_maxno() inline in header
  zram: fix pool name truncation
  memory-hotplug: fix wrong edge when hot add a new node
  .mailmap: Andrey Ryabinin has moved
  ipc/sem.c: update/correct memory barriers
  mm/hwpoison: fix panic due to split huge zero page
  ipc,sem: remove uneeded sem_undo_list lock usage in exit_sem()
  ipc,sem: fix use after free on IPC_RMID after a task using same semaphore set exits
  mm/hwpoison: fix fail isolate hugetlbfs page w/ refcount held
  mm/hwpoison: fix page refcount of unknown non LRU page
parents fbd9163f 7f11c476
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@ Aleksey Gorelov <aleksey_gorelov@phoenix.com>
Al Viro <viro@ftp.linux.org.uk>
Al Viro <viro@zenIV.linux.org.uk>
Andreas Herrmann <aherrman@de.ibm.com>
Andrey Ryabinin <ryabinin.a.a@gmail.com> <a.ryabinin@samsung.com>
Andrew Morton <akpm@linux-foundation.org>
Andrew Vasquez <andrew.vasquez@qlogic.com>
Andy Adamson <andros@citi.umich.edu>
+9 −0
Original line number Diff line number Diff line
@@ -3587,6 +3587,15 @@ S: Maintained
F:	drivers/gpu/drm/rockchip/
F:	Documentation/devicetree/bindings/video/rockchip*

DRM DRIVERS FOR STI
M:	Benjamin Gaignard <benjamin.gaignard@linaro.org>
M:	Vincent Abriou <vincent.abriou@st.com>
L:	dri-devel@lists.freedesktop.org
T:	git http://git.linaro.org/people/benjamin.gaignard/kernel.git
S:	Maintained
F:	drivers/gpu/drm/sti
F:	Documentation/devicetree/bindings/gpu/st,stih4xx.txt

DSBR100 USB FM RADIO DRIVER
M:	Alexey Klimov <klimov.linux@gmail.com>
L:	linux-media@vger.kernel.org
+2 −4
Original line number Diff line number Diff line
@@ -496,10 +496,9 @@ static void zram_meta_free(struct zram_meta *meta, u64 disksize)
	kfree(meta);
}

static struct zram_meta *zram_meta_alloc(int device_id, u64 disksize)
static struct zram_meta *zram_meta_alloc(char *pool_name, u64 disksize)
{
	size_t num_pages;
	char pool_name[8];
	struct zram_meta *meta = kmalloc(sizeof(*meta), GFP_KERNEL);

	if (!meta)
@@ -512,7 +511,6 @@ static struct zram_meta *zram_meta_alloc(int device_id, u64 disksize)
		goto out_error;
	}

	snprintf(pool_name, sizeof(pool_name), "zram%d", device_id);
	meta->mem_pool = zs_create_pool(pool_name, GFP_NOIO | __GFP_HIGHMEM);
	if (!meta->mem_pool) {
		pr_err("Error creating memory pool\n");
@@ -1031,7 +1029,7 @@ static ssize_t disksize_store(struct device *dev,
		return -EINVAL;

	disksize = PAGE_ALIGN(disksize);
	meta = zram_meta_alloc(zram->disk->first_minor, disksize);
	meta = zram_meta_alloc(zram->disk->disk_name, disksize);
	if (!meta)
		return -ENOMEM;

+35 −12
Original line number Diff line number Diff line
@@ -252,6 +252,16 @@ static void sem_rcu_free(struct rcu_head *head)
	ipc_rcu_free(head);
}

/*
 * spin_unlock_wait() and !spin_is_locked() are not memory barriers, they
 * are only control barriers.
 * The code must pair with spin_unlock(&sem->lock) or
 * spin_unlock(&sem_perm.lock), thus just the control barrier is insufficient.
 *
 * smp_rmb() is sufficient, as writes cannot pass the control barrier.
 */
#define ipc_smp_acquire__after_spin_is_unlocked()	smp_rmb()

/*
 * Wait until all currently ongoing simple ops have completed.
 * Caller must own sem_perm.lock.
@@ -275,6 +285,7 @@ static void sem_wait_array(struct sem_array *sma)
		sem = sma->sem_base + i;
		spin_unlock_wait(&sem->lock);
	}
	ipc_smp_acquire__after_spin_is_unlocked();
}

/*
@@ -327,13 +338,12 @@ static inline int sem_lock(struct sem_array *sma, struct sembuf *sops,
		/* Then check that the global lock is free */
		if (!spin_is_locked(&sma->sem_perm.lock)) {
			/*
			 * The ipc object lock check must be visible on all
			 * cores before rechecking the complex count.  Otherwise
			 * we can race with  another thread that does:
			 * We need a memory barrier with acquire semantics,
			 * otherwise we can race with another thread that does:
			 *	complex_count++;
			 *	spin_unlock(sem_perm.lock);
			 */
			smp_rmb();
			ipc_smp_acquire__after_spin_is_unlocked();

			/*
			 * Now repeat the test of complex_count:
@@ -2074,17 +2084,28 @@ void exit_sem(struct task_struct *tsk)
		rcu_read_lock();
		un = list_entry_rcu(ulp->list_proc.next,
				    struct sem_undo, list_proc);
		if (&un->list_proc == &ulp->list_proc)
			semid = -1;
		 else
		if (&un->list_proc == &ulp->list_proc) {
			/*
			 * We must wait for freeary() before freeing this ulp,
			 * in case we raced with last sem_undo. There is a small
			 * possibility where we exit while freeary() didn't
			 * finish unlocking sem_undo_list.
			 */
			spin_unlock_wait(&ulp->lock);
			rcu_read_unlock();
			break;
		}
		spin_lock(&ulp->lock);
		semid = un->semid;
		spin_unlock(&ulp->lock);

		/* exit_sem raced with IPC_RMID, nothing to do */
		if (semid == -1) {
			rcu_read_unlock();
			break;
			continue;
		}

		sma = sem_obtain_object_check(tsk->nsproxy->ipc_ns, un->semid);
		sma = sem_obtain_object_check(tsk->nsproxy->ipc_ns, semid);
		/* exit_sem raced with IPC_RMID, nothing to do */
		if (IS_ERR(sma)) {
			rcu_read_unlock();
@@ -2112,9 +2133,11 @@ void exit_sem(struct task_struct *tsk)
		ipc_assert_locked_object(&sma->sem_perm);
		list_del(&un->list_id);

		spin_lock(&ulp->lock);
		/* we are the last process using this ulp, acquiring ulp->lock
		 * isn't required. Besides that, we are also protected against
		 * IPC_RMID as we hold sma->sem_perm lock now
		 */
		list_del_rcu(&un->list_proc);
		spin_unlock(&ulp->lock);

		/* perform adjustments registered in un */
		for (i = 0; i < sma->sem_nsems; i++) {
+1 −1
Original line number Diff line number Diff line
@@ -16,7 +16,7 @@ struct cma {
extern struct cma cma_areas[MAX_CMA_AREAS];
extern unsigned cma_area_count;

static unsigned long cma_bitmap_maxno(struct cma *cma)
static inline unsigned long cma_bitmap_maxno(struct cma *cma)
{
	return cma->count >> cma->order_per_bit;
}
Loading