PHP7 Upgrade Practice for QQ Member Activity Platform (AMS)
The QQ Member Activity Platform upgraded its legacy PHP 5.2/Apache 2.0 stack to PHP 7.0 with Apache 2.4 through staged migrations, extensive extension refactoring, and rigorous debugging, ultimately achieving roughly double the request‑handling performance and significant hardware cost savings while maintaining service stability.
QQ Member Activity Operation Platform (AMS) is an important carrier for QQ Member value-added operations, handling massive activity operations with a Web system built mainly in PHP. The system handles approximately 300 million CGI requests daily, peaking at 800 million. Previously, AMS used outdated software versions: PHP 5.2 + Apache 2.0 (2008 technology). With rapid business growth, performance pressure increased significantly.
Starting from May 2015, the team planned the PHP底层 upgrade, ultimately targeting PHP7. At that time, PHP7 was still in development, and research and discussion began early.
PHP7 Learning and Pre-research
1. HHVM and JIT
In 2015, HHVM (HipHop Virtual Machine), an open-source PHP virtual machine from Facebook, was an important option for PHP performance optimization. HHVM uses JIT (Just In Time) compilation and other technologies to significantly improve PHP code execution performance, reportedly achieving 5-10x performance improvement over PHP5.
HHVM originated from Facebook, which used PHP extensively in its early days. As business grew, PHP execution efficiency became a bottleneck. In 2008, Facebook started using HipHop, a PHP execution engine originally designed to convert PHP code to C++ for better performance. Later, Facebook open-sourced HipHop, which evolved into HHVM.
At the PHPCon China 2015, the team learned about PHP7 kernel technical sharing from PHP7 kernel developers. In 2013, attempts were made to add JIT to PHP5.5, achieving 8x performance improvement in benchmarks. However, when applied to real projects like WordPress, almost no performance improvement was observed because the generated machine code was too large, causing CPU cache miss.
2. PHP7 Performance Optimizations
PHP7 represents a fundamental upgrade compared to PHP5.6. Performance optimizations include:
Changing basic variables from struct to union, saving memory space and reducing CPU overhead in memory allocation and management.
Using contiguous memory allocation for basic variables (zend_array, zend_string), reducing CPU Cache Miss probability. The efficiency difference between CPU getting data from Cache vs. memory can be as high as 100 times.
Using macro definitions and inline functions to allow the compiler to complete some work in advance, eliminating function call overhead.
Upgrade Challenges and Risks
For a large-scale production Web service, upgrading fundamental software is challenging. The main challenges identified were:
Apache2.0 and PHP5.2 (2008-2009 versions) are very old; upgrading to Apache2.4 and PHP7 spans 7-8 years with significant compatibility challenges.
AMS extensively uses self-developed tphplib extensions, which only had PHP5.3 and PHP5.2 compiled versions and lacked thread safety support.
Syntax compatibility issues: the跨度 from PHP5.2 to PHP7 is large; although PHP claims 99% backward compatibility, the large code base presents unknown risks.
New software risks: upgrading to the latest versions may have unknown defects.
Upgrade Implementation Process
1. High-span Version Upgrade Approach
Directly upgrading from Apache2.0 (2008) to Apache2.4 (2016) was too large a span. The team first upgraded Apache2.0 to Apache2.2, tested compatibility, then proceeded to Apache2.4. Similarly, PHP5.2 was upgraded to PHP5.6 first, then to PHP7.
The upgrade plan became: PHP5.2 + Apache2.0 → PHP5.6 + Apache2.2 → PHP7.0 + Apache2.4
Apache2.4 was compiled as dynamic MPM mode (supporting prefork/worker/event mode switching via httpd configuration), with real-time degradation based on production risks.
2. Debugging Methods During Upgrade
When PHP7 extension execution results don't meet expectations or processes core dump, many errors cannot be seen in error logs. Methods include:
var_dump/exit - Gradually output information from PHP code layer to locate abnormal execution positions.
gdb -p / gdb -c - Mainly used for analyzing process core scenarios, monitoring Apache service processes.
strace -Ttt -v -s1024 -f -p pid - View what Apache processes are specifically doing to analyze and locate problems.
PHP5.6 to PHP7.0 Extension Upgrade Practice
1. Data Type Changes
zval: PHP7 no longer needs pointer-to-pointer; most zval** need to be changed to zval* . If PHP7 directly operates on zval , then zval* also needs to be changed to zval . Macros like ALLOC_ZVAL , ALLOC_INIT_ZVAL , MAKE_STD_ZVAL have been removed.
Integer: Direct switch: long → zend_long
String: PHP5.6 uses char* + len to represent strings, while PHP7.0 defines the zend_string type. Use ZSTR_VAL(str) and ZSTR_LEN(str) to get char* and len; use zend_string_init to create zend_string.
Custom Objects: zend_object is a variable-length structure, so in custom object structures, zend_object must be placed at the last position.
Array: PHP7 uses new hash table implementation with macros like ZEND_Hash_FOREACH_STR_KEY_VAL for traversal.
2. API Changes in PHP7
duplicate parameter: Many APIs in PHP5.6 require a duplicate parameter, especially for string operations. PHP7.0 removes this parameter; for string operations, simply remove the duplicate parameter.
MAKE_STD_ZVAL: In PHP5.6, zval variables are allocated on the heap; creating a zval requires first declaring a pointer, then using MAKE_STD_ZVAL to allocate space. In PHP7.0, this macro is canceled; variables are allocated on the stack.
ZEND_RSRC_DTOR_FUNC: PHP7.0 upgrades zend_rsrc_list_entry structure to zend_resource , requiring only parameter name changes.
PP macros: PHP7.0 cancels all PP macros; in most cases, directly use the corresponding P macros.
zend_object_store_get_object: Cancelled; can define macros using offset to get objects.
zend_hash_exists, zend_hash_find: For functions requiring string parameters, PHP5.6 passes two parameters ( char* + len ), while PHP7.0 only needs one zend_string variable. Return value becomes zend_bool type.
Performance Optimization Results
After completing PHP7 compilation and testing in late April 2016, the team conducted gray-scale deployment on one AMS machine, observed for several days, then gradually expanded the scope, completing the upgrade in early May.
Pressure testing results and production CGI machine CPU load data under high-traffic TGW scenarios show approximately 100% performance improvement, consistent with official PHP7 claims.
The PHP7 upgrade brought significant performance improvements to the AMS platform, effectively saving hardware resource costs. Additionally, Apache2.4's Event mode enhanced Apache's concurrency support capabilities.
Tencent Cloud Developer
Official Tencent Cloud community account that brings together developers, shares practical tech insights, and fosters an influential tech exchange community.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.