首頁 >php教程 >php手册 >一次失败的PHP扩展开发之旅

一次失败的PHP扩展开发之旅

WBOY
WBOY原創
2016-06-06 20:01:41890瀏覽

终于到了组装成型的时刻了,通过 telnet 玩了几把 EchoDemo ,看到一行一行的回显,不禁心情大好。 ?php class EchoDemo { public static function init($server, $conf) { log_debug($server, init in php.\n); return true; } public static function inpu

终于到了组装成型的时刻了,通过telnet玩了几把EchoDemo,看到一行一行的回显,不禁心情大好。

<?php class EchoDemo {
        public static function init($server, $conf) {
            log_debug($server, "init in php.\n");
            return true;
        }   

        public static function input($server, $req, $ext_info = array()) {
            log_debug($server, "input in php.\n");
            return strlen($req);
        }   

        public static function route($server, $req, $ext_info = array()) {
            log_debug($server, "route in php.\n");
            return 1;
        }   

        public static function process($server, $req, $ext_info = array()) {
            log_debug($server, "process in php.\n");
            $ret = sendrecv($req, strlen($req), $rsp, 65535, "127.0.0.1", 2345, 500);
            if ($ret != 0) {
                log_debug($server, "sendrecv fail. ret=$ret");
                return false;
            }   
            log_debug($server, "sendrecv finish. rsp=$rsp");
            return true;
        }   

        public static function fini($server) {
            log_debug($server, "fini in php.\n");
        }   
    }
?>

这里最值得赞叹的就是process函数对于sendrecv扩展调用,这里背后通过协程其实已经实现了一次异步网络交互:既能像同步CGI般书写逻辑代码,又能无痛地享受异步的高并发。

愿望是美好的,现实是残酷的!

我这时突然心血来潮:来压测一把性能吧,看看相比于原生C++代码有多大的性能衰减。单次请求1KB,施以1w/s的压力,压了一会coredump了。

内存泄漏?协程栈溢出?...

期间各种折腾:GDB,修改协程栈大小,Google,咨询PHPer ...

很快到了晚上,该查的都查过了,该问的都问过了,实在没辙了,停下来喝杯茶:“call_user_function可重入么”?想到这一层,相信了解协程本质的兄弟又秒懂了:你妹的,人家实现Zend的时候怎么知道调用线程还会玩协程进行用户态调度啊,这个黑盒里面一切皆有可能啊!全局变量、静态变量 ...

好吧,去掉sendrecv这类基于协程的扩展,重新压测,单worker对于3w/secho还是轻松无压力的。

结局

虽然这次最吸引人的一个Feature最终未能实现,不过我还是很开心,因为再次印证了一个观点:思考往往比蛮干高效百倍,尤其在处理棘手问题时,无头苍蝇般乱闯乱撞往往费力不讨好,此时,如果能够冷静下来,尽力搜集现有知识储备,说不定灵感就来光顾你了。

未来可能的方向:PHP5.5版本引入了yield,感觉如果挖掘出来Zend对于yield的支持细节,说不定有希望和我们的C框架很好的融合,但是总觉得是个填不平的大坑。如果抛开其它因素,也许我还是希望选择Golang一类语言直接享受goroutine的优势吧,哈哈!

附录

PHP扩展开发及内核应用

http://www.walu.cc/phpbook/preface.md

编译PHP扩展的两种方式

http://521-wf.com/archives/227.html

如何使用C++开发PHP扩展(上)

http://521-wf.com/archives/241.html

如何使用C++开发PHP扩展(下)

http://521-wf.com/archives/245.html

Wrapping C++ Classes in a PHP Extension

http://devzone.zend.com/1435/wrapping-c-classes-in-a-php-extension/

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn