logansama Posted January 12, 2009 Share Posted January 12, 2009 Good day, Attempting the way of dynamically loading a created extension (.so) via the php.ini on linux. The extension is a c++ based extension created using Swig framework. I understand the php.ini way being: (for explaining purposes 'extension.so' represents the extension file/s ) 1. copy the extension.so file to be used, to the extensions dir/location specified by the the php.ini file 2. add to the php.ini file (under Dynamic Extensions) the line "extension=extension.so" 3. Restart the apache to reload the new settings of the php.ini. 4. Call the functions in a php file to test. unfortunately i receive errors when calling the function: "Fatal error: Call to undefined function foo() in /file_location/file.php on line #" when testing by adding the following code to top of php file....: (please note that enable_dl is On in the php.ini) if( dl('extension.so') ) { echo "could load all good! <br>"; } ..i recieve the output: ""Warning: Module 'extension' already loaded in Unknown on line 0"" i understand the above to mean that dl is trying to load something that is already loaded. i also did a command line check 'php -m' to check that the 'test' extension i am dynamically loading has not been compiled in with php. And it has not been. I am not sure if this all means the extension has loaded correctly but its been created incorrectly, or if the shared object has just not been loaded correctly. If anyone knows that my php.ini implementation is flawed, please tell me and if possible also on how to do it correctly. If you know of another way to do dynamically add extension library files, please help me out. I thank you in advance. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/ Share on other sites More sharing options...
trq Posted January 12, 2009 Share Posted January 12, 2009 i understand the above to mean that dl is trying to load something that is already loaded. That is indeed correct, so it would appear your extension loads. i also did a command line check 'php -m' to check that the 'test' extension i am dynamically loading has not been compiled in with php. And it has not been. The php cli is a completely different engine to that of mod_php. Are all these test happening via the cli? Maybe there is a fault in the extension itself? Does foo() actually exist? (Silly question I'm sure) Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-735226 Share on other sites More sharing options...
logansama Posted January 12, 2009 Author Share Posted January 12, 2009 by all means i am sure that the extension has not been configured as part of php. I am not sure if the extension shared-object does contain a fault. Is there a means to test it? The shared object is created by compiling a wrapped .cpp file. This wrapped .cpp file is created by Swig using a normal .cpp file with c++ code. This wrapped cpp file contains the needed php/zend/cpp/c converted code used by php to understand extension. The original cpp file has the function foo(), the wrapped cpp file (before compiling) has the function as _wrap_foo() and the EXAMPLE php file the Swig created (to test the shared object extension) has a call to _foo(). In my test php file i have made a call to foo(), _wrap_foo() and _foo() and all of them result in "call to undefined function". I am now trying to figure out what the extension contains, wonder if there is a standard way to view the content of a loaded extension? Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-735261 Share on other sites More sharing options...
corbin Posted January 12, 2009 Share Posted January 12, 2009 You could look at its exports in a debugger or something. So, how exactly does the C wrapper work? (I'm guessing the wrapper is written in C and is around a C++ class.) Is the C++ code compiled into a lib and then the wrapper compiles it in and makes calls with the right calling type or something? What exactly is the wrapper doing? Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-735608 Share on other sites More sharing options...
logansama Posted January 13, 2009 Author Share Posted January 13, 2009 Swig does the 'wrapping' of your source/implementation code before you proceed to compile it into a shared object. Normal extensions are in C so you need some extra conversion if you are using C++. Swig apparently does all the needed changes for you. I just need to figure out exactly how so i can actually use the extension. A link if you want more detail http://www.swig.org/Doc1.3/Php.html#Php_nn2_6 it also deals with many other langiages, not just php and c++. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-735974 Share on other sites More sharing options...
logansama Posted January 13, 2009 Author Share Posted January 13, 2009 Some additional findings: (and with these i find myself in waters i have not swam in before. ) ran "php --re test" ('test' being the name of the extension i created using the Swig environment): Extension [ <persistent> extension #55 test version <no_version> ] { - Functions { Function [ <internal:test> function new_test ] { } Function [ <internal:test> function test_calc ] { } Function [ <internal:test> function test_getnumber ] { } } } test_calc is implemented in the original cpp file to receive two int parameters. so when i call itin a php file as follows: <?PHP test_calc(10,10); i get the following: Warning: Wrong parameter count for test_getnumber() in /opt/lampp/htdocs/extension/calculate.php on line 6 the test_getnumber() is supposed to receive no parameters but when i call test_getnumber() i get the same warning as above. At this point i am not even sure what to ask help for? hehe I think i will settle for ANY input or opinions etc. Thank you. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-736003 Share on other sites More sharing options...
corbin Posted January 15, 2009 Share Posted January 15, 2009 Is test_calc something like: void test_calc(int i1, int i2); Because if so, that's not how PHP extensions work. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-737480 Share on other sites More sharing options...
logansama Posted January 15, 2009 Author Share Posted January 15, 2009 Last night i managed to get something going. Its basic, maybe not exactly 100% correct, but it works and is a good starting point. Please note that i still created the extension using Swig. Also note that the C++ i used was based on tutorial examples i could find, i am not a c++ programmer. To provide the data and steps: 1.) The Input file :: test4.i %module test4 %{ #include "test4.cpp" %} %include "test4.cpp" This file describes what you want to include. I always had the file.h descriptions here, but that caused a fault when a function was called from the php. The reason was that the function is listed in the extension but the implementation does not exist. By listing the cpp file (implementation) the function calls result correctly in the php. 2.) test4.h #ifndef __TEST4_H__ #define __TEST4_H__ int test4_showNumber(); #endif 3.) test4.cpp #include <iostream> #include "test4.h" using namespace std; int test4_showNumber() { int num = 8 +12; return num; } Please note this is VERY simple, the point was just to test actual implementation. I did everything in Ubuntu 8.10. In order to use swig you need to have it installed. View their website for more details on everything they do. http://www.swig.org. You also need a working PHP installed. I used XAMPP for linux (lampp) as well as a version compiled from source. v5.2.8 PHP in both cases. And lastly a working gcc/g++ installation. I used version 4.3.2. In the directory where the three above files are located i ran the following commands: 1.) swig -php5 -c++ test4.i this builds a few files. Their uses can be read about on their site. 2.) g++ 'php-config --includes' -fpic -c test4_wrap.cpp Please note that i did not type 'php-config --includes' as part of the command. What i mean by it is that the output you get from the command 'php-config --includes' should be added in the command above in its place. The lampp installation did not have the needed include directories and files, so i used those from the source built php. 3.) g++ -shared test4_wrap.o -o test4.so Then copy the .so file to where your extensions are stored. In my case with lampp it was in ../lampp/lib/php/extension/no-debug-non-zts-20060613/. Then edit your php.ini file: Add the following under "Dynamic Extensions": extension=test4.so Then restart your apache so that the new settings of the php.ini is loaded. The test php file i created was as follows: <?PHP if( extension_loaded("test4") ) { echo "<br><br><br>LOADED TEST 4 !! <br>"; } else { echo "NOTHING!! <br>"; } if (function_exists('test4_showNumber')) { echo "test4_showNumber is available.<br />\n"; } else { echo "test2_testNumber not available.<br />\n"; } echo "<br>The number is ....<br>"; $val1= test4_showNumber(); echo $val1; the output is then: LOADED TEST 4 !! test4_showNumber is available. The number is .... 20 Like i said a very simple implementation, but still an implementation and a start. Thank you for all the help everybody and hope someone finds this helpful/interesting. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-737537 Share on other sites More sharing options...
corbin Posted January 15, 2009 Share Posted January 15, 2009 Glad you got it figured out ;p. Just wondering, are you writing an extension from scratch, or are you using some pre-written library of yours or something? If you're writing from scratch, it might just be easier to write it in C. That code up there was entirely valid with C. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-737953 Share on other sites More sharing options...
logansama Posted January 16, 2009 Author Share Posted January 16, 2009 hehe, yes i will be given pre-written c++ to turn into an extension this way. My level of skill with C and C++ is entry-level at best. But yes, since php extensions should be written in C i fully agree with you. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-738179 Share on other sites More sharing options...
corbin Posted January 16, 2009 Share Posted January 16, 2009 Ahhhh was just wondering ;p. Quote Link to comment https://forums.phpfreaks.com/topic/140502-solved-issue-with-dynamically-loading-c-created-extension-in-phpini/#findComment-738754 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.