summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZdenek Kabelac <zkabelac@redhat.com>2018-01-23 13:36:12 +0100
committerZdenek Kabelac <zkabelac@redhat.com>2018-01-23 13:36:12 +0100
commita1cfef9f26a47bf414240b8c87865caf6ac15092 (patch)
treef03969cd745d796587ff838f50ab10f713a5c81b
parent102926ed9fb231fbe54d020dcc5873bf97c09e51 (diff)
downloadlvm2-a1cfef9f26a47bf414240b8c87865caf6ac15092.tar.gz
dev_io: fix writes for unaligned buffers
Actually the removed code is necessary - since not all writes are getting alligned buffer - older compilers seems to be not able to create 4K aligned buffers on stack - this the aligning code still need to be present for write path.
-rw-r--r--lib/device/dev-io.c17
1 files changed, 14 insertions, 3 deletions
diff --git a/lib/device/dev-io.c b/lib/device/dev-io.c
index c4666122d..3af4236ed 100644
--- a/lib/device/dev-io.c
+++ b/lib/device/dev-io.c
@@ -153,12 +153,10 @@ static int _io(struct device_buffer *devbuf, unsigned ioflags)
return 0;
}
-#ifndef DEBUG_MEM
if (!devbuf->buf && !(devbuf->malloc_address = devbuf->buf = dm_malloc_aligned((size_t) devbuf->where.size, 0))) {
log_error("Bounce buffer malloc failed");
return 0;
}
-#endif
log_debug_io("%s %s(fd %d):%8" PRIu64 " bytes (sync) at %" PRIu64 "%s (for %s)",
devbuf->write ? "Write" : "Read ", dev_name(where->dev), fd,
@@ -316,9 +314,22 @@ static int _aligned_io(struct device_area *where, char *write_buffer,
if (should_write && !buffer_was_widened && !((uintptr_t) write_buffer & mask))
/* Perform the I/O directly. */
devbuf->buf = write_buffer;
- else
+ else if (!should_write)
/* Postpone buffer allocation until we're about to issue the I/O */
devbuf->buf = NULL;
+ else {
+ /* Allocate a bounce buffer with an extra block */
+ if (!(devbuf->malloc_address = devbuf->buf = dm_malloc((size_t) devbuf->where.size + block_size))) {
+ log_error("Bounce buffer malloc failed");
+ return 0;
+ }
+
+ /*
+ * Realign start of bounce buffer (using the extra sector)
+ */
+ if (((uintptr_t) devbuf->buf) & mask)
+ devbuf->buf = (char *) ((((uintptr_t) devbuf->buf) + mask) & ~mask);
+ }
devbuf->write = 0;