The implementation method of PHP calling C code

Source: Internet
Author: User
Tags bool config function prototype min php code php source code

  This article is mainly on the PHP to invoke the implementation of the C code is introduced, the need for friends can come to the reference, I hope to help you.

In the PHP program needs to use the C code, should be the following two kinds of cases:   1 already have C code, in the PHP program to directly use 2 because of PHP performance problems, need to use C to implement some of the functions   for the first case, the most appropriate method is to use system calls, Write the existing C code as a separate program. The parameters are passed through the command line or standard input, and the results are read from the standard output. Second, a little bit of trouble is the C code written in a daemon,php program with the socket to communicate with it.   Focus on the second case, although it's OK to follow the system call method, but think about your goal of optimizing performance, so many processes are so frequent that it will certainly degrade performance. and write daemon method is feasible, but cumbersome a lot.   My simple test, the same algorithm, using C to write than PHP efficiency can be improved 500 times times. And the way to expand in PHP, can also improve 90 times (which performance loss in the parameters of the pass, I guess).   So there are times when PHP extensions are our best choice.   Here I will highlight the way to write PHP extensions in C, and do not need to recompile PHP.   First, find a PHP source code, PHP4 or PHP5 version of the can, and your target platform of the PHP version has no relationship.   In the source of the Ext directory can find a script named Ext_skel (Windows platform using ext_skel_win32.php) in this directory to execute./ext_skel--extname=hello (I use Hello as an example) This generates a directory hello, there are several files in the directory, you only need to care about these three: config.m4 hello.c php_hello.h   Copy this directory to any place you want, CD in, and then execute phpize/configure Make doesn't happen, does it? This is because of a missed step, open CONFIG.M4, find the following dnl If your extension references something, use with:. DNL otherwise use enable:.. This is where you choose your extension to use with or enable, we use with bar. Uncomment the WITH section. If you use the Vim editor as much as I do, it's easy to see that the three-letter dnl is originally annotated (this is because VIM defaults to a syntax coloring package with various file formats)   We modifyAfter CONFIG.M4, continue phpize/configure make, modules generates hello.so and hello.la files below. One is a dynamic library, the other is a static library.   Your PHP extension has been done, although it has not yet achieved the functionality you want, let me first say how to use this extension! Ext_skel for you to generate a hello.php inside a call example, but that example requires you to copy the hello.so to PHP's extended directory, we just want to achieve their own functions, do not want to build a cottage version of PHP, use my following method to load it:   code as follows : if (!extension_loaded ("Hello")) {        dl_local ("hello.so");} function dl_local ($extensionFile) {       //make sure that we are able to load LIBRARIES06.        IF (!) ( BOOL) Ini_get ("Enable_dl") | | (BOOL) Ini_get ("Safe_mode")) {                Die ("dh_local (): Loading Extensi ONS is not permitted./n ");        }        //check to make sure the file EXISTS11.        if (!file_exists) (DirName (__file__). "/". $extensionFile)) {                Die ("dl_local (): File ' $extensionFile ' does Not exist./n ");        }        //check the file PERMISSIONS16.        if (!is_executable) (DirName (__file__). "/". $extensionFile)) {                Die ("dl_local (): File ' $extensionFile ' is no T executable./n ");        }        //we figure out the path21.         $currentDir = dirname (__file__). "/";         $currentExtPath = Ini_get ("Extension_dir");         $subDirs = Preg_match_all ("////", $currentExtPath, $matches);         unset ($matches);        //lets Make sure we extracted a valid extension path27.        IF ( BOOL) $subDirs) {                Die ("dl_local (): Could not determine a valid ex Tension path [extension_dir]./n];        }         $extPathLastChar = strlen ( $currentExtPath)-1;         if ($extPathLastChar = = Strrpos ($currentExtPath, "/") {        &NBSP ;       $subDirs--;        }         $BACKDIRSTR = ";          for ($i = 1; $i <= $subDirs; $i + +) {                $backDirStr. = "...";           & nbsp     if ($i!= $subDirs) {                  $BACKDIRSTR. = "/"; &N Bsp               {               //construct t He final path to load46.         $finalExtPath = $backDirStr. $currentDir. $extensionFile;        //now we execute DL () to actually load the module49.        if (!DL ($finalExtPath)) {              &NBsp Die ();        }        //if the module was loaded correctly, we must bow grab the Modul E name54.         $loadedExtensions = Get_loaded_extensions ();         $thisExtName = $loadedExtensions [sizeof ($loadedExtensions)-1];        //lastly, we return the extension name58.        return $thisExtName; }//end dl_local ()   The advantage is that your PHP extensions can go with your PHP code, green extensions.   Then a matter of concern is how to add functions, implement parameter passing, and return values   add functions as follows: Php_hello.h:php_function (confirm_hello_compiled); Inside the parentheses fill in the function name   hello.c zend_function_entry hello_functions[] = {    Php_fe (confirm_hello_compiled,   NULL)      /* Here is a line to add/    {null, NULL, NULL}  /* must be is the last lines in Hello_functions [] */ }; Php_function (confirm_hello_compiled)   {//Here write function body} to implement the function prototype is actually the same, with a macro php_function to wrap up, in addition, in Hello_ Functions adds a line of information that says you have this function in the module.   That's the same function prototype., how do you differentiate between return values and parameters? I give an example:     code as follows: Php_function (Hello_strdiff) {    char *r1 = null, *R2 = NULL;     INT n = 0, m = 0;     if (Zend_parse_parameters (Zend_num_args () TSRMLS_CC, "SS", &r1, &n, &R2, &m) = = failure) {& nbsp       return;    }     while (n && m && *r1 = *r2) {        r1++   &NBSP ;     r2++;         n--;         m--;    }     if (n = 0) Return_long (m);     if (M = = 0) return_long (n);     INT d[n+1][m+1];     int cost;     int i,j;     for (i = 0; I <= N; i++) d[i][0] = i;     for (j = 0 J <= m; j + +) d[0][j] = j;     for (i = 1; I <= n; i++) {        for (j = 1; j <= M; j +) {      & nbsp     if (r1[i-1] = = R2[j-1]) cost = 0;            Else cost = 1;             int a = MIN (d[i-1][j]+1,d[i][j-1]+1);             A = MIN (A, d[i-1][j-1]+cost);             D[I][J] = A;        }     {    Return_long (d[n][m]);   This is a two-string difference algorithm, input parameter two string, return integral type. The passing of the parameters looks here Zend_parse_parameters (Zend_num_args () TSRMLS_CC, "SS", &r1, &n, &R2, &m)   Take this as a scanf to understand. The type description is shown in the following table: Boolean b zend_bool  Long l long  Double d double  String s char*, int  Resource R zval*&nbsp ; Array a zval*  Object o zval*  zval z zval*      If you want to implement optional parameters, such as a string, a floating-point, and an optional bool, you can use the "sd|b" to indicate. What's different with scanf is that for strings, you provide two variables to store, one is char *, the address of the stored string, an int, to keep the length of the string. When this is necessary, you can safely handle binary data.   What about the return value? Use the following set of macros to represent:   return_string return_long return_double return_bool return_null   Note return_string has two parameters Use return_string when you need to copy a string ("Hello World", 1); &nbsp Otherwise use return_string (str, 0);   This involves the allocation of memory in the module, when you request the memory needs to release the PHP program, please refer to the following table   traditional non-persistent persistent  malloc (count) Calloc (count, num) emalloc (count) ecalloc (count, num) Pemalloc (count, 1) * PECALLOC (count, num, 1)   StrDup (str) strnd Up (str, len) estrdup (str) estrndup (str, len) pestrdup (str, 1) pemalloc () & memcpy ()   free (PTR) efree (PTR) pefree ( PTR, 1)   realloc (PTR, newsize) Erealloc (PTR, newsize) Perealloc (PTR, newsize, 1)   malloc (count * num + extr) * * Afe_emalloc (count, num, extr) safe_pemalloc (count, num, extr)     Generally we use these listed in the Non-persistent to good.   Basically, you can start writing a php extension. From my current application, the ability to manipulate strings is enough, so I can only introduce so much.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.