php kuozhan
1、php環境的搭建
我們一般使用源碼包編譯安裝,而不是binary包安裝。因為使用PHP的二進制分發包安裝有些冒險,這些版本傾向于忽略./configure的兩個重要選項,它們在開發過程中很便利: 第一個--enable-debug。這個選項將把附加的符號信息編譯進PHP的執行文件,以便如果發生段錯誤,你能從中得到一個內核轉儲文件,使用gdb追蹤并發現什么地方以及為什么會發生段錯誤。 另 一個選項依賴于你的PHP版本。在PHP 4.3中該選項名為--enable-experimental-zts,在PHP 5及以后的版本中為--enable-maintainer-zts。這個選項使PHP以為自己執行于多線程環境,并且使你能捕獲通常的程序錯誤,然而它 們在非多線程環境中是無害的,卻使你的擴展不可安全用于多線程環境。一旦你已經使用這些額外的選項編譯了PHP并安裝于你的開發服務器(或者工作站)中,你就可以把你的第一個擴展加入其中了。 ?? yum install php-devel? ? ? Zend 引擎提供了一個內存管理器,有在擴展中跟蹤內存泄漏的能力并提供詳盡的調試信息。跟蹤在默認情況下是被禁用的,同時也是線程安全的。要打開的話,應將?--enable-debug?和?--enable-maintainer-zts?選項與其他常用選項一起傳給?configure。要獲得從源代碼構建 PHP 的說明,請看位于?安裝前需要考慮的事項?的說明。
典型的?configure?命令行可能看起來象這樣:
$ ./configure --prefix=/usr/local/php --enable-debug --enable-maintainer-zts --enable-cgi --enable-cli --with-mysql=/path/to/mysql ? ? 1)一般可以把php安裝在/usr/local/php目錄下。 ? ? 2)php的二進制可執行文件都在/usr/local/php/bin目錄,包括php自帶工具phpize. ? ? ? ?phpize實際上是個shell腳本,可以用vi phpize來查看其內容. 注意:使用phpize需要安裝autoconf 宏。 因為config.m4?文件使用 GNU?autoconf?語法編寫。簡而言之,就是用強大的宏語言增強的 shell 腳本。注釋用字符串?dnl?分隔,字符串則放在左右方括號中間(例如,[?和?])。字符串可按需要多次嵌套引用。完整的語法參考可參見位于http://www.gnu.org/software/autoconf/manual/ 安裝autoconf 宏最簡單的方法:apt-get install autoconf2、ext_skel腳本
PHP 擴展由幾個文件組成,這些文件對所有擴展來說都是通用的。不同擴展之間,這些文件的很多細節是相似的,只是要費力去復制每個文件的內容。幸運的是,有腳本可以做所有的初始化工作,名為?ext_skel,自 PHP 4.0 起與其一起分發。
不帶參數運行?ext_skel?在 PHP 5.3.2 中會產生以下輸出:
?
?剩下的?--extname?會將擴展的名稱傳給?ext_skel。"name" 是一個全為小寫字母的標識符,僅包含字母和下劃線,在 PHP 發行包的?ext/?文件夾下是唯一的。
?--proto選項允許開發人員指定一個頭文件,由此創建一系列 PHP 函數,表面上看就是要開發基于一個函數庫的擴展,但對大多數頭現代的文件來說很少能起作用。如果用?zlib.h?頭文件來做測試,就會導致在?ext_skel?的輸出文件中存在大量的空的和無意義的原型文件。--xml?和?--full-xml?選項當前完全不起作用。--skel?選項可用于指定用一套修改過的框架文件來工作,這是本節范圍之外的話題了。
3、擴展組成文件
不管是通過手工,通過 ext_skel?,還是通過另外的擴展生成器,所有的擴展都會有以下個文件: 1) ? config.m4:phpize用來準備構建系統哪些擴展的配置文件configure?選項 ,是UNIX 構建系統配置。對應的win系統是config.w32: ??????????? http://www.php.net/manual/zh/internals2.buildsys.configunix.php 2)?php_hello_module.h ?:包含引用的頭文件當將擴展作為靜態模塊構建并放入PHP 二進制包時,構建系統要求用?php_?加擴展的名稱命名的 頭文件包含一個對擴展模塊結構的指針定義。就象其他頭文件,此文件經常包含附加的宏、原型和全局量。當然你可以把頭文件內容放在源文件hello_module.c頂部。分開只是讓代碼組織更清晰,而且是個很好的習慣。 3) hello_module.c : 包含模塊函數的源碼文件? 擴展應包含任意數量的頭文件、源文件、單元測試和其他支持文件,此四個文件僅夠組成最小的擴展。hello_module擴展的文件列表如下所示:4、與 UNIX 構建系統交互: config.m4
? ? ? ? config.m4文件負責在配置時解析configure的命令行選項。這就是說它將檢查所需的外部文件并且要做一些類似配置與安裝的任務。config.m4?文件告訴 UNIX 構建系統哪些擴展?configure?選項是支持的,你需要哪些擴展庫,以及哪些源文件要編譯成它的一部分。對所有經常使用的 autoconf 宏,包括 PHP 特定的及 autoconf 內建的,
config.m4 文件舉例注意:凡是帶有dnl前綴的都是注釋,注釋是不被解析的。
4.1 PHP_ARG_*: 賦予用戶可選項
?在以上的? config.m4?例子中,兩條注釋后,最先見到的 3 行代碼,使用了?PHP_ARG_WITH()?和?PHP_ARG_ENABLE()。這些給?configure?提供了可選項,和在運行?./configure --help?時顯示的幫助文本。就象名稱所暗示的,其兩者的不同點在于是創建?--with-*?選項還是?--enable-*?選項。每個擴展應提供至少一個以上的選項以及擴展名稱,以便用戶可選擇是否將擴展構建至 PHP 中。按慣例,PHP_ARG_WITH()?用于取得參數的選項,例如擴展所需庫或程序的位置;而?PHP_ARG_ENABLE()?用于代表簡單標志的選項。不管你使用哪一個指令,你都應該注釋掉另外一個。也就是說,如果你使用了–enable-my_module,那就應該去掉–with-my_module。反之亦然。
configue使用例子:./configure ? --enable-hello_module 則將 dnl PHP_ARG_ENABLE(hello_module, whether to enablehello_module support, dnl Make sure that the comment is aligned: dnl [ --enable-hello_module Enablehello_module support]) 修改成 PHP_ARG_ENABLE(hello_module, whether to enablehello_module support, [ --enable-hello_module Enablehello_module support])4.2 處理用戶選擇
? ? ? ?config.m4
?可給用戶提供一些做什么的選擇,現在就是做出選擇的時候了。在上例中,三個選項在未指定時顯然默認為 "no"。習慣上,最好用此值作為用于啟用擴展的選項的默認值,為了擴展與 PHP 分開構建則用?phpize?覆蓋此值,而要構建在 PHP 中時則不應被默認值將擴展空間弄亂。處理這三個選項的代碼要復雜得多。處理 --with-example[=FILE] 選項
? ? ?首先檢測是否設置了?--with-example[=FILE]?選項。如此選項未被指定,或使用否定的格式(--without-example?),或賦值為 "no" 時,它會控制整個擴展的含有物其他任何事情都不會發生。在上面的例子中所指定的值為?/some/library/path/example-config,所以第一個 test 成功了。
接下來,代碼調用?AC_MSG_CHECKING(),這是一個?autoconf?宏,輸出一行標準的如 "checking for ..." 的信息,并檢測用戶假定的?example-config?是否是一個明確的路徑。在這個例子中,PHP_EXAMPLE?所取到的值為?/some/library/path/example-config,現已復制到 EXAMPLE_PATH 變量中了。只有用戶指定了?--with-example?,才會執行代碼?$php_shtool path $EXAMPLE_CONFIG,嘗試使用用戶當前的?PATH?環境變量推測?example-config?的位置。無論如何,下一步都是檢測所選的EXAMPLE_PATH?是否是正常文件,是否可執行,及是否執行成功。如成功,則調用?AC_MSG_RESULT(),結束由?AC_MSG_CHECKING()?開始的輸出行。否則,調用?AC_MSG_ERROR(),打印所給的信息并立即中斷執行?configure。
代碼現在執行幾次?example-config?以確定一些站點特定的配置信息。下一步調用的是?PHP_CHECK_LIBRARY(),這是 PHP 構建系統提供的一個宏,包裝了?autoconf?的?AC_CHECK_LIB()?函數。PHP_CHECK_LIBRARY()?嘗試編譯、鏈接和執行程序,在第一個參數指定的庫中調用由第二個參數指定的符號,使用第五個參數給出的字符串作為額外的鏈接選項。如果嘗試成功了,則運行第三個參數所給出的腳本。此腳本從?example-config?所提供的原始的選項字符串中取出頭文件路徑、庫文件路徑和庫名稱,告訴 PHP 構建系統。如果嘗試失敗,腳本則運行第四個參數中的腳本。此時調用?AC_MSG_ERROR()?來中斷程序執行。
處理 --enable-example-debug 選項
? ? ? 處理?--enable-example-debug?很簡單。只簡單地檢測其真實值。如果檢測成功,則調用?AC_DEFINE()?使 C 語言宏指令?USE_EXAMPLE_DEBUG?可用于擴展的源代碼。第三個參數是給?config.h?的注釋字符串,通常可放心的留空。
處理 --with-example-extra=DIR 選項
? ? ? 對于此例子來說,由?--with-example-extra=DIR?選項所請求的假定的“額外”功能操作不會與假定的?example-config?程序共享,也沒有默認的搜索路徑。因此,用戶需要在所需的庫之前提供設置程序。有點不象現實中的擴展,在這里的設置僅僅起說明性的作用。
代碼開始用已熟知的方式來檢測?PHP_EXAMPLE_EXTRA?的真實值。如果所提供的為否定形式,則不會進行其他處理,用戶也不會請求額外的功能。如果所提供的為未提供參數的肯定形式,則調用?AC_MSG_ERROR()?中止處理。下一步則再次調用PHP_CHECK_LIBRARY()。這一次,因為沒有提供預定義編譯選項,PHP_ADD_INCLUDE()?和?PHP_ADD_LIBRARY_WITH_PATH()?用于構建額外功能所需的頭文件路徑、庫文件路徑和庫標志。也調用?AC_DEFINE()?來指示所請求的額外功能代碼是可用的,設置變量來告訴以后的代碼,有額外的源代碼要構建。如果檢測失敗,則調用所熟悉的?AC_MSG_ERROR()。另一種不同的處理失敗的方式是更換為調用?AC_MSG_WARNING(),例如:
4.3?PHP_NEW_EXTENSION宏
? ? ? ? 默認情況下,通過ext_skel創建的config.m4都能接受指令,并且會自動啟用該擴展。啟用該擴展是通過PHP_EXTENSION這個宏進行 的。如果你要改變一下默認的情況,想讓用戶明確的使用 –enable-my_module或 –with-my_module指令來把擴展包含在PHP二進制文件當中,那么將 “if test "$PHP_MY_MODULE" != "no"”改為“if test "$PHP_MY_MODULE" == "yes"”即可。
if test "$PHP_MY_MODULE" == "yes"; thendnl
? ? ? ? ? PHP_EXTENSION(hello_module, $ext_shared)
fi?
這樣就會導致在每次重新配置和編譯PHP時都要求用戶使用 –enable-my_module指令。??
PHP_NEW_EXTENSION()
?就是宏告訴構建系統去構建擴展本身和被其用到的文件。PHP_NEW_EXTENSION()參數:
? ? ?第一個參數是擴展的名稱,和包含它的目錄同名。
? ? ?第二個參數是做為擴展的一部分的所有源文件的列表
。參見?PHP_ADD_BUILD_DIR()?以獲取將在子目錄中源文件添加到構建過程的相關信息。? ? ?第三個參數總是?$ext_shared, 當為了?--with-example[=FILE]?而調用?PHP_ARG_WITH()時,由?configure?決定參數的值。
? ? ?第四個參數指定一個“SAPI 類”,僅用于專門需要 CGI 或 CLI SAPI 的擴展。其他情況下應留空。
? ? ?第五個參數指定了構建時要加入?CFLAGS?的標志列表。
? ? ?第六個參數是一個布爾值,為 "yes" 時會強迫整個擴展使用?$CXX?代替?$CC?來構建。第三個以后的所有參數都是可選的。最后,調用?PHP_SUBST()?來啟用擴展的共享構建。
? 例如我們要構建擴展是hello_module5、擴展模塊代碼的
模塊結構
所有的PHP模塊通常都包含以下幾個部分:
·????????包含頭文件(引入所需要的宏、API定義等);
·????????聲明導出函數(用于Zend函數塊的聲明);
·????????聲明Zend函數塊;
·????????聲明Zend模塊;
·????????實現get_module()函數;
·????????實現導出函數。
詳解請看:
PHP擴展代碼結構詳解
6、創建擴展的詳細步驟
我們創建擴展最好放在php的源碼包的ext目錄下。如/opt/php-5.3.2/ext/下 1) ext_skel來建立一個php擴展的一個框架 root@ubuntu:/#?cd /opt/php-5.3.2/ext/ root@ubuntu:opt/php-5.3.2/ext/]# ./ext_skel --extname=hello_module 執行了這個步驟以后看到這樣的結果:?
?root@ubuntu:/opt/php-5.3.2/ext/hello_module# ls
config.m4 ?config.w32 ?CREDITS ?EXPERIMENTAL ?hello_module.c ?hello_module.php ?php_hello_module.h ?tests
然后我們要修改文件順序是 configue.m4 hello_module.c php_hello_module.h 2)編輯config.m4文件,我們使用enable-hello_module選項: dnl PHP_ARG_ENABLE(hello_module, whether to enablehello_module support, dnl Make sure that the comment is aligned: dnl [ --enable-hello_module Enable hello_module support]) 修改成 PHP_ARG_ENABLE(hello_module, whether to enable hello_module support,[ ?--enable-hello_module ? ? ? ? ? Enable hello_module support]) 3)vi?hello_module.c 主要是給模塊添加函數: ?/* Every user visible function must have an entry in my_module_functions[].*/ function_entry hello_module_functions[] = { PHP_FE(hello_world, NULL) /* 添加著一行代碼 */ PHP_FE(confirm_my_module_compiled, NULL) /* For testing, remove later. */ {NULL, NULL, NULL} /* Must be the last line in my_module_functions[] */ }; 在文件的最后添加下列代碼 ?定義函數: PHP_FUNCTION(hello_world) { zend_printf("hello sdomain!"); }
4)修改php_hello_module.h 在PHP_FUNCTION(confirm_my_module_compiled ); /* For testing, remove later. */ 這行的下面添加一行: PHP_FUNCTION(hello_world); /* 函數的聲明 */ 5) 執行phpiz并編譯 ?root@ubuntu:/opt/php-5.3.2/ext/hello_module#?/usr/local/php/bin/phpize ?執行以后會看到下面的 ? ? ? ? ?Configuring for:
? ? ? ? ?PHP Api Version: ? ? ? ? 20090626
? ? ? ? ?Zend Module Api No: ? ? ?20090626
? ? ? ? ?Zend Extension Api No: ? 220090626 然后執行: root@ubuntu:/opt/php-5.3.2/ext/hello_module#./configure ?--enable-hello_module --with-php-config=/usr/local/php/bin/php-config root@ubuntu:/opt/php-5.3.2/ext/hello_module#?make 這個時候會在當前的目錄下生成一個目錄叫modules先存放著hello_module.so文件 cp modules/hello_module.so ? ? /usr/local/php/ext/ 然后再把hello_module.so文件拷到php.ini里面的extension_dir所指定的位置 6)開啟擴展 php.ini文件中打開這個擴展 extension=hello_module.so 重新起動apache 用phpinfo來察看一下ok了
轉載于:https://blog.51cto.com/zhaojunjie/1028541
總結
以上是生活随笔為你收集整理的php kuozhan的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: AIX 系统的启动和关机
- 下一篇: JQuery图表插件之Flot