【发布时间】:2016-01-13 10:30:39
【问题描述】:
我们在 Apache httpd 模块中使用 Apache Thrift 将来自另一个服务的数据注入到请求中。除了似乎源于 gobject 的一些奇怪的性能问题之外,这很好用。
类型系统和/或第一个对象的初始化通常需要 100ms)。
在child_init-Handler中,调用g_type_init()来初始化类型系统。读取请求时,使用 g_object_new(大约 6)创建对象。
使用gettimeofday 测量对象初始化的时间,以获取用户经过的时间。它看起来像这样:
VhostResult *result = NULL;
struct timeval tv1, tv2;
gettimeofday(&tv1, NULL);
result = g_object_new (TYPE_VHOST_RESULT, NULL);
gettimeofday(&tv2, NULL);
这个问题只分批出现。所有对象初始化都低于 1 毫秒几分钟,然后在同一秒内有大约 10 个请求需要 500 毫秒来创建第一个对象,同时完成。
请注意进程总是在请求之后被销毁,所以它总是是一个新的分叉进程,这意味着没有内存泄漏。
编辑:按照建议,我在墙上时间之外添加了 clock() 的测量值,它报告测量代码块的 0。
编辑 2:我查看了 grafana 数据,了解这些批次的缓慢初始化弹出且 iowait 始终很高的时间。是否会因为 iowait 或 iowait 也在测量内存访问而阻塞进程?
编辑3:用于计时(cpu时间)的代码是
clock_t t = clock();
result = g_object_newv(TYPE_VHOST_RESULT, 0, NULL);
t = clock() - t; // stop
ap_log_error(APLOG_MARK, APLOG_ERR, 0, r->server, "%i %s result init clock %f ms", thepid, r->hostname, ((float)t)/CLOCKS_PER_SEC*1000);
这可能是什么原因?
【问题讨论】:
-
恕我直言,您可能需要改进您的配置文件。
gettimeofday是挂壁时间。因此,如果您的进程在调用gettimeofday之间切换,那么计算的时间将不准确。一个建议是改用clock- 只是为了消除它作为一个因素。 -
@kaylum 但有了时钟我会得到 CPU 时间,而不是调用者/用户经过的时间,对吧?我想为用户测量和改进时间,而不是 CPU 时间。
-
是的,最终目标当然是为用户缩短时间。但是要到达那里,您需要拥有正确的数据。您已经得出结论,
g_object_new有时需要 500 毫秒。但这个结论可能不正确,因此你会在完全错误的地方寻找。这就是为什么您需要 CPU 时间,以便您可以自信地说,是的,这个调用 单独 花费了所有时间。 -
我也使用了clock() (
clock() - t_start / CLOCKS_PER_SECOND),它给了我零。 -
请显示您为
clock尝试的准确和完整代码。首先,您显示的 sn-p 看起来不正确,因为它似乎缺少减法周围的括号。
标签: c performance glib gobject