Add umem_alloc_aligned() and honor cache_align field for umem caches

Under linux we open block devices with O_DIRECT which means we must
provide aligned memory buffers.  This patch adds the needed umem
interfaces or in the case of caches simply honors alignment provided
at cache creation time.
This commit is contained in:
Ricardo M. Correia 2010-03-10 11:51:43 -08:00 committed by Brian Behlendorf
parent 3670186d0a
commit c557557e4a
1 changed files with 29 additions and 3 deletions

View File

@ -37,6 +37,7 @@
*/ */
#include <stdlib.h> #include <stdlib.h>
#include <stdio.h>
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
@ -82,9 +83,30 @@ umem_alloc(size_t size, int flags)
{ {
void *ptr; void *ptr;
do {
ptr = malloc(size); ptr = malloc(size);
while (ptr == NULL && (flags & UMEM_NOFAIL)) } while (ptr == NULL && (flags & UMEM_NOFAIL));
ptr = malloc(size);
return ptr;
}
static inline void *
umem_alloc_aligned(size_t size, size_t align, int flags)
{
void *ptr;
int rc;
do {
rc = posix_memalign(&ptr, align, size);
} while (rc == ENOMEM && (flags & UMEM_NOFAIL));
if (rc == EINVAL) {
fprintf(stderr, "%s: invalid memory alignment (%zd)\n",
__func__, align);
if (flags & UMEM_NOFAIL)
abort();
return NULL;
}
return ptr; return ptr;
} }
@ -146,7 +168,11 @@ umem_cache_alloc(umem_cache_t *cp, int flags)
{ {
void *ptr; void *ptr;
if (cp->cache_align != 0)
ptr = umem_alloc_aligned(cp->cache_bufsize, cp->cache_align, flags);
else
ptr = umem_alloc(cp->cache_bufsize, flags); ptr = umem_alloc(cp->cache_bufsize, flags);
if (ptr && cp->cache_constructor) if (ptr && cp->cache_constructor)
cp->cache_constructor(ptr, cp->cache_private, UMEM_DEFAULT); cp->cache_constructor(ptr, cp->cache_private, UMEM_DEFAULT);