文档章节

使用php trie_filter扩展,cpu高负载问题排查

布几岛
 布几岛
发布于 2017/09/11 16:22
字数 493
阅读 13
收藏 0
点赞 0
评论 0
PHP

       今天一同事在使用php trie_filter跑脚本,循环匹配关键词,发现cpu利用率达到了99%。通过strace命令跟踪,发现进程在反复的打开读取和关闭.tree文件,定位到trie_filter_load这个方法被反复调用。按正常的情况,这个文件应该会一次读到内存中,在内存中查询匹配关键词。为了证实,我追踪到扩展源码如下:

PHP_FUNCTION(trie_filter_load)
{
    Trie *trie;
    char *path;
    int path_len;

    if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s",
                &path, &path_len) == FAILURE) {
        RETURN_NULL();
    }

    trie = trie_new_from_file(path);
    if (!trie) {
        php_error_docref(NULL TSRMLS_CC, E_WARNING,
                "Unable to load %s", path);
        RETURN_NULL();
    }

    ZEND_REGISTER_RESOURCE(return_value, trie, le_trie_filter);
}

 

trie变量保存的是一个Trie *结构体,还不能保证已读取到内存中,继续打开libdatrie源码,查找到.datrie/trie.c

Trie *
trie_new_from_file (const char *path)
{
    Trie       *trie;
    FILE       *trie_file;

    trie_file = fopen (path, "r");
    if (!trie_file)
        return NULL;

    trie = trie_fread (trie_file);
    fclose (trie_file);
    return trie;
}

粗看之下trie 结构体读取并保存了文件内容,再继续定位trie_fread

Trie *
trie_fread (FILE *file)
{
    Trie       *trie;

    trie = (Trie *) malloc (sizeof (Trie));
    if (!trie)
        return NULL;

    if (NULL == (trie->alpha_map = alpha_map_fread_bin (file)))
        goto exit_trie_created;
    if (NULL == (trie->da   = da_fread (file)))
        goto exit_alpha_map_created;
    if (NULL == (trie->tail = tail_fread (file)))
        goto exit_da_created;

    trie->is_dirty = FALSE;
    return trie;

exit_da_created:
    da_free (trie->da);
exit_alpha_map_created:
    alpha_map_free (trie->alpha_map);
exit_trie_created:
    free (trie);
    return NULL;
}

通过alpha_map_fread_bin方法读取二进制文件到trie->alpha_map

AlphaMap *
alpha_map_fread_bin (FILE *file)
{
    long        save_pos;
    uint32      sig;
    int32       total, i;
    AlphaMap   *alpha_map;

    /* check signature */
    save_pos = ftell (file);
    if (!file_read_int32 (file, (int32 *) &sig) || ALPHAMAP_SIGNATURE != sig)
        goto exit_file_read;

    if (NULL == (alpha_map = alpha_map_new ()))
        goto exit_file_read;

    /* read number of ranges */
    if (!file_read_int32 (file, &total))
        goto exit_map_created;

    /* read character ranges */
    for (i = 0; i < total; i++) {
        int32   b, e;

        if (!file_read_int32 (file, &b) || !file_read_int32 (file, &e))
            goto exit_map_created;
        alpha_map_add_range (alpha_map, b, e);
    }

    return alpha_map;

exit_map_created:
    alpha_map_free (alpha_map);
exit_file_read:
    fseek (file, save_pos, SEEK_SET);
    return NULL;
}

Bool
file_read_int32 (FILE *file, int32 *o_val)
{
    unsigned char   buff[4];

    if (fread (buff, 4, 1, file) == 1) {
        *o_val = (buff[0] << 24) | (buff[1] << 16) |  (buff[2] << 8) | buff[3];
        return TRUE;
    }

    return FALSE;
}

至此已确定trie_filter_load方法在打开tree文件后读取到内存,因此将trie_filter_load的返回值赋给静态变量,就不用反复打开读取关闭tree文件了,修改后跟踪进程恢复正常。

 

 

© 著作权归作者所有

共有 人打赏支持
布几岛
粉丝 6
博文 37
码字总数 10513
作品 0
海淀
高级程序员
服务器性能指标(一)——负载(Load)分析及问题排查

平常的工作中,在衡量服务器的性能时,经常会涉及到几个指标,load、cpu、mem、qps、rt等。每个指标都有其独特的意义,很多时候在线上出现问题时,往往会伴随着某些指标的异常。大部分情况下...

05/20
0
0
Mysql 高负载排查思路

Mysql 高负载排查思路 发现问题 top命令 查看服务器负载,发现 mysql竟然百分之两百的cpu,引起Mysql 负载这么高的原因,估计是索引问题和某些变态SQL语句. 排查思路 1. 确定高负载的类型,top命...

huangzp168
2017/11/13
0
0
用十条命令在一分钟内检查 Linux 服务器性能

如果你的Linux服务器突然负载暴增,告警短信快发爆你的手机,如何在最短时间内找出Linux性能问题所在?来看Netflix性能工程团队的这篇博文,看它们通过十条命令在一分钟内对机器性能问题进行...

oschina
2015/12/19
18.8K
25
查看linux系统性能

概述 通过执行以下命令,可以在1分钟内对系统资源使用情况有个大致的了解。 uptime dmesg | tail vmstat 1 mpstat -P ALL 1 pidstat 1 iostat -xz 1 free -m sar -n DEV 1 sar -n TCP,ETCP 1...

五大三粗
2015/12/18
125
0
CPU 100% 异常排查实践与总结

CPU 100% 异常排查实践与总结 leejun2005的个人页面2018-01-041 阅读 java 1、问题背景 昨天下午突然收到运维邮件报警,显示数据平台服务器cpu利用率达到了98.94%,而且最近一段时间一直持续...

leejun_2005的个人页面
01/04
0
0
如何用十条命令在一分钟内检查 Linux 服务器性能

如果你的Linux服务器突然负载暴增,报警短信快发爆你的手机,如何在最短时间内找出Linux性能问题所在?来看Netflix性能工程团队的这篇博文,看它们通过十条命令在一分钟内对机器性能问题进行...

局长
2016/09/28
4.7K
5
如何用十条命令在一分钟内检查Linux服务器性能

如果你的Linux服务器突然负载暴增,告警短信快发爆你的手机,如何在最短时间内找出Linux性能问题所在?来看Netflix性能工程团队的这篇博文,看它们通过十条命令在一分钟内对机器性能问题进行...

JasonO
2016/03/04
49
0
用十条命令在一分钟内检查Linux服务器性能

如果你的Linux服务器突然负载暴增,告警短信快发爆你的手机,如何在最短时间内找出Linux性能问题所在?来看Netflix性能工程团队的这篇博文,看它们通过十条命令在一分钟内对机器性能问题进行...

摆渡者
2016/01/31
425
1
如何用九条命令在一分钟内检查Linux服务器性能?

一、uptime命令 这个命令可以快速查看机器的负载情况。在Linux系统中,这些数据表示等待CPU资源的进程和阻塞在不可中断IO进程(进程状态为D)的数量。这些数据可以让我们对系统资源使用有一个...

柠檬琉璃H
06/29
0
0
如何用九条命令在一分钟内检查Linux服务器性能?

一、uptime命令 这个命令可以快速查看机器的负载情况。在Linux系统中,这些数据表示等待CPU资源的进程和阻塞在不可中断IO进程(进程状态为D)的数量。这些数据可以让我们对系统资源使用有一个...

马哥教育
2017/11/06
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

istio 请求路由

请求路由 此页面描述了如何在Istio服务网格中的服务之间路由请求。 服务模型和服务版本 如Pilot中所述,Pilot维护特定网格中服务的规范表示。服务的Istio模型独立于它在底层平台(Kubernete...

xiaomin0322
3分钟前
0
0
运行.jar后缀的文件

前提必须安装了jdk,正确配置环境变量。 在dos窗口执行以下命令即可。 java -jar C:\Users\10492\Desktop\turn.jar

haha360
5分钟前
0
0
Java程序员如何做代码压力测试?【JWordPress前台项目实战】

代码 pom.xml文件引入包 <dependency><groupId>com.taobao.stresstester</groupId><artifactId>stresstester</artifactId><version>1.0</version></dependency> 编写测试代码 /**......

迷你芊宝宝
10分钟前
0
0
面试宝典-什么是缓存穿透?

缓存穿透是说收到了一个请求,但是该请求缓存里没有,只能去数据库里查询,然后放进缓存。 这里面有两个风险,一个是同时有好多请求访问同一个数据,然后业务系统把这些请求全发到了数据库;...

suyain
16分钟前
0
0
vue基础知识练习2

一、发送AJAX请求 <div id="demo1"><button @click="send">发送AJAX请求</button><button @click="sendGet">GET方式发送AJAX请求</button><button @click="sendPost">POST方式发送A......

一个yuanbeth
18分钟前
0
0
Xamarin Essentials教程磁力计Magnetometer

Xamarin Essentials教程磁力计Magnetometer 磁力计也叫地磁、磁感器,可用于测试磁场强度和方向。在手持设备中,通过磁力计可以计算设备的左右、前后倾斜角度,广泛应用于手机各种的应用中。...

大学霸
22分钟前
0
0
mesos:Authentication timed out

最近当slave开始慢慢部署异地集群的时候又碰上了这个问题 I0717 10:27:11.695762 28852 slave.cpp:895] New master detected at master@192.168.2.161:5050I0717 10:27:11.695811 28852 sl......

xueyi28
29分钟前
0
0
赋予用户库的读写权限

1、创建用户 CREATE USER 'test'@'%' IDENTIFIED BY '15ht46389012t'; #'%' - 所有情况都能访问;‘localhost’ - 本机才能访问;’192.168.1.2‘ - 指定 ip 才能访问 2、赋予权限 grant al...

xixingzhe
30分钟前
0
0
Spring核心——JSR250与资源控制

JSR-175与元编程 要说明JSR-250先要解释清楚JSR-175,要解释清楚JSR就的先了解JCP是什么。网上资料很多,就不细说了,简单的说JCP(Java Community Process)是管理Java生态(包括J2SE、J2E...

随风溜达的向日葵
31分钟前
3
0
Java面试基础篇——第五篇:类的实例化顺序

类的实例化顺序:包括 1.父类静态数据,构造函数,字段;2.子类静态数据,构造函数,字段等, 当我们new一个对象的时候,类实例化的顺序是怎么样的呢? OK.还是上代码比较实在(我就是个实在...

developlee的潇洒人生
31分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部