# 风雪之隅 > 风雪之隅 是惠新宸(Laruence)的个人技术博客. 惠新宸是 PHP 核心开发者, PHP 扩展 Yaf、Yar、Tair 的作者, 如视(Realsee)创始人. 内容涵盖 PHP 内核源码分析、PHP 应用开发、PHP 扩展开发、性能优化、C/C++、Linux 及 AI 编程. 自 2007 年持续更新至今, 共 300 余篇原创技术文章, 另附 Yaf 官方中文手册. ## Yaf 手册(技术参考) - [Yaf 中文手册](https://www.laruence.com/manual/): Yaf 框架完整中文文档, 类与方法的 API 参考 ## PHP应用 - [Wechatian: 让AI有事就来微信找你](https://www.laruence.com/2026/08/17/6297.html): Wechatian 是一款 Obsidian 插件,把微信变成 AI Agent 与本地知识库的双向通道:微信发来的文字、图片、文章链接自动剪藏进 vault;Agent 往 outbox 文件夹写文件即可经腾讯 ilink 网关发出微信消息。无第三方中转,任何会写文件的程序都能发微信。 - [用DeepSeek V4 Pro改进Yaconf:快是真快,但它把我代码搞丢了](https://www.laruence.com/2026/08/14/6343.html): yaconf 1.2.0 新增子目录支持(最深16层)与仿照 opcache 的两阶段 compact 存储:配置数据紧凑存于一块连续内存并去重相同字符串,实测随机访问提速40%、内存降低16%。全程由 DeepSeek V4 Pro 编码,速度快但上下文压缩后易失忆、稳定性存疑。 - [Taint支持PHP8啦!](https://www.laruence.com/2026/08/07/6340.html): Taint是检测XSS/SQL注入的PHP扩展,通过GC_FLAGS标记并劫持Opcode传递污点。因PHP8引入JIT且无空闲bit而停更,现由Qwen-3.8-Max完成PHP8适配,耗时5小时、消耗2亿Token,验证了AI可胜任复杂工程执行。 - [PHP8.0的Named Parameter](https://www.laruence.com/2022/05/10/6192.html): 解决 Yar_Concurrent_Client::call 并行 RPC 调用时大量 NULL 占位传参的问题:用 argument unpacking(...$arguments)把数组解开按位置传参,配合 PHP8 Named Parameter 命名参数直接跳过可选参数,无需给 Yar 新增 API 或多态。 - [PHP8新特性之match表达式](https://www.laruence.com/2020/07/13/6033.html): match 表达式是 PHP8 引入的新语法:类似 switch 但直接返回值可赋值;采用严格比较 ===,避免 switch 宽松比较陷阱;多个条件可共用一个分支;所有条件都不匹配时抛出 UnhandledMatchError。match 成为保留字,不能再用作类名。 - [PHP 8新特性之JIT简介](https://www.laruence.com/2020/06/27/5963.html): PHP8 的 JIT 实现在 Opcache 中,于 opcode 优化之上结合运行时信息生成机器码,是增强而非替代,仅支持 x86。opcache.jit 由四个数字组成,分别指定 AVX、寄存器分配、触发策略与优化策略,推荐 12x5;bench.php 开启后耗时降低近60%,性能约提升2倍。 - [使用SSE2指令高效实现strtolower](https://www.laruence.com/2020/06/16/5916.html): PHP8 用 SSE2 指令实现 locale 无关的 strtolower:利用 ASCII 中 A-Z 与 a-z 连续编码且相差32,通过 SIMD 比较指令并行判断大写字母并加32转小写,一次处理16字节,替代旧版256项码表逐字符处理。选 SSE2 而非 SSE4/AVX 是因 CPU 兼容性更广。 - [PHP 8新特性之Attributes(注解)](https://www.laruence.com/2020/06/12/5902.html): PHP8 引入 Attributes(注解) 特性,用 #[...] 语法取代 doc_comment 注释解析,通过 Reflection 的 getAttributes 以结构化方式读取注解名与参数,支持定义注解类。 - [Yaf 3.2 发布](https://www.laruence.com/2020/04/18/5832.html): Yaf 3.2.0 beta 发布,将 Yaf 对象重构为自定义 C 结构体,按偏移量直接访问属性提升性能;新增部分 PSR-4 autoloading 支持,cachegrind 实测性能明显提升。 - [使用PHP Socket开发Yar TCP服务](https://www.laruence.com/2020/04/01/5726.html): Yar RPC 框架支持 HTTP 与 TCP 两种 Transporter。用 PHP Socket 可实现 Yar TCP Server,解析 Yar 打包协议,可结合 Swoole 构建高性能服务。 - [Yac 2.1 升级说明](https://www.laruence.com/2020/03/25/5657.html): Yac 2.1.0 发布,Lock-free 共享内存 PHP 缓存。用 CAS 原子操作保护 key 读写降低读到错误数据的概率,以 SSE4.2 CRC32-C 指令加速校验;set 可能因冲突重试失败。 - [Yar-2.1 新功能介绍](https://www.laruence.com/2020/03/16/5578.html): Yar-2.1 发布,轻量级支持并行调用的 PHP RPC 框架。YAR_OPT_PERSISTENT 改为基于 PHP 请求生命期的连接保持,RPC 调用后不销毁连接,加速后续调用。 ## 随笔 - [Wechatian: 让AI有事就来微信找你](https://www.laruence.com/2026/08/17/6297.html): Wechatian 是一款 Obsidian 插件,把微信变成 AI Agent 与本地知识库的双向通道:微信发来的文字、图片、文章链接自动剪藏进 vault;Agent 往 outbox 文件夹写文件即可经腾讯 ilink 网关发出微信消息。无第三方中转,任何会写文件的程序都能发微信。 - [用Obsidian+Claudian+Ds搭建个人AI助理](https://www.laruence.com/2026/08/10/6299.html): 用 Obsidian + Claudian + Claude Code + CC Switch 路由 DeepSeek 搭建私人 AI 知识库:Claudian 提供对话窗,Claude Code 做 Agent 引擎,CC Switch 转发请求并记账;AI 行为由 CLAUDE.md 定义,目录分 raw/wiki/assets,数据全部为本地 Markdown,双平台 iCloud 同步。 - [PHP8.0的Named Parameter](https://www.laruence.com/2022/05/10/6192.html): 解决 Yar_Concurrent_Client::call 并行 RPC 调用时大量 NULL 占位传参的问题:用 argument unpacking(...$arguments)把数组解开按位置传参,配合 PHP8 Named Parameter 命名参数直接跳过可选参数,无需给 Yar 新增 API 或多态。 - [关于PHP,关于Realsee](https://www.laruence.com/2022/04/12/6089.html): PHP8.0 JIT 后逐渐减少 PHP 开源投入,全面转向如视(Realsee)创业:自2018年在贝壳带领团队做 VR 看房,实现对2000多万套物理空间三维重建、面积超16亿平方米,延伸出户型图自动生成、AI 设计贝壳未来家与开发者开放平台。 - [PHP8新特性之match表达式](https://www.laruence.com/2020/07/13/6033.html): match 表达式是 PHP8 引入的新语法:类似 switch 但直接返回值可赋值;采用严格比较 ===,避免 switch 宽松比较陷阱;多个条件可共用一个分支;所有条件都不匹配时抛出 UnhandledMatchError。match 成为保留字,不能再用作类名。 - [一个关于if else容易迷惑的问题](https://www.laruence.com/2020/07/09/6015.html): PHP 代码 if($a){...} else label: {...} 会输出 truefalse:在 zend_language_parser.y 中 label 单独规约为一条 statement,其后的语句块并不属于 else 分支。else 后可接任意 statement,elseif 本质是 else 加 if 语句。 - [使用SSE2指令高效实现strtolower](https://www.laruence.com/2020/06/16/5916.html): PHP8 用 SSE2 指令实现 locale 无关的 strtolower:利用 ASCII 中 A-Z 与 a-z 连续编码且相差32,通过 SIMD 比较指令并行判断大写字母并加32转小写,一次处理16字节,替代旧版256项码表逐字符处理。选 SSE2 而非 SSE4/AVX 是因 CPU 兼容性更广。 - [PHP 8新特性之Attributes(注解)](https://www.laruence.com/2020/06/12/5902.html): PHP8 引入 Attributes(注解) 特性,用 #[...] 语法取代 doc_comment 注释解析,通过 Reflection 的 getAttributes 以结构化方式读取注解名与参数,支持定义注解类。 - [使用OSC52实现iTerm2远程pbcopy](https://www.laruence.com/2020/05/21/5880.html): 利用 ANSI escape code 中的 OSC 52 转义序列,可在 iTerm2 中实现远程 SSH 服务器直接写入 Mac 本地剪贴板,替代仅限本机的 pbcopy。 - [Yac 2.1 升级说明](https://www.laruence.com/2020/03/25/5657.html): Yac 2.1.0 发布,Lock-free 共享内存 PHP 缓存。用 CAS 原子操作保护 key 读写降低读到错误数据的概率,以 SSE4.2 CRC32-C 指令加速校验;set 可能因冲突重试失败。 - [Yaf-3.1 10%性能提升版](https://www.laruence.com/2020/03/15/5563.html): Yaf-3.1.0 发布,重构 Yaf_Loader::autoload、重写 Yaf_Route_Static/Rewrite 路由核心、is_localnamespace 改用 Hash 匹配并减少内存分配,QPS 提升约 11%。 - [Yaconf-1.1 40%速度提升版](https://www.laruence.com/2020/03/12/5521.html): Yaconf-1.1.0 发布,高性能 PHP 配置容器,启动时将 INI 配置解析入常驻内存并 zero-copy 读取。重构后获取配置平均耗时降低约 40%。 ## PHP源码分析 - [用DeepSeek V4 Pro改进Yaconf:快是真快,但它把我代码搞丢了](https://www.laruence.com/2026/08/14/6343.html): yaconf 1.2.0 新增子目录支持(最深16层)与仿照 opcache 的两阶段 compact 存储:配置数据紧凑存于一块连续内存并去重相同字符串,实测随机访问提速40%、内存降低16%。全程由 DeepSeek V4 Pro 编码,速度快但上下文压缩后易失忆、稳定性存疑。 - [深入理解PHP7内核之OBJECT](https://www.laruence.com/2020/03/23/5605.html): 深入解析 PHP7 内核 Object 变化:对比 PHP5 的 zend_object 结构(ce、properties、properties_table)与 PHP7 新实现,分析属性存储底层机制。 - [PHP FFI详解 - 一种全新的PHP扩展方式](https://www.laruence.com/2020/03/11/5475.html): PHP 7.4 引入 FFI(Foreign Function Interface) 扩展,可在纯 PHP 中直接调用 C 库函数,无需编写扩展。以调用 libcurl 抓取网页为例对比 FFI 与传统扩展用法。 - [深入理解PHP7内核之FAST_ZPP](https://www.laruence.com/2020/02/27/5213.html): FAST_ZPP是PHP7引入的快速参数解析方式,以ZEND_PARSE_PARAMETERS_START/Z_PARAM_*宏取代zend_parse_parameters。借助编译期常量剪枝与内联消除运行时type_spec解析开销(wordpress基准中约占6%耗时),代价是binary size增大,建议仅用于高频调用且逻辑简单的函数。 - [深入理解PHP7内核之HashTable](https://www.laruence.com/2020/02/25/3182.html): PHP7新HashTable(zend_array)的设计动机与实现:针对PHP5的zval**双指针、Bucket独立分配、链表遍历缓存局部性差等问题重新设计,结构体从72字节降至56字节,数据存于arData连续Bucket数组,并用ZEND_ENDIAN_LOHI_4处理大小端。 - [深入理解PHP7内核之Reference](https://www.laruence.com/2018/04/08/3179.html): PHP7内核中引用(Reference)从标志位变为独立类型IS_REFERENCE,通过zend_reference结构存储引用计数和zval。解析该设计如何解决PHP5中IS_LONG引用无法用标志位表示的问题,以及Change On Write分离机制在PHP7下的优化。 - [深入理解PHP7内核之zval](https://www.laruence.com/2018/04/08/3170.html): PHP7内核zval结构重构详解:对比PHP5的24字节zval(refcount__gc、type、is_ref__gc)设计局限,包括zval_gc_info劫持分配、对象双重引用计数等问题,解析PHPNG项目为何从改写zval结构体开始及其带来的性能提升。 - [让你的PHP7更快之Hugepage](https://www.laruence.com/2015/10/02/3069.html): PHP7 HugePage性能优化指南:HugePageFy PHP TEXT segment特性将PHP执行体挪到大内存页,利用2MB大页减少TLB Cache Miss,在WordPress上稳定提升2%~3% QPS。配置方法:系统分配HugePages后设置opcache.huge_code_pages=1。 - [Curl的毫秒超时的一个"Bug"](https://www.laruence.com/2014/01/21/2939.html): libcurl 在 Linux 用系统 DNS 时靠 SIGALARM 控制解析超时,精度仅到秒,超时小于 1000ms 直接返回错误码 28。解法:设 CURLOPT_NOSIGNAL 绕过,或编译启用 c-ares 做异步 DNS。 - [Yac (Yet Another Cache) - 无锁共享内存Cache](https://www.laruence.com/2013/03/18/2846.html): 好久没有更新blog了, 这一年来的工作确实很忙..... anyway, 今天终于有新东西可以和大家分享. 这个idea来自一个很简单的想法, 以及目前所遇到的一个机会. 首先我们来谈谈这个机会. 在以前, 很多人都会选择使用APC, APC除了提供Opcode Cache以外, 还会提供一套User Data Cache(apc_store/apc_fetch), 所以对于很多有需求使用User Data Cache的同学, 使用A - [PDOStatement::bindParam的一个陷阱](https://www.laruence.com/2012/10/16/2831.html): 废话不多说, 直接看代码: - [Yar - 并行的RPC框架(Concurrent RPC framework)](https://www.laruence.com/2012/09/15/2779.html): Yar(yet another RPC framework, 教主问我为啥都是Ya打头, 呵呵, 因为这样名字好起)是我在3个多月前, 为了解决一个实际的问题, 而开发的一个PHP扩展的, RPC框架, 和现有的RPC框架(xml-rpc, soap)不同, 这是一个轻量级的框架, 支持多种打包协议(msgpack, json, php), 并且最重要的一个特点是, 它是可并行化的.. 考虑如下的场景: 传统的Web应用, 一个进程, ## 转载 - [Yaf 3.2 发布](https://www.laruence.com/2020/04/18/5832.html): Yaf 3.2.0 beta 发布,将 Yaf 对象重构为自定义 C 结构体,按偏移量直接访问属性提升性能;新增部分 PSR-4 autoloading 支持,cachegrind 实测性能明显提升。 - [Yar-2.1 新功能介绍](https://www.laruence.com/2020/03/16/5578.html): Yar-2.1 发布,轻量级支持并行调用的 PHP RPC 框架。YAR_OPT_PERSISTENT 改为基于 PHP 请求生命期的连接保持,RPC 调用后不销毁连接,加速后续调用。 - [PHP的性能演进(从PHP5.0到PHP7.1的性能全评测)](https://www.laruence.com/2016/12/18/3137.html): PHP 5.0到PHP 7.1全版本CPU性能基准测试对比,使用bench.php、micro_bench.php、mandelbrot.php评测各版本。结论:性能飞跃来自大版本升级而非小版本,PHP 7.0是重大突破,PHP 8试验性JIT分支比PHP 5.0快41倍以上。 - [在PHP中使用协程实现多任务调度](https://www.laruence.com/2015/05/28/3038.html): PHP5.5生成器(Generator)与协程(Coroutine)实现协作式多任务调度教程:yield实现任务中断与调度器通信,send()实现双向数据传递,通过Task包装协程函数、任务队列和run()调度器实现协作多任务,区别于抢占式多任务调度。 - [记录一场没有胜利的局部战斗](https://www.laruence.com/2015/05/14/3021.html): Valgrind 报 Invalid free,指向 glibc-2.5 的 __libc_freeres bug,用 --run-libc-freeres=no 规避。空共享库链接 -lm 即可复现,未定位根因,仅得规避方案。 - [PHP的历史](https://www.laruence.com/2012/01/11/2482.html): 了解下PHP的历史, 有助于更加深刻的了解PHP发展到今天的轨迹, 下面的文字都是从» PHP手册中转载过来的. PHP 在过去的几年里走过了漫长的道路。成长为处理 web 的最卓越的语言并非易事。如果对 PHP 如何发展到今天很感兴趣,那么请继续读下去吧。以前的 PHP 发行版可以在 » PHP 博物馆找到。 PHP/FI PHP 继承自一个老的工程,名叫 PHP/FI。PHP/FI 在 1995 年由 Rasmus Lerdorf - [2012年1月全球www网站技术报告](https://www.laruence.com/2012/01/07/2453.html): W3Techs在2012年1月7日, 发出最新的"全球www网站技术报告". 该统计基于对全球Alexa排名前100W的www网站做分析而得出. 统计报告(Usage of server-side programming languages for websites)显示, 相比2011年12月, 使用PHP构建的前100W名中的网站,又增长了约0.1%(30个), PHP占据的份额增长至77.3%, 依旧排名第一. 下图显示了1年来的 - [PHP数组的Hash冲突实例](https://www.laruence.com/2011/12/30/2435.html): 上一篇文章, 我介绍了一个利用Hash冲突(碰撞)来对各种语言(包括,PHP, Java, Ruby等等)实施拒绝服务攻击的可能, 但是没有给出实例, 文章发出后, @Ferrari同学给出了一个另外一篇文章Supercolliding a PHP array, 文章中作者介绍了一种基于PHP的冲突实例, 以及带来的性能恶化对比. 我就借花献佛, 翻译给大家看看. 你知道不知道, 插入65536个经过构造的键值的元素到PHP数组, 会需 - [Yaf的性能对比测试](https://www.laruence.com/2011/11/05/2262.html): 从Yaf诞生以来, 我就没把它与其他框架的性能对比测试放出来, 原因呢, 也很简单, 我懒, 没对比过(只是和原生的PHP做了简单的对比). 最近, 关注Yaf的人越来越多, 今天从访问来源发现了这个页面reddit.com, 继而发现了Eryx朋友, 做的一份性能对比测试, 我就借花谢佛, 转载了过来. 后记(2011-12-02补充), Yaf 2.1做了一些性能优化的升级, 基于Yaf 2.1的性能测试报告可以参见: Yaf 2. - [JsonSerializable接口](https://www.laruence.com/2011/10/10/2204.html): 昨天funlake提醒了我, 应该把一些PHP的新动向传播一下. 恭喜候鸟加入了pdt,有什么新进展别忘了给咱cn phper通报一下呀。 那么, 今天为大家介绍一下5.4中对Json做的一个改进. Json是Ajax应用中最为通用的数据传输格式(协议), 主流的编程语言都带有对Json的支持, 在PHP中, 有json_encode/json_decode, 可以很方便的构造Json数据格式. //[1,2,3,4] 也可以Json化 - [和一朋友对话有感](https://www.laruence.com/2011/09/30/2187.html): 朋友: 你知道你的 nginx+php pathinfo的问题的那文章, 我看了多少遍吗? 我: ..... 看了多少遍... 朋友: 从去年这个问题出现,到我写那个运维开发安全的PPT,我看了不少于50遍吧。 我: ..... 你看那么多遍干啥,,,. 朋友:不是看一遍就能读懂的。 我: 是我写的不明白? -_# 汗,,你看吧, 我就说我不能写东西.. 朋友: 不是。 前置知识需求太多。 我: 哦, 呵呵. 那对你有好处啊, 嘿嘿 朋 - [PHP RFC: 让PHP的foreach支持list](https://www.laruence.com/2011/07/13/2110.html): 上个月, 终于算加入了PHP developer team, 一直以来最大的障碍就是语言, 现在想起来, 当年真应该更加认真努力的去学习英语. 得到的第一个任务是: 解决一个feature request, 请求在allow foreach($array as list($a,$b) 大意是说, 希望PHP能支持如下语法: ## Js/CSS - [HTTP 204和205的应用](https://www.laruence.com/2011/01/20/1844.html): 之前和人讨论过这个问题,,, 今天感冒在家休息, 就回忆了一下, 整理如下. 我们很多的应用在使用Ajax的时候, 大多数情况都是询问型操作, 比如提交数据, 则Ajax只是期待服务器返回: {status: 0, message:""} //status 0代表成功, 非零的时候, message中包含出错信息. 我们知道HTTP的状态码, 2xx都是表示成功, 而HTTP的204(No Content)响应, 就表示执行成功, 但是 - [Javascript原型链和原型的一个误区](https://www.laruence.com/2010/05/13/1462.html): 之前我对Javascript的原型链中, 原型继承与标识符查找有些迷惑, 如, 如下的代码: function Foo() {}; var foo = new Foo(); Foo.prototype.label = "laruence"; alert(foo.label); //output: laruence alert(Foo.label);//output: undefined 今天看到了如下这个图: 另外, 在Javascri - [IE下var的重要性的又一佐证](https://www.laruence.com/2010/01/21/1254.html): 一个朋友问了一个js问题, 一段看不出有任何问题的代码, 在ie下报错:"object doesn't support this property or method". function foo(obj) { productTree = obj.toString(); document.getElementById('productTree').innerHTML = productTree; } 开始, 还以为错误是指obj的toS - [关于Javascript的俩个有趣的探讨](https://www.laruence.com/2009/09/27/1123.html): 首先祝贺在经历了几乎一天的等待以后. 我的空间商终于把服务器迁到了电信机房, 外加网通CDN加速. 关于事件处理函数引用的一个佐证 之前, 我在分析Javascript的This关键字的时候, 说过, 当使用inline的方式写dom元素的事件处理函数的时候, 采用的是引用的方式. 刚好nullbyte童鞋给我提供了一个很有意思的Case: alert(document.getElementById("foo").onerror); 在 - [深入理解JavaScript定时机制](https://www.laruence.com/2009/09/23/1089.html): 转帖地址:http://www.9demo.com/archives/341 容易欺骗别人感情的JavaScript定时器 JavaScript的setTimeout与setInterval是两个很容易欺骗别人感情的方法,因为我们开始常常以为调用了就会按既定的方式执行, 我想不少人都深有同感, 例如 setTimeout(function() { alert('你好!'); }, 0); setInterval(callbackFunc - [CSS让你的IE浏览器崩溃(Crash your IE)](https://www.laruence.com/2009/09/14/1081.html): 严格来说不单是CSS就能令IE浏览器崩溃(crash),而要配合相应的XHTML架构。到现时为止发现有两种正常写法及一种错误结构分别导致会IE6、IE7崩溃(crash),至于原因我尝试寻找过答案但至今还没找到…如你有这方面的认识或更详细的资料很希望你能分享! 1 crash IE6 code Demo:http://blog.gulu77.com/demo/200808/crash_ie6.html 此BUG只存在IE6中,当伪类为 - [深入理解Javascript之this关键字](https://www.laruence.com/2009/09/08/1076.html): Javascript是一种很灵活的语言, 而This关键字又是灵活中的灵活, 但是因为它的灵活, 也注定了它的难用. 以前我用this的时候, 都会觉得不踏实, 老是担心它不知道怎么地就会指到另外的什么地方. 其实, 这都是因为, 我们对它的不了解. 刚好最近再给百度学院做《Javascript高级-作用域/原型链》的ppt, 而swit1983网友也刚好提这个问题, 索性就把这部分内容独立总结出来, 与大家分享. 首先, 我先抛出一个 - [纯属娱乐(彩蛋)](https://www.laruence.com/2009/08/31/1072.html): 现在, 请依次按下:"上上下下左右左右BA"~, ;) - [正确使用JS中的正则](https://www.laruence.com/2009/08/09/1036.html): yuchen网友发来一个问题, 大体意思就是在JS中, 同样的正则, 同样的字符串, 循环匹配结果却不一样 , var reTest = /^aid=(.*)/ig; var aData = [ 'aid=^$', 'aid=^$', 'aid=^$', 'aid=^$' ]; for (var i=0, l=aData.length; i - [开心网偷菜外挂](https://www.laruence.com/2009/06/01/905.html): 一个基于greaseMonkey的开心网(kaixin001)偷菜外挂. 这个版本: 1. 修整了一个问题应付最近的开心网调整. 2. 使用OOP重写 如果不知道怎么使用,请google"greaseMonkey". changelog: version 1.0.2:开心网调整了URL, 已经调整相应策略. 2009.06.09 基于Gxd(onmouse.cn)的version 0.0.1重写 // ==UserScript== // - [Javascript作用域原理](https://www.laruence.com/2009/05/28/863.html): 问题的提出 首先看一个例子: var name = 'laruence'; function echo() { alert(name); var name = 'eve'; alert(name); alert(age); } echo(); 运行结果是什么呢? 上面的问题, 我相信会有很多人会认为是: laruence eve [脚本出错] 因为会以为在echo中, 第一次alert的时候, 会取到全局变量name的值, 而第二次值被 - [JS文件装载器(Eve Js Loader)](https://www.laruence.com/2009/05/21/829.html): 最近的项目中,需要对于不同的用户角色分别读取不同的的JS文件簇, 从而避免一次载入全部JS文件, 于是就写了一个简单的JS Loader. 这个loader, 每次载入一个js文件, 在前一个文件完全载入后, 才继续载入下一个文件. Loader提供了俩个事件: onLoad 每当一个单独的js文件被载入完成后, 就会调用这个事件函数. onReady 当全部载入完成后, 会调用OnReady事件处理函数. 一个完整的实例, 看这里: ## PHP Extension - [Wechatian: 让AI有事就来微信找你](https://www.laruence.com/2026/08/17/6297.html): Wechatian 是一款 Obsidian 插件,把微信变成 AI Agent 与本地知识库的双向通道:微信发来的文字、图片、文章链接自动剪藏进 vault;Agent 往 outbox 文件夹写文件即可经腾讯 ilink 网关发出微信消息。无第三方中转,任何会写文件的程序都能发微信。 - [用DeepSeek V4 Pro改进Yaconf:快是真快,但它把我代码搞丢了](https://www.laruence.com/2026/08/14/6343.html): yaconf 1.2.0 新增子目录支持(最深16层)与仿照 opcache 的两阶段 compact 存储:配置数据紧凑存于一块连续内存并去重相同字符串,实测随机访问提速40%、内存降低16%。全程由 DeepSeek V4 Pro 编码,速度快但上下文压缩后易失忆、稳定性存疑。 - [Taint支持PHP8啦!](https://www.laruence.com/2026/08/07/6340.html): Taint是检测XSS/SQL注入的PHP扩展,通过GC_FLAGS标记并劫持Opcode传递污点。因PHP8引入JIT且无空闲bit而停更,现由Qwen-3.8-Max完成PHP8适配,耗时5小时、消耗2亿Token,验证了AI可胜任复杂工程执行。 - [一个小玩意PHP-Valgrind的介绍](https://www.laruence.com/2013/08/14/2899.html): php-valgrind 工具让 PHP 脚本在运行中控制 Valgrind/Callgrind 的 Profile 开关,借助 CALLGRIND_TOGGLE_COLLECT 机制实现按代码段粒度分析,代码开源于 GitHub。 - [Yac (Yet Another Cache) - 无锁共享内存Cache](https://www.laruence.com/2013/03/18/2846.html): 好久没有更新blog了, 这一年来的工作确实很忙..... anyway, 今天终于有新东西可以和大家分享. 这个idea来自一个很简单的想法, 以及目前所遇到的一个机会. 首先我们来谈谈这个机会. 在以前, 很多人都会选择使用APC, APC除了提供Opcode Cache以外, 还会提供一套User Data Cache(apc_store/apc_fetch), 所以对于很多有需求使用User Data Cache的同学, 使用A - [关于PHP的编译和执行分离](https://www.laruence.com/2012/08/16/2701.html): 关于让"PHP的编译和执行分离"这个问题, 一直有人提, 也一直有人尝试. 提的人认为编译执行分离以后, 可以得到性能提升, 可以做代码保护等. 我本身并不是对这个特性很感冒, 因为这里面存在一个投入产出比. 让我来给大家解释一下, 然而不管怎么样, 在最后我会给大家提供一种方案来实现这个功能. 1. PHP的编译并不是很耗时 我之前的文章也介绍过, PHP的编译是线性的编译过程, 不做优化, 所以这个过程非常之快. 而编译和执行分离这 - [Taint-0.3.0(A XSS codes sniffer) released](https://www.laruence.com/2012/02/18/2560.html): 最近几天忙里偷闲, 一直在完善taint, 今天我觉得终于算做到了80%的满意了, 根据80:20原则, 我觉得可以做为一个里程碑的版本了 :). 什么是Taint? An extension used for detecting XSS codes(tainted string), And also can be used to spot sql injection vulnerabilities, shell inject, etc - [PHP Taint - 一个用来检测XSS/SQL/Shell注入漏洞的扩展](https://www.laruence.com/2012/02/14/2544.html): 之前, 小顿和我提过一个想法, 就是从PHP语言层面去分析,找出一些可能的注入漏洞代码. 当时我一来没时间, 而来也确实不知道从何处下手.. 直到上周的时候, 我看到了这个RFC: RFC:Taint. 但是这个RFC的问题在于, 它需要为PHP打Patch, 修改了PHP本身的数据结构, 这对于以后维护, 升级PHP来说, 很不方便, 也会有一些隐患. 虽然这样, 但这个RFC却给了我一个启发, 于是我就完成了这样的一个扩展:Tain - [Yaf 2.1性能测试(Yaf 2.1 Benchmark)](https://www.laruence.com/2011/12/02/2333.html): Thanks to Ruilog agian for his work of second benchmark of Yaf 2.1. Yaf 2.1 (github, manual) did a lot of work to improve performance and reduce memory usage, so let's take a look at the result(Yaf 2.1重写了很多逻辑来提升性能, 并且降低内 - [Plua进入Pecl](https://www.laruence.com/2011/08/04/2131.html): 一个月以前, 我开发了一个php扩展( PLua – Lua for PHP ), 支持在PHP中调用Lua脚本 后续, 发现在pecl中有一个类似的扩展, lua 在和lua的作者johannes, Andreas讨论过以后, 我们一致认为, 应该只保留一个lua扩展. 考虑到Plua的设计更加符合PHP思维习惯, 功能上也比lua要更加丰富, 大家就一致决定把plua作为新的lua标准扩展, 当然plua也会借鉴lua现在的一些优点 - [Yaf已提交到PECL](https://www.laruence.com/2011/06/26/2083.html): 是个值得Yaf纪念的日子.. http://pecl.php.net/package/yaf btw: 终于有了at php.net马甲了, 呵呵 - [PLua - Lua for PHP](https://www.laruence.com/2011/06/19/2047.html): 上周的时候, 搞mysql proxy, 发现要用lua写服务器脚本, 加之以前配置lighttpd的时候, 配置也可以用lua来写, 就想彻底学习和研究下lua. 本着学习Lua的态度, 写了一个PHP扩展Plua, 把Lua解析器嵌入了PHP. Lua的堆栈式传参, 很值得借鉴, 这点上, 感觉比PHP用一个结构体表示弱类型, 要来的更严格, 更可靠一些. 目前可以想到的应用场景, 是可以实现一种编写(Lua), 多处调用(C, P ## Linux/Unix - [Apache Access Log中的Options的含义](https://www.laruence.com/2011/05/05/2002.html): 写博客最怕啥,,,最怕没话题, 没说的, 呵呵 好在公司内的PHP群里,同学众多, 于是又有了今天的这个话题. 说是, 在Apache的Access Log中会看到很多如下的访问日志: 127.0.0.1 - - [05/May/2011:10:54:07 +0800] "OPTIONS * HTTP/1.0" 200 - 127.0.0.1 - - [05/May/2011:10:54:08 +0800] "OPTIONS * HTT - [BTwitter(Twitter In Bash)](https://www.laruence.com/2010/05/24/1526.html): 完成了第一版的bTwitter, 完美支持linux命令行下使用推特. 有几点要说明的: 1. 脚本假设终端是UTF-8的, 如果不是, 请自行iconv之类的. 2. 脚本中in_reply_to, 不知何故, 不能正常在推下方显示, 谁知道为什么? 3. 新浪微薄的API地址,调用很类似, 可以方便的修改以后用到新浪微薄中. 现在支持: Usage: btwitter content 发表Twitter btwitter -l|-- - [shell下发推脚本](https://www.laruence.com/2010/05/24/1515.html): Be Lazy, 懒得能不动鼠标, 就不愿动鼠标.. 今天在推上看到有人的下面缀着"via bash", 好奇怎么做到, 找来推的API, 其实挺简单.. 请参看最新的bTwitter. 直接上代码, 不解释了, 只是有几点解释下 1. 如果是VPN, 不用代理, 就取消-x选项 2. 脚本直接从STDIN读取内容,内容需要是UTF-8编码, 如果你的终端不是, 那请在脚本中添加iconv 3. 做到完全脚本浏览/发推也是可以的. 4. - [Le Putty - Putty with Zmodem](https://www.laruence.com/2010/04/21/1442.html): 一直使用putty(pietty), 因为简单,小巧. 但是, 一直也羡慕SecureCRT支持sz/rs进行file transfer, 很简单,,,很方便... 而小Putty就只能借助ftp或者winscp了.... 今天发现了一个基于Putty的改进版Le Putty(项目地址:http://sourceforge.net/projects/leputty/), 可以完美的支持ZModem进行file transfer. 下载L - [用Vim写Blog](https://www.laruence.com/2010/04/17/1433.html): Vim是一种毒品,一旦你习惯之后就无法离开:),写Blog也是如此。以前用Vim写Blog是依赖Vimperator可以调出Vim进行编辑,不过今天发现了更简便、连游览器都不需要开的方法,那就是Vim的Blog插件:vimpress。vimpress支持获取文章列表并编辑修改文件、新建文章、现场保存,并支持文章分类、标签。 PS:这篇文章就是我使用vimpress直接在gVim中完成的。 需注意的是,vimpress仅支持xlmrpc, - [pkg-config与LD_LIBRARY_PATH](https://www.laruence.com/2010/01/27/1265.html): 最近遇到的几个问题, 都和LD_LIBRARY_PATH有关, 想整理一篇心得, 但发现一片比较好的介绍文章, 就不再赘笔了。 一、编译和连接 一般来说,如果库的头文件不在 /usr/include 目录中,那么在编译的时候需要用 -I 参数指定其路径。由于同一个库在不同系统上可能位于不同的目录下,用户安装库的时候也可以将库安装在不同的目录下,所以即使使用同一个库,由于库的路径的不同,造成了用 -I 参数指定的头文件的路径也可能不同,其 - [automake,autoconf使用详解](https://www.laruence.com/2009/11/18/1154.html): 作为Linux下的程序开发人员,大家一定都遇到过Makefile,用make命令来编译自己写的程序确实是很方便.一般情况下,大家都是手工写一个简单Makefile,如果要想写出一个符合自由软件惯例的Makefile就不那么容易了. 在本文中,将给大家介绍如何使用autoconf和automake两个工具来帮助我们自动地生成符合自由软件惯例的 Makefile,这样就可以象常见的 GNU程序一样,只要使用"./configure","ma - [Nginx(PHP/fastcgi)的PATH_INFO问题](https://www.laruence.com/2009/11/13/1138.html): PATH_INFO是一个CGI 1.1的标准,经常用来做为传参载体. 比如, 我们可以使用PATH_INFO来代替Rewrite来实现伪静态页面, 另外不少PHP框架也使用PATH_INFO来作为路由载体. 在Apache中, 当不加配置的时候, 对于PHP脚本, AcceptPathInfo是默认接受的, 也就是说: 如果在服务器在存在一个/laruence/index.php 那么, 对于如下请求, /laruence/index. - [Linux上配置Nginx+PHP5(FastCGI)](https://www.laruence.com/2009/07/28/1030.html): 原文地址:http://shiningray.cn/linux-shang-pei-zhi-nginx-php5-fastcgi.html Nginx是俄罗斯人编写的十分轻量级的HTTP服务器,以事件驱动的方式编写,所以有非常好的性能,同时也是一个非常高效的反向代理、负载平衡。其拥有匹配Lighttpd的性能,同时还没有Lighttpd的内存泄漏问题,而且Lighttpd的mod_proxy也有一些问题并且很久没有更新。 因此我打算用其 - [phpDocumentor](https://www.laruence.com/2009/04/21/680.html): 最近再总结一些PHP的规范, 想起之前在Y!的时候的API描述自动生成工具, 翻到了phpDocumentor, 用起来感觉还是很方便 , 就安装到使用的过程写下来, 与大家分享 phpDocumentor的安装很简单, 如果通过pear自动安装 在命令行下输入 pear install PhpDocumentor 如果是手动安装 则在http://manual.phpdoc.org/下载最新版本的PhpDocumentor(现在是1. - [PHP5多层继承顺序的bug](https://www.laruence.com/2008/08/24/427.html): 今天guoxiaod提出了一个问题,如下: 会导致fatal error: PHP Fatal error: Class 'b' not found in /home/xinchen/1.php on line 2 Fatal error: Class 'b' not found in /home/xinchen/1.php on line 2 分析这个问题,是运行阶段出错,经过分析PHP的编译,执行过程,得出如下的parsing顺序… - [深入浅出PHP(Exploring PHP)](https://www.laruence.com/2008/08/11/147.html): 一直以来,横观国内的PHP现状,很少有专门介绍PHP内部机制的书。呵呵,我会随时记录下研究的心得,有机会的时候,汇总成书。:) 今天这篇,我内心是想打算做为一个导论: PHP是一个被广泛应用的脚本语言,因为它的成功,所以很多时候,我们应用PHP的时候是更不不需要考虑底层到底是怎么实现的。我相信大多数的PHP程序 员是不会去考虑这一点的。从我接触PHP开始,到今天也就是3年,这三年里,前俩年我一直都是在"用"PHP,每次写出来一段脚本,我 ## GNU C/C++ - [使用SSE2指令高效实现strtolower](https://www.laruence.com/2020/06/16/5916.html): PHP8 用 SSE2 指令实现 locale 无关的 strtolower:利用 ASCII 中 A-Z 与 a-z 连续编码且相差32,通过 SIMD 比较指令并行判断大写字母并加32转小写,一次处理16字节,替代旧版256项码表逐字符处理。选 SSE2 而非 SSE4/AVX 是因 CPU 兼容性更广。 - [使用OSC52实现iTerm2远程pbcopy](https://www.laruence.com/2020/05/21/5880.html): 利用 ANSI escape code 中的 OSC 52 转义序列,可在 iTerm2 中实现远程 SSH 服务器直接写入 Mac 本地剪贴板,替代仅限本机的 pbcopy。 - [使用SSE2指令集加速字符替换](https://www.laruence.com/2020/03/09/5412.html): 用SSE2 SIMD指令集加速字符串字符替换:_mm_cmpeq_epi8一次比较16个字符,结合ASCII差值delta与_mm_add_epi8原地替换目标字符。应用于Yaf_Loader命名空间反斜杠转下划线,字符串超16字节约提速40%-50%,短串无优势。同思路曾用于PHP7的base64_encode/decode优化。 - [GCC优化引起的一个"问题"](https://www.laruence.com/2014/06/26/2955.html): PHP NG 的 zend_string 按偏移仅分配 22 字节,GCC 将 len==1 && val[0]=='0' 优化为一次 8 字节读,越界 3 字节触发 valgrind invalid read 误报,修复为至少分配 24 字节。 - [Weibo LAMP演变 - 6月在上海分享的PPT](https://www.laruence.com/2013/08/15/2913.html): 微博 LAMP 架构优化实践:以提速、降成本、清晰架构、SOA 为方针,改造 Yaf 并推出 Yar RPC 与 Yac 缓存,使微博首页响应时间下降一倍以上并降低成本,依赖工具均已开源。 - [一个小玩意PHP-Valgrind的介绍](https://www.laruence.com/2013/08/14/2899.html): php-valgrind 工具让 PHP 脚本在运行中控制 Valgrind/Callgrind 的 Profile 开关,借助 CALLGRIND_TOGGLE_COLLECT 机制实现按代码段粒度分析,代码开源于 GitHub。 - [关于语言的选择-选易用的](https://www.laruence.com/2012/08/06/2681.html): 首先, 这篇文章不是对@左耳朵耗子的C++的坑真的多吗?一文的反驳, 我只是在我的理解角度说一下我对语言选择的一些感悟. 关于C和C++的争论, 由来已久, 从当年Linus攻击C++是恐怖的语言的时候, 就一直没有停歇, 而就我自己来说, 我对C++的掌握还远远不够, 所以没有能力来从语言设计角度来对比(我在最初, 也尝试学过C++, 用过C++, 但后来发现, 我学不好, 用不好, 就放弃了). 所以我尽量避免在这个方面说错话. 诚 - [浏览器多tab打开同一URL串行化的问题](https://www.laruence.com/2011/07/16/2123.html): 最近同事"神经病"同学的项目中, 发现一个问题. 用firefox打开多个tab, 每个tab都去请求同一个URL(尽量同时), 会发现, 这些请求, 会被浏览器串行化. 也就是说, 浏览器会在第一个页面请求结束以后, 再发起第二个请求, 比如对于如下脚本: - [pkg-config与LD_LIBRARY_PATH](https://www.laruence.com/2010/01/27/1265.html): 最近遇到的几个问题, 都和LD_LIBRARY_PATH有关, 想整理一篇心得, 但发现一片比较好的介绍文章, 就不再赘笔了。 一、编译和连接 一般来说,如果库的头文件不在 /usr/include 目录中,那么在编译的时候需要用 -I 参数指定其路径。由于同一个库在不同系统上可能位于不同的目录下,用户安装库的时候也可以将库安装在不同的目录下,所以即使使用同一个库,由于库的路径的不同,造成了用 -I 参数指定的头文件的路径也可能不同,其 - [automake,autoconf使用详解](https://www.laruence.com/2009/11/18/1154.html): 作为Linux下的程序开发人员,大家一定都遇到过Makefile,用make命令来编译自己写的程序确实是很方便.一般情况下,大家都是手工写一个简单Makefile,如果要想写出一个符合自由软件惯例的Makefile就不那么容易了. 在本文中,将给大家介绍如何使用autoconf和automake两个工具来帮助我们自动地生成符合自由软件惯例的 Makefile,这样就可以象常见的 GNU程序一样,只要使用"./configure","ma - [关于调用约定(cdecl、fastcall、stcall、thiscall) 的一点知识](https://www.laruence.com/2008/04/01/116.html): 当高级语言函数被编译成机器码时, 有一个问题就必须解决:因为CPU没有办法知道一个函数调用需要多少个、什么样的参数. 即计算机不知道怎么给这个函数传递参数, 传递参数的工作必须由函数调用者和函数本身来协调. 为此, 计算机提供了一种被称为栈的数据结构来支持参数传递. 函数调用时, 调用者依次把参数压栈, 然后调用函数, 函数被调用以后, 在堆栈中取得数据, 并进行计算. 函数计算结束以后, 或者调用者、或者函数本身修改堆栈, 使堆栈恢复 ## 关于作者 - 惠新宸(Laruence), PHP 核心开发者, GitHub: https://github.com/laruence