Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > linux.kernel > #1426199 > unrolled thread
| Started by | Byungchul Park <byungchul.park@lge.com> |
|---|---|
| First post | 2016-06-20 07:20 +0200 |
| Last post | 2016-06-20 07:20 +0200 |
| Articles | 3 — 1 participant |
Back to article view | Back to linux.kernel
[PATCH 0/5] Implement bitlock map allocator Byungchul Park <byungchul.park@lge.com> - 2016-06-20 07:20 +0200
[PATCH 4/5] fs/buffer.c: Remove trailing white space Byungchul Park <byungchul.park@lge.com> - 2016-06-20 07:20 +0200
[PATCH 2/5] lockdep: Apply bitlock to bit_spin_lock Byungchul Park <byungchul.park@lge.com> - 2016-06-20 07:20 +0200
| From | Byungchul Park <byungchul.park@lge.com> |
|---|---|
| Date | 2016-06-20 07:20 +0200 |
| Subject | [PATCH 0/5] Implement bitlock map allocator |
| Message-ID | <rLZMR-42g-9@gated-at.bofh.it> |
Currently, bit-based lock e.g. bit_spin_lock cannot use the lock correctness validator using lockdep. However, it would be useful if the validator supports for even bit-based lock as well. Therefore, this patch provides interface for allocation and freeing lockdep_map for bit-based lock so that the bit-based lock can also use the lock correctness validator with the lockdep_map, allocated for each bit address. This patch can be applied to any bit_spin_lock user except slab allocator where I am not sure if using kmalloc is safe. Anyway I chose two example to apply bitlock map allocator, zram and buffer head. And applied it and included it in this patch set. Byungchul Park (5): lockdep: Implement bitlock map allocator lockdep: Apply bitlock to bit_spin_lock lockdep: Apply bit_spin_lock lockdep to zram fs/buffer.c: Remove trailing white space lockdep: Apply bit_spin_lock lockdep to BH_Uptodate_Lock drivers/block/zram/zram_drv.c | 10 +++ fs/buffer.c | 24 +++---- include/linux/bit_spinlock.h | 57 ++++++++++++++-- include/linux/bitlock.h | 20 ++++++ kernel/locking/Makefile | 1 + kernel/locking/bitlock_map.c | 147 ++++++++++++++++++++++++++++++++++++++++++ lib/Kconfig.debug | 10 +++ 7 files changed, 252 insertions(+), 17 deletions(-) create mode 100644 include/linux/bitlock.h create mode 100644 kernel/locking/bitlock_map.c -- 1.9.1
[toc] | [next] | [standalone]
| From | Byungchul Park <byungchul.park@lge.com> |
|---|---|
| Date | 2016-06-20 07:20 +0200 |
| Subject | [PATCH 4/5] fs/buffer.c: Remove trailing white space |
| Message-ID | <rLZMS-42g-43@gated-at.bofh.it> |
| In reply to | #1426199 |
Trailing white space is not accepted in kernel coding style. Remove
them.
Signed-off-by: Byungchul Park <byungchul.park@lge.com>
---
fs/buffer.c | 22 +++++++++++-----------
1 file changed, 11 insertions(+), 11 deletions(-)
diff --git a/fs/buffer.c b/fs/buffer.c
index e1632ab..a75ca74 100644
--- a/fs/buffer.c
+++ b/fs/buffer.c
@@ -439,7 +439,7 @@ EXPORT_SYMBOL(mark_buffer_async_write);
* try_to_free_buffers() will be operating against the *blockdev* mapping
* at the time, not against the S_ISREG file which depends on those buffers.
* So the locking for private_list is via the private_lock in the address_space
- * which backs the buffers. Which is different from the address_space
+ * which backs the buffers. Which is different from the address_space
* against which the buffers are listed. So for a particular address_space,
* mapping->private_lock does *not* protect mapping->private_list! In fact,
* mapping->private_list will always be protected by the backing blockdev's
@@ -713,7 +713,7 @@ EXPORT_SYMBOL(__set_page_dirty_buffers);
* Do this in two main stages: first we copy dirty buffers to a
* temporary inode list, queueing the writes as we go. Then we clean
* up, waiting for those writes to complete.
- *
+ *
* During this second stage, any subsequent updates to the file may end
* up refiling the buffer on the original inode's dirty list again, so
* there is a chance we will end up with a buffer queued for write but
@@ -791,7 +791,7 @@ static int fsync_buffers_list(spinlock_t *lock, struct list_head *list)
brelse(bh);
spin_lock(lock);
}
-
+
spin_unlock(lock);
err2 = osync_buffers_list(lock, list);
if (err)
@@ -901,7 +901,7 @@ no_grow:
/*
* Return failure for non-async IO requests. Async IO requests
* are not allowed to fail, so we have to wait until buffer heads
- * become available. But we don't want tasks sleeping with
+ * become available. But we don't want tasks sleeping with
* partially complete buffers, so all were released above.
*/
if (!retry)
@@ -910,7 +910,7 @@ no_grow:
/* We're _really_ low on memory. Now we just
* wait for old buffer heads to become free due to
* finishing IO. Since this is an async request and
- * the reserve list is empty, we're sure there are
+ * the reserve list is empty, we're sure there are
* async buffer heads in use.
*/
free_more_memory();
@@ -946,7 +946,7 @@ static sector_t blkdev_max_block(struct block_device *bdev, unsigned int size)
/*
* Initialise the state of a blockdev page's buffers.
- */
+ */
static sector_t
init_page_buffers(struct page *page, struct block_device *bdev,
sector_t block, int size)
@@ -1448,7 +1448,7 @@ static bool has_bh_in_lru(int cpu, void *dummy)
{
struct bh_lru *b = per_cpu_ptr(&bh_lrus, cpu);
int i;
-
+
for (i = 0; i < BH_LRU_SIZE; i++) {
if (b->bhs[i])
return 1;
@@ -1952,7 +1952,7 @@ int __block_write_begin(struct page *page, loff_t pos, unsigned len,
if (PageUptodate(page)) {
if (!buffer_uptodate(bh))
set_buffer_uptodate(bh);
- continue;
+ continue;
}
if (!buffer_uptodate(bh) && !buffer_delay(bh) &&
!buffer_unwritten(bh) &&
@@ -2258,7 +2258,7 @@ EXPORT_SYMBOL(block_read_full_page);
/* utility function for filesystems that need to do work on expanding
* truncates. Uses filesystem pagecache writes to allow the filesystem to
- * deal with the hole.
+ * deal with the hole.
*/
int generic_cont_expand_simple(struct inode *inode, loff_t size)
{
@@ -2819,7 +2819,7 @@ int block_truncate_page(struct address_space *mapping,
length = blocksize - length;
iblock = (sector_t)index << (PAGE_CACHE_SHIFT - inode->i_blkbits);
-
+
page = grab_cache_page(mapping, index);
err = -ENOMEM;
if (!page)
@@ -3069,7 +3069,7 @@ EXPORT_SYMBOL(submit_bh);
*
* ll_rw_block sets b_end_io to simple completion handler that marks
* the buffer up-to-date (if appropriate), unlocks the buffer and wakes
- * any waiters.
+ * any waiters.
*
* All of the buffers must be for the same device, and must also be a
* multiple of the current approved size for the device.
--
1.9.1
[toc] | [prev] | [next] | [standalone]
| From | Byungchul Park <byungchul.park@lge.com> |
|---|---|
| Date | 2016-06-20 07:20 +0200 |
| Subject | [PATCH 2/5] lockdep: Apply bitlock to bit_spin_lock |
| Message-ID | <rLZMR-42g-15@gated-at.bofh.it> |
| In reply to | #1426199 |
Currently, bit_spin_lock does not use lockdep_map at all. Of course,
the lock correctness validator is not supported for bit_spin_lock.
This patch makes bit_spin_lock possible to use the validator using
CONFIG_BITLOCK_ALLOC.
Signed-off-by: Byungchul Park <byungchul.park@lge.com>
---
include/linux/bit_spinlock.h | 57 +++++++++++++++++++++++++++++++++++++++-----
1 file changed, 51 insertions(+), 6 deletions(-)
diff --git a/include/linux/bit_spinlock.h b/include/linux/bit_spinlock.h
index 3b5bafc..3f8b013 100644
--- a/include/linux/bit_spinlock.h
+++ b/include/linux/bit_spinlock.h
@@ -6,13 +6,43 @@
#include <linux/atomic.h>
#include <linux/bug.h>
+#ifdef CONFIG_BITLOCK_ALLOC
+#include <linux/bitlock.h>
+#define bit_spin_init(b, a) \
+do { \
+ static struct lock_class_key __key; \
+ bitlock_init(b, a, #b "@" #a, &__key); \
+} while (0)
+
+static inline void bit_spin_free(int bitnum, unsigned long *addr)
+{
+ bitlock_free(bitnum, addr);
+}
+
+static inline void bit_spin_acquire(int bitnum, unsigned long *addr, int try)
+{
+ struct lockdep_map *map = bitlock_get_map(bitnum, addr, BIT_ACQUIRE);
+ if (map)
+ spin_acquire(map, 0, try, _RET_IP_);
+}
+
+static inline void bit_spin_release(int bitnum, unsigned long *addr)
+{
+ struct lockdep_map *map = bitlock_get_map(bitnum, addr, BIT_RELEASE);
+ if (map)
+ spin_release(map, 0, _RET_IP_);
+}
+#else
+static inline void bit_spin_init(int bitnum, unsigned long *addr) {}
+static inline void bit_spin_free(int bitnum, unsigned long *addr) {}
+static inline void bit_spin_acquire(int bitnum, unsigned long *addr, int try) {}
+static inline void bit_spin_release(int bitnum, unsigned long *addr) {}
+#endif
+
/*
- * bit-based spin_lock()
- *
- * Don't use this unless you really need to: spin_lock() and spin_unlock()
- * are significantly faster.
+ * bit-based spin_lock() without lock acquiring
*/
-static inline void bit_spin_lock(int bitnum, unsigned long *addr)
+static inline void do_raw_bit_spin_lock(int bitnum, unsigned long *addr)
{
/*
* Assuming the lock is uncontended, this never enters
@@ -21,7 +51,6 @@ static inline void bit_spin_lock(int bitnum, unsigned long *addr)
* busywait with less bus contention for a good time to
* attempt to acquire the lock bit.
*/
- preempt_disable();
#if defined(CONFIG_SMP) || defined(CONFIG_DEBUG_SPINLOCK)
while (unlikely(test_and_set_bit_lock(bitnum, addr))) {
preempt_enable();
@@ -35,6 +64,19 @@ static inline void bit_spin_lock(int bitnum, unsigned long *addr)
}
/*
+ * bit-based spin_lock()
+ *
+ * Don't use this unless you really need to: spin_lock() and spin_unlock()
+ * are significantly faster.
+ */
+static inline void bit_spin_lock(int bitnum, unsigned long *addr)
+{
+ preempt_disable();
+ bit_spin_acquire(bitnum, addr, 0);
+ do_raw_bit_spin_lock(bitnum, addr);
+}
+
+/*
* Return true if it was acquired
*/
static inline int bit_spin_trylock(int bitnum, unsigned long *addr)
@@ -46,6 +88,7 @@ static inline int bit_spin_trylock(int bitnum, unsigned long *addr)
return 0;
}
#endif
+ bit_spin_acquire(bitnum, addr, 1);
__acquire(bitlock);
return 1;
}
@@ -55,6 +98,7 @@ static inline int bit_spin_trylock(int bitnum, unsigned long *addr)
*/
static inline void bit_spin_unlock(int bitnum, unsigned long *addr)
{
+ bit_spin_release(bitnum, addr);
#ifdef CONFIG_DEBUG_SPINLOCK
BUG_ON(!test_bit(bitnum, addr));
#endif
@@ -72,6 +116,7 @@ static inline void bit_spin_unlock(int bitnum, unsigned long *addr)
*/
static inline void __bit_spin_unlock(int bitnum, unsigned long *addr)
{
+ bit_spin_release(bitnum, addr);
#ifdef CONFIG_DEBUG_SPINLOCK
BUG_ON(!test_bit(bitnum, addr));
#endif
--
1.9.1
[toc] | [prev] | [standalone]
Back to top | Article view | linux.kernel
csiph-web