Partial implementation of mallinfo(). It still puts zero in all
the fields, but all the plumbing is now there so that m_mallocfree.c
can fill them in.
git-svn-id: svn://svn.valgrind.org/valgrind/trunk@4441 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/coregrind/m_mallocfree.c b/coregrind/m_mallocfree.c
index e21ed62..ae73919 100644
--- a/coregrind/m_mallocfree.c
+++ b/coregrind/m_mallocfree.c
@@ -1204,6 +1204,14 @@
return get_pszB(a, b);
}
+// We cannot return the whole struct as the library function does,
+// because this is called by a client request. So instead we use
+// a pointer to do call by reference.
+void VG_(mallinfo) ( ThreadId tid, struct vg_mallinfo* mi )
+{
+ // Should do better than this...
+ VG_(memset)(mi, 0x0, sizeof(struct vg_mallinfo));
+}
/*------------------------------------------------------------*/
/*--- Services layered on top of malloc/free. ---*/
diff --git a/coregrind/m_replacemalloc/vg_replace_malloc.c b/coregrind/m_replacemalloc/vg_replace_malloc.c
index df5603e..a86b063 100644
--- a/coregrind/m_replacemalloc/vg_replace_malloc.c
+++ b/coregrind/m_replacemalloc/vg_replace_malloc.c
@@ -429,36 +429,18 @@
PANIC(m_libc_dot_so_dot_6, malloc_get_state);
PANIC(m_libc_dot_so_dot_6, malloc_set_state);
-
-/* Yet another ugly hack. Cannot include <malloc.h> because we
- implement functions implemented there with different signatures.
- This struct definition MUST match the system one. */
-
-/* SVID2/XPG mallinfo structure */
-struct mallinfo {
- int arena; /* total space allocated from system */
- int ordblks; /* number of non-inuse chunks */
- int smblks; /* unused -- always zero */
- int hblks; /* number of mmapped regions */
- int hblkhd; /* total space in mmapped regions */
- int usmblks; /* unused -- always zero */
- int fsmblks; /* unused -- always zero */
- int uordblks; /* total allocated space */
- int fordblks; /* total non-inuse space */
- int keepcost; /* top-most, releasable (via malloc_trim) space */
-};
-
+// mi must be static; if it is auto then Memcheck thinks it is
+// uninitialised when used by the caller of this function, because Memcheck
+// doesn't know that the call to mallinfo fills in mi.
#define MALLINFO(soname, fnname) \
\
- struct mallinfo VG_REPLACE_FUNCTION(soname, fnname) ( void ); \
- struct mallinfo VG_REPLACE_FUNCTION(soname, fnname) ( void ) \
+ struct vg_mallinfo VG_REPLACE_FUNCTION(soname, fnname) ( void ); \
+ struct vg_mallinfo VG_REPLACE_FUNCTION(soname, fnname) ( void ) \
{ \
- /* Should really try to return something a bit more meaningful */ \
- UInt i; \
- struct mallinfo mi; \
- UChar* pmi = (UChar*)(&mi); \
- for (i = 0; i < sizeof(mi); i++) \
- pmi[i] = 0; \
+ static struct vg_mallinfo mi; \
+ MALLOC_TRACE("mallinfo()"); \
+ if (!init_done) init(); \
+ (void)VALGRIND_NON_SIMD_CALL1( info.mallinfo, &mi ); \
return mi; \
}
diff --git a/coregrind/m_scheduler/scheduler.c b/coregrind/m_scheduler/scheduler.c
index 4b05036..a941685 100644
--- a/coregrind/m_scheduler/scheduler.c
+++ b/coregrind/m_scheduler/scheduler.c
@@ -1027,6 +1027,7 @@
info->tl___builtin_vec_delete = VG_(tdict).tool___builtin_vec_delete;
info->arena_payload_szB = VG_(arena_payload_szB);
+ info->mallinfo = VG_(mallinfo);
info->clo_trace_malloc = VG_(clo_trace_malloc);
SET_CLREQ_RETVAL( tid, 0 ); /* return value is meaningless */
diff --git a/coregrind/pub_core_mallocfree.h b/coregrind/pub_core_mallocfree.h
index 94dcbc6..5167042 100644
--- a/coregrind/pub_core_mallocfree.h
+++ b/coregrind/pub_core_mallocfree.h
@@ -68,6 +68,21 @@
// greater than 8.
#define VG_MIN_MALLOC_SZB 8
+/* This struct definition MUST match the system one. */
+/* SVID2/XPG mallinfo structure */
+struct vg_mallinfo {
+ int arena; /* total space allocated from system */
+ int ordblks; /* number of non-inuse chunks */
+ int smblks; /* unused -- always zero */
+ int hblks; /* number of mmapped regions */
+ int hblkhd; /* total space in mmapped regions */
+ int usmblks; /* unused -- always zero */
+ int fsmblks; /* unused -- always zero */
+ int uordblks; /* total allocated space */
+ int fordblks; /* total non-inuse space */
+ int keepcost; /* top-most, releasable (via malloc_trim) space */
+};
+
extern void* VG_(arena_malloc) ( ArenaId arena, SizeT nbytes );
extern void VG_(arena_free) ( ArenaId arena, void* ptr );
extern void* VG_(arena_calloc) ( ArenaId arena,
@@ -83,6 +98,8 @@
extern SizeT VG_(arena_payload_szB) ( ThreadId tid, ArenaId aid, void* p );
+extern void VG_(mallinfo) ( ThreadId tid, struct vg_mallinfo* mi );
+
extern void VG_(sanity_check_malloc_all) ( void );
extern void VG_(print_all_arena_stats) ( void );
diff --git a/coregrind/pub_core_replacemalloc.h b/coregrind/pub_core_replacemalloc.h
index e50de51..7f27ce0 100644
--- a/coregrind/pub_core_replacemalloc.h
+++ b/coregrind/pub_core_replacemalloc.h
@@ -51,6 +51,7 @@
void* (*tl_realloc) (ThreadId tid, void* p, SizeT size);
SizeT (*arena_payload_szB) (ThreadId tid, ArenaId aid, void* payload);
+ void (*mallinfo) (ThreadId tid, struct vg_mallinfo* mi);
Bool clo_trace_malloc;
};