diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2013-07-02 19:07:52 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2013-07-02 19:07:52 -0400 |
commit | 3e42dee676e8cf5adca817b1518b2e99d1c138ff (patch) | |
tree | 23580fe97d1e452667b507c2aadb99877d0b574c | |
parent | 42daabf62bfa3c00974b43f030dadcf704c0db59 (diff) | |
parent | 88c8004fd3a5fdd2378069de86b90b21110d33a4 (diff) |
Merge branch 'core-locking-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull locking changes from Ingo Molnar:
"Four miscellanous standalone fixes for futexes, rtmutexes and
Kconfig.locks."
* 'core-locking-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
futex: Use freezable blocking call
futex: Take hugepages into account when generating futex_key
rtmutex: Document rt_mutex_adjust_prio_chain()
locking: Fix copy/paste errors of "ARCH_INLINE_*_UNLOCK_BH"
-rw-r--r-- | include/linux/hugetlb.h | 16 | ||||
-rw-r--r-- | kernel/Kconfig.locks | 6 | ||||
-rw-r--r-- | kernel/futex.c | 6 | ||||
-rw-r--r-- | kernel/rtmutex.c | 13 | ||||
-rw-r--r-- | mm/hugetlb.c | 17 |
5 files changed, 53 insertions, 5 deletions
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h index 6b4890fa57e7..feaf0c7fb7d8 100644 --- a/include/linux/hugetlb.h +++ b/include/linux/hugetlb.h | |||
@@ -358,6 +358,17 @@ static inline int hstate_index(struct hstate *h) | |||
358 | return h - hstates; | 358 | return h - hstates; |
359 | } | 359 | } |
360 | 360 | ||
361 | pgoff_t __basepage_index(struct page *page); | ||
362 | |||
363 | /* Return page->index in PAGE_SIZE units */ | ||
364 | static inline pgoff_t basepage_index(struct page *page) | ||
365 | { | ||
366 | if (!PageCompound(page)) | ||
367 | return page->index; | ||
368 | |||
369 | return __basepage_index(page); | ||
370 | } | ||
371 | |||
361 | #else /* CONFIG_HUGETLB_PAGE */ | 372 | #else /* CONFIG_HUGETLB_PAGE */ |
362 | struct hstate {}; | 373 | struct hstate {}; |
363 | #define alloc_huge_page_node(h, nid) NULL | 374 | #define alloc_huge_page_node(h, nid) NULL |
@@ -378,6 +389,11 @@ static inline unsigned int pages_per_huge_page(struct hstate *h) | |||
378 | } | 389 | } |
379 | #define hstate_index_to_shift(index) 0 | 390 | #define hstate_index_to_shift(index) 0 |
380 | #define hstate_index(h) 0 | 391 | #define hstate_index(h) 0 |
392 | |||
393 | static inline pgoff_t basepage_index(struct page *page) | ||
394 | { | ||
395 | return page->index; | ||
396 | } | ||
381 | #endif /* CONFIG_HUGETLB_PAGE */ | 397 | #endif /* CONFIG_HUGETLB_PAGE */ |
382 | 398 | ||
383 | #endif /* _LINUX_HUGETLB_H */ | 399 | #endif /* _LINUX_HUGETLB_H */ |
diff --git a/kernel/Kconfig.locks b/kernel/Kconfig.locks index 44511d100eaa..d2b32ac27a39 100644 --- a/kernel/Kconfig.locks +++ b/kernel/Kconfig.locks | |||
@@ -138,7 +138,7 @@ config INLINE_SPIN_UNLOCK_BH | |||
138 | 138 | ||
139 | config INLINE_SPIN_UNLOCK_IRQ | 139 | config INLINE_SPIN_UNLOCK_IRQ |
140 | def_bool y | 140 | def_bool y |
141 | depends on !PREEMPT || ARCH_INLINE_SPIN_UNLOCK_BH | 141 | depends on !PREEMPT || ARCH_INLINE_SPIN_UNLOCK_IRQ |
142 | 142 | ||
143 | config INLINE_SPIN_UNLOCK_IRQRESTORE | 143 | config INLINE_SPIN_UNLOCK_IRQRESTORE |
144 | def_bool y | 144 | def_bool y |
@@ -175,7 +175,7 @@ config INLINE_READ_UNLOCK_BH | |||
175 | 175 | ||
176 | config INLINE_READ_UNLOCK_IRQ | 176 | config INLINE_READ_UNLOCK_IRQ |
177 | def_bool y | 177 | def_bool y |
178 | depends on !PREEMPT || ARCH_INLINE_READ_UNLOCK_BH | 178 | depends on !PREEMPT || ARCH_INLINE_READ_UNLOCK_IRQ |
179 | 179 | ||
180 | config INLINE_READ_UNLOCK_IRQRESTORE | 180 | config INLINE_READ_UNLOCK_IRQRESTORE |
181 | def_bool y | 181 | def_bool y |
@@ -212,7 +212,7 @@ config INLINE_WRITE_UNLOCK_BH | |||
212 | 212 | ||
213 | config INLINE_WRITE_UNLOCK_IRQ | 213 | config INLINE_WRITE_UNLOCK_IRQ |
214 | def_bool y | 214 | def_bool y |
215 | depends on !PREEMPT || ARCH_INLINE_WRITE_UNLOCK_BH | 215 | depends on !PREEMPT || ARCH_INLINE_WRITE_UNLOCK_IRQ |
216 | 216 | ||
217 | config INLINE_WRITE_UNLOCK_IRQRESTORE | 217 | config INLINE_WRITE_UNLOCK_IRQRESTORE |
218 | def_bool y | 218 | def_bool y |
diff --git a/kernel/futex.c b/kernel/futex.c index b26dcfc02c94..c3a1a55a5214 100644 --- a/kernel/futex.c +++ b/kernel/futex.c | |||
@@ -61,6 +61,8 @@ | |||
61 | #include <linux/nsproxy.h> | 61 | #include <linux/nsproxy.h> |
62 | #include <linux/ptrace.h> | 62 | #include <linux/ptrace.h> |
63 | #include <linux/sched/rt.h> | 63 | #include <linux/sched/rt.h> |
64 | #include <linux/hugetlb.h> | ||
65 | #include <linux/freezer.h> | ||
64 | 66 | ||
65 | #include <asm/futex.h> | 67 | #include <asm/futex.h> |
66 | 68 | ||
@@ -365,7 +367,7 @@ again: | |||
365 | } else { | 367 | } else { |
366 | key->both.offset |= FUT_OFF_INODE; /* inode-based key */ | 368 | key->both.offset |= FUT_OFF_INODE; /* inode-based key */ |
367 | key->shared.inode = page_head->mapping->host; | 369 | key->shared.inode = page_head->mapping->host; |
368 | key->shared.pgoff = page_head->index; | 370 | key->shared.pgoff = basepage_index(page); |
369 | } | 371 | } |
370 | 372 | ||
371 | get_futex_key_refs(key); | 373 | get_futex_key_refs(key); |
@@ -1807,7 +1809,7 @@ static void futex_wait_queue_me(struct futex_hash_bucket *hb, struct futex_q *q, | |||
1807 | * is no timeout, or if it has yet to expire. | 1809 | * is no timeout, or if it has yet to expire. |
1808 | */ | 1810 | */ |
1809 | if (!timeout || timeout->task) | 1811 | if (!timeout || timeout->task) |
1810 | schedule(); | 1812 | freezable_schedule(); |
1811 | } | 1813 | } |
1812 | __set_current_state(TASK_RUNNING); | 1814 | __set_current_state(TASK_RUNNING); |
1813 | } | 1815 | } |
diff --git a/kernel/rtmutex.c b/kernel/rtmutex.c index 1e09308bf2a1..0dd6aec1cb6a 100644 --- a/kernel/rtmutex.c +++ b/kernel/rtmutex.c | |||
@@ -145,6 +145,19 @@ int max_lock_depth = 1024; | |||
145 | /* | 145 | /* |
146 | * Adjust the priority chain. Also used for deadlock detection. | 146 | * Adjust the priority chain. Also used for deadlock detection. |
147 | * Decreases task's usage by one - may thus free the task. | 147 | * Decreases task's usage by one - may thus free the task. |
148 | * | ||
149 | * @task: the task owning the mutex (owner) for which a chain walk is probably | ||
150 | * needed | ||
151 | * @deadlock_detect: do we have to carry out deadlock detection? | ||
152 | * @orig_lock: the mutex (can be NULL if we are walking the chain to recheck | ||
153 | * things for a task that has just got its priority adjusted, and | ||
154 | * is waiting on a mutex) | ||
155 | * @orig_waiter: rt_mutex_waiter struct for the task that has just donated | ||
156 | * its priority to the mutex owner (can be NULL in the case | ||
157 | * depicted above or if the top waiter is gone away and we are | ||
158 | * actually deboosting the owner) | ||
159 | * @top_task: the current top waiter | ||
160 | * | ||
148 | * Returns 0 or -EDEADLK. | 161 | * Returns 0 or -EDEADLK. |
149 | */ | 162 | */ |
150 | static int rt_mutex_adjust_prio_chain(struct task_struct *task, | 163 | static int rt_mutex_adjust_prio_chain(struct task_struct *task, |
diff --git a/mm/hugetlb.c b/mm/hugetlb.c index e2bfbf73a551..5cf99bf8cce2 100644 --- a/mm/hugetlb.c +++ b/mm/hugetlb.c | |||
@@ -690,6 +690,23 @@ int PageHuge(struct page *page) | |||
690 | } | 690 | } |
691 | EXPORT_SYMBOL_GPL(PageHuge); | 691 | EXPORT_SYMBOL_GPL(PageHuge); |
692 | 692 | ||
693 | pgoff_t __basepage_index(struct page *page) | ||
694 | { | ||
695 | struct page *page_head = compound_head(page); | ||
696 | pgoff_t index = page_index(page_head); | ||
697 | unsigned long compound_idx; | ||
698 | |||
699 | if (!PageHuge(page_head)) | ||
700 | return page_index(page); | ||
701 | |||
702 | if (compound_order(page_head) >= MAX_ORDER) | ||
703 | compound_idx = page_to_pfn(page) - page_to_pfn(page_head); | ||
704 | else | ||
705 | compound_idx = page - page_head; | ||
706 | |||
707 | return (index << compound_order(page_head)) + compound_idx; | ||
708 | } | ||
709 | |||
693 | static struct page *alloc_fresh_huge_page_node(struct hstate *h, int nid) | 710 | static struct page *alloc_fresh_huge_page_node(struct hstate *h, int nid) |
694 | { | 711 | { |
695 | struct page *page; | 712 | struct page *page; |