summaryrefslogtreecommitdiffstats
path: root/src/interface/linux
diff options
context:
space:
mode:
authorPiotr Jaroszyński2010-07-01 03:47:52 +0200
committerMichael Brown2011-03-27 22:03:05 +0200
commitb604e8a388702df3cd4d3d64cf42dfc361b235c0 (patch)
treed3e581fc9462b3658fb1a2d354794108e85a3086 /src/interface/linux
parent[image] Remove redundant call to basename() (diff)
downloadipxe-b604e8a388702df3cd4d3d64cf42dfc361b235c0.tar.gz
ipxe-b604e8a388702df3cd4d3d64cf42dfc361b235c0.tar.xz
ipxe-b604e8a388702df3cd4d3d64cf42dfc361b235c0.zip
[linux] Make malloc and linux_umalloc valgrindable
Make the allocators used by malloc and linux_umalloc valgrindable. Include valgrind headers in the codebase to avoid a build dependency on valgrind. Signed-off-by: Piotr Jaroszyński <p.jaroszynski@gmail.com> Modified-by: Michael Brown <mcb30@ipxe.org> Signed-off-by: Michael Brown <mcb30@ipxe.org>
Diffstat (limited to 'src/interface/linux')
-rw-r--r--src/interface/linux/linux_umalloc.c34
1 files changed, 31 insertions, 3 deletions
diff --git a/src/interface/linux/linux_umalloc.c b/src/interface/linux/linux_umalloc.c
index 5167d382..aa0052c5 100644
--- a/src/interface/linux/linux_umalloc.c
+++ b/src/interface/linux/linux_umalloc.c
@@ -18,6 +18,8 @@
FILE_LICENCE(GPL2_OR_LATER);
+#include <valgrind/memcheck.h>
+
/** @file
*
* iPXE user memory allocation API for linux
@@ -56,7 +58,9 @@ static void * linux_realloc(void *ptr, size_t size)
/* Check whether we have a valid pointer */
if (ptr != NULL && ptr != NOWHERE) {
mdptr = ptr - SIZE_MD;
+ VALGRIND_MAKE_MEM_DEFINED(mdptr, SIZE_MD);
md = *mdptr;
+ VALGRIND_MAKE_MEM_NOACCESS(mdptr, SIZE_MD);
/* Check for poison in the metadata */
if (md.poison != POISON) {
@@ -78,32 +82,56 @@ static void * linux_realloc(void *ptr, size_t size)
if (mdptr) {
if (linux_munmap(mdptr, md.size))
DBG("linux_realloc munmap failed: %s\n", linux_strerror(linux_errno));
+ VALGRIND_FREELIKE_BLOCK(ptr, sizeof(*mdptr));
}
return NOWHERE;
}
if (ptr) {
- /* ptr is pointing to an already allocated memory, mremap() it with new size */
+ char *vbits = NULL;
+
+ if (RUNNING_ON_VALGRIND > 0)
+ vbits = linux_realloc(NULL, min(size, md.size));
+
+/* prevent an unused variable warning when building w/o valgrind support */
+#ifndef NVALGRIND
+ VALGRIND_GET_VBITS(ptr, vbits, min(size, md.size));
+#endif
+
+ VALGRIND_FREELIKE_BLOCK(ptr, SIZE_MD);
+
mdptr = linux_mremap(mdptr, md.size + SIZE_MD, size + SIZE_MD, MREMAP_MAYMOVE);
if (mdptr == MAP_FAILED) {
DBG("linux_realloc mremap failed: %s\n", linux_strerror(linux_errno));
return NULL;
}
-
ptr = ((void *)mdptr) + SIZE_MD;
+
+ VALGRIND_MALLOCLIKE_BLOCK(ptr, size, SIZE_MD, 0);
+/* prevent an unused variable warning when building w/o valgrind support */
+#ifndef NVALGRIND
+ VALGRIND_SET_VBITS(ptr, vbits, min(size, md.size));
+#endif
+
+ if (RUNNING_ON_VALGRIND > 0)
+ linux_realloc(vbits, 0);
} else {
- /* allocate new memory with mmap() */
mdptr = linux_mmap(NULL, size + SIZE_MD, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
if (mdptr == MAP_FAILED) {
DBG("linux_realloc mmap failed: %s\n", linux_strerror(linux_errno));
return NULL;
}
ptr = ((void *)mdptr) + SIZE_MD;
+ VALGRIND_MALLOCLIKE_BLOCK(ptr, size, SIZE_MD, 0);
}
/* Update the metadata */
+ VALGRIND_MAKE_MEM_DEFINED(mdptr, SIZE_MD);
mdptr->poison = POISON;
mdptr->size = size;
+ VALGRIND_MAKE_MEM_NOACCESS(mdptr, SIZE_MD);
+ // VALGRIND_MALLOCLIKE_BLOCK ignores redzones currently, make our own
+ VALGRIND_MAKE_MEM_NOACCESS(ptr + size, SIZE_MD);
return ptr;
}