} ProfileEnv;
/**
- * @brief A structure of containg profiling data.
+ * @brief A structure of containg profiled elased time data.
* @details This structure contains profiling data while in inference.
*
* @since_tizen 6.0
typedef struct _ProileData {
unsigned int env_idx; /**< An index of v_mProfileEnv vector.*/
std::string function_name; /**< A function name targetd to profile. */
- size_t memory_usage; /**< memory size consumed by a given function. */
unsigned int elapsed_time; /**< A latency to how long time a given function is performed. */
} ProfileData;
+/**
+ * @brief A structure of containg profiled memory usage data.
+ * @details This structure contains profiling data while in inference.
+ *
+ * @since_tizen 6.0
+ */
+typedef struct _MemoryData {
+ long rss; /** A number of physical pages consumed by current process. */
+ long gpu_memory; /** A number of physical pages consumed by GPU device. */
+ // TODO.
+} MemoryData;
+
/**
* @brief A class of representing profiler.
* @details This class interfaces will be called by InferenceEngineCommon class properly.
* @param[in] env_idx A index to v_mProfileEnv vector object.
* @param[in] func_name A function name to be profiled.
*/
- void Stop(const unsigned int type, const char *func_name);
+ void Stop(const unsigned int type, const char *func_name = "Unknown");
/**
* @brief Dump profiled data to console or a given file.
void PushData(ProfileData &data);
struct timespec GetTimeDiff(struct timespec &start, struct timespec &end);
unsigned long ConvertMillisec(const struct timespec &time);
+ void GetMemoryUsage(MemoryData &data);
void DumpToConsole(void);
void DumpToFile(const unsigned int dump_type, std::string filename);
std::vector<ProfileData> v_mProfileData;
std::map<const char *, const void *> m_mDataTable;
std::string mDumpFilename;
+ MemoryData mStartMemoryData;
+ MemoryData mEndMemoryData;
};
} /* Profiler */
} /* InferenceEngineInterface */
#include <fstream>
#include <iostream>
#include <time.h>
+#include <unistd.h>
extern "C" {
namespace Profiler {
// In default, we will use Markdown syntax to print out profile data.
-static const std::string sTitleMarkdown("backend|target devices|model name|Function name|Latency(ms)|Memory Usage(kb)\n--|--|--|--|--|--\n");
+static const std::string sTitleMarkdown("backend|target devices|model name|Function name|Latency(ms)\n--|--|--|--|--\n");
InferenceEngineProfiler::InferenceEngineProfiler()
{
// In default. we will store profile data to dump.txt file.
// If you want to use other file then use SetDumpFilename function to change the filename.
mDumpFilename = "dump.txt";
+
+ mStartMemoryData = {0, };
+ mEndMemoryData = {0, };
}
InferenceEngineProfiler::~InferenceEngineProfiler()
if (iter != m_mDataTable.end()) {
ProfileData *item = (ProfileData *)iter->second;
item->elapsed_time = (item->elapsed_time + data.elapsed_time) >> 1;
- item->memory_usage = (item->memory_usage + data.memory_usage) >> 1;
return;
}
}
return (unsigned long)(time.tv_sec * MILLI_PER_SEC + time.tv_nsec / NANO_PER_MILLI);
}
+void InferenceEngineProfiler::GetMemoryUsage(MemoryData &data)
+{
+ unsigned long resident_set = 0, rss = 0;
+
+ std::string ignore;
+ std::ifstream ifs("/proc/self/stat", std::ios_base::in);
+ ifs >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore
+ >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore >> ignore
+ >> ignore >> ignore >> ignore >> rss;
+
+ resident_set = (rss * getpagesize()) / 1024;
+ data.rss = resident_set;
+
+ // TODO. Collect GPU memory usage specific to board in case of GPU acceleration.
+ //
+ // If current Linux kernel used Linux DMA mapping framework which is a generic solution for GPU memory management
+ // then we can get all memory usage.
+ // On the other hands, GPU driver on some boards may use reserved memory which is hided
+ // from Linux kernel memory subsystem so the memory usage cannot be measured in generic way.
+ // In this case, board specific interface is required.
+}
+
void InferenceEngineProfiler::Start(const unsigned int type)
{
if (IE_PROFILER_MIN >= type && IE_PROFILER_MAX <= type) {
clock_gettime(CLOCK_MONOTONIC, &mStartTime);
break;
case IE_PROFILER_MEMORY:
+ mStartMemoryData = { 0, };
+ GetMemoryUsage(mStartMemoryData);
break;
/* TODO */
}
return;
}
- ProfileData data = { mEnvNum - 1, func_name, 0, 0 };
+ ProfileData data = { mEnvNum - 1, func_name, 0 };
switch (type) {
case IE_PROFILER_LATENCY: {
clock_gettime(CLOCK_MONOTONIC, &mEndTime);
data.elapsed_time = ConvertMillisec(GetTimeDiff(mStartTime, mEndTime));
+ // TODO.
+ PushData(data);
break;
}
case IE_PROFILER_MEMORY:
+ mEndMemoryData = { 0, };
+ GetMemoryUsage(mEndMemoryData);
break;
- /* TODO */
+ /* TODO */
}
-
- PushData(data);
}
void InferenceEngineProfiler::DumpToConsole(void)
ProfileData data = *iter;
ProfileEnv env = v_mProfileEnv[data.env_idx];
std::cout << env.backend_name << "|" << env.target_devices << "|" << env.model_name << "|";
- std::cout << data.function_name << "|" << data.elapsed_time << "|" << "\n";
+ std::cout << data.function_name << "|" << data.elapsed_time << "\n";
}
+
+ std::cout << "***" << "\n";
+ std::cout << "Memory Usage(kb) : " << mEndMemoryData.rss - mStartMemoryData.rss << "\n";
std::cout << "***" << "\n";
}
dump_file.write("|", 1);
std::string sElapsedTime(std::to_string(data.elapsed_time));
dump_file.write(sElapsedTime.c_str(), sElapsedTime.length());
- dump_file.write("|", 1);
dump_file.write("\n", 1);
}
+
+ dump_file.write("***\n", 4);
+ std::string sMemoryUsage = std::to_string(mEndMemoryData.rss - mStartMemoryData.rss);
+ dump_file.write(sMemoryUsage.c_str(), sMemoryUsage.length());
+ dump_file.write("\n", 1);
dump_file.write("***\n", 4);
}