diff --git a/configure.in b/configure.in index 27c5a59b..8423080e 100644 --- a/configure.in +++ b/configure.in @@ -1467,6 +1467,23 @@ AC_SUBST(QT4_VER) AC_SUBST(QT4_STATIC_MODULES) +HAVE_MALLINFO=no +AC_ARG_ENABLE(mallinfo,AC_HELP_STRING([--enable-mallinfo],[Enable malloc info if available (default: yes)]),[ac_cv_use_mallinfo=$withval],[ac_cv_use_mallinfo=yes]) +if [[ "x$ac_cv_use_mallinfo" != "xno" ]]; then +AC_MSG_CHECKING([for mallinfo in malloc.h]) +AC_TRY_COMPILE([ +#include +],[ +struct mallinfo info = mallinfo(); +return info.keepcost; +], +HAVE_MALLINFO=yes +) +AC_MSG_RESULT([$HAVE_MALLINFO]) +fi +AC_SUBST(HAVE_MALLINFO) + + HAVE_COREDUMPER=no COREDUMPER_INC="" COREDUMPER_LIB="" diff --git a/modules/Makefile.in b/modules/Makefile.in index 450f19dd..cca33954 100644 --- a/modules/Makefile.in +++ b/modules/Makefile.in @@ -175,6 +175,10 @@ ifneq ($(HAVE_ZLIB),no) PROGS := $(PROGS) zlibcompress.yate endif +ifeq (@HAVE_MALLINFO@,yes) +MALLINFO_DEF := -DHAVE_MALLINFO +endif + ifeq (@HAVE_COREDUMPER@,yes) COREDUMP_INC := -DHAVE_COREDUMPER @COREDUMPER_INC@ COREDUMP_LIB := @COREDUMPER_LIB@ @@ -379,7 +383,7 @@ yrtpchan.yate: LOCALLIBS = -L../libs/yrtp -lyatertp openssl.yate: EXTERNFLAGS = $(OPENSSL_INC) openssl.yate: EXTERNLIBS = $(OPENSSL_LIB) -rmanager.yate: EXTERNFLAGS = $(COREDUMP_INC) +rmanager.yate: EXTERNFLAGS = $(COREDUMP_INC) $(MALLINFO_DEF) rmanager.yate: EXTERNLIBS = $(COREDUMP_LIB) qt4/updater.yate: EXTERNFLAGS = $(QT4_INC_NET) diff --git a/modules/rmanager.cpp b/modules/rmanager.cpp index e717507e..4ad02252 100644 --- a/modules/rmanager.cpp +++ b/modules/rmanager.cpp @@ -29,6 +29,15 @@ #include #include +#ifdef NDEBUG +#undef HAVE_MALLINFO +#undef HAVE_COREDUMPER +#endif + +#ifdef HAVE_MALLINFO +#include +#endif + #ifdef HAVE_COREDUMPER #include #endif @@ -111,6 +120,9 @@ static const CommandInfo s_cmdInfo[] = // Admin commands { "debug", "[module] [level|objects|on|off]", s_level, "Show or change debugging level globally or per module" }, +#ifdef HAVE_MALLINFO + { "meminfo", 0, 0, "Displays memory allocation statistics" }, +#endif #ifdef HAVE_COREDUMPER { "coredump", "[filename]", 0, "Dumps memory image of running Yate to a file" }, #endif @@ -1546,6 +1558,25 @@ bool Connection::processLine(const char *line, bool saveLine) str = (m_machine ? "%%=control:fail:" : "Could not control ") + str + "\r\n"; writeStr(str); } +#ifdef HAVE_MALLINFO + else if (str.startSkip("meminfo")) + { + struct mallinfo info = ::mallinfo(); + str = "Memory allocation statistics:"; + str << "\r\n arena = " << info.arena; + str << "\r\n ordblks = " << info.ordblks; + str << "\r\n smblks = " << info.smblks; + str << "\r\n hblks = " << info.hblks; + str << "\r\n hblkhd = " << info.hblkhd; + str << "\r\n usmblks = " << info.usmblks; + str << "\r\n fsmblks = " << info.fsmblks; + str << "\r\n uordblks = " << info.uordblks; + str << "\r\n fordblks = " << info.fordblks; + str << "\r\n keepcost = " << info.keepcost; + str << "\r\n"; + writeStr(str); + } +#endif #ifdef HAVE_COREDUMPER else if (str.startSkip("coredump")) {