Upload
elizabeth-smith
View
13.555
Download
0
Embed Size (px)
Citation preview
PHP
EXTENSIONSFor Dummies
But I don’t know C!1.compiled
2.strictly typed
3.php internals do “hard” stuff
4.copy and paste!
5.cairo, pecl_http, date, imagick, dio
lxr.php.net
Quick Setup Needs1.compiler
2.sdk (on win, put this on FIRST)
3.tools
4.dependencies
5.code
phpize is your friend!
How to Compile1.phpize
2../configure
3.make
4.make install
5.make test
configure might require –with-php-config
How to Play alonghttps://github.com/auroraeosrose/php-extensions-code.git
git://github.com/auroraeosrose/php-extensions-code.git
1. Set up configuration2. Write a module definition3. Learn about the PHP lifecycle4. Learn about zvals5. Add functions6. ???7. Profit!
Every Other Extensions Talk
DO
IN IT R
ON
G
Which do YOU want?
Please be the solution, not the problemWe need no more painful APIs in PHP
1. Do something you can’t do in userland2. Utilize a C library3. Make slow code faster
Maybe you should just use ffi!
Step 1. What, When, Why
FFI
1. Think about what the API should be2. Look at the C APIs but don’t mimic them3. Write an example of how you WANT it to
work4. Write more then one example!
Step 2. How
1. This is copy and paste1. config.m4 & config.w322. macros for version api changes if
necessary3. main module file (php_{$ext}.c)4. main header file (php_{$ext}.h)
2. Compile it and test!
Step 3. Scaffolding
Configure files
Module struct
Scaffolding rules
1. make sure you name your files in a standard way2. document! use a license header, proto statements3. read the coding standards http://
lxr.php.net/xref/PHP_5_4/CODING_STANDARDS 4. FOLLOW THE CODING STANDARDS5. use version control early on – github is easy!
php –d extension=myext.so –m
The scaffold extension should show up in the list
Make sure to 1. define a version constant2. read and use PHP code standards
Check if it works
1. run-test.php2. make test will magically have output
more at http://qa.php.net/write-test.php and docs at http://qa.php.net/phpt_details.php
Step 4. Write the test
PHPT tests
1. add functions2. get data3. return data
Step 5. Actually do something
long any numeric
double numeric with decimal
char* + int
(length)strings, binary
Hashtabledictionaries,
arrays,structs
object any complicated type
Anatomy of a Function
zval
getting data OUTZ_LVAL(zval) Z_LVAL_P(zval_p) Z_LVAL_PP(zval_pp)
Z_BVAL(zval) Z_BVAL_P(zval_p) Z_BVAL_PP(zval_pp)
Z_DVAL(zval) Z_DVAL_P(zval_p) Z_DVAL_PP(zval_pp)
Z_STRVAL(zval) Z_STRVAL_P(zval_p) Z_STRVAL_PP(zval_pp)
Z_STRLEN(zval) Z_STRLEN_P(zval_p) Z_STRLEN_PP(zval_pp)
Z_ARRVAL(zval) Z_ARRVAL_P(zval_p) Z_ARRVAL_PP(zval_pp)
Z_OBJVAL(zval) Z_OBJVAL_P(zval_p) Z_OBJVAL_PP(zval_pp)
Z_OBJ_HANDLE(zval)
Z_OBJ_HANDLE_P(zval_p)
Z_OBJ_HANDLE_PP(zval_pp)
Z_OBJ_HT(zval) Z_OBJ_HT_P(zval_p) Z_OBJ_HT_PP(zval_pp)
Z_OBJCE(zval) Z_OBJCE_P(zval_p) Z_OBJCE_PP(zval_pp)
Z_OBJPROP(zval) Z_OBJPROP_P(zval_p) Z_OBJPROP_PP(zval_pp)
Z_TYPE(zval) Z_TYPE_P(zval_p) Z_TYPE_PP(zval_pp)
zend_parse_parametersphp type cod
e c type
array or object a zval *
boolean b zend_bool
class C zend_class_entry *
double d double
callable f zend_fcall_info andzend_fcall_info_cache
array or HASH_OF(object) H HashTable*
array h HashTable*
integer l long (NOT INT)
integer L long with LONG_MAX, LONG_MIN limits
object o zval *
object of specific type O zval *, zend_class_entry
string (no null bytes) p char*, int
resource r zval *
string (possible null bytes)
s char*, int
actual zval z zval *
actual zval Z zval**
zend_parse_parameterstype code
variable args (any) * int, zval***
variable args (1 or more) + int, zval***
| anything after is optional, use defaults
/ use SEPARATE_ZVAL_IF_NOT_REF
doesn’t apply to b, l, and d ! C NULL for zval null
Returning Data with return_valueRETURN_RESOURCE(l)
RETURN_BOOL(b)
RETURN_NULL()
RETURN_LONG(l)
RETURN_DOUBLE(d)
RETURN_STRING(s, duplicate)
RETURN_STRINGL(s, l, duplicate)
RETURN_EMPTY_STRING()
RETURN_ZVAL(zv, copy, dtor)
RETURN_FALSE
RETURN_TRUE
RETVAL_RESOURCE(l)
RETVAL_BOOL(b)
RETVAL_NULL()
RETVAL_LONG(l)
RETVAL_DOUBLE(d)
RETVAL_STRING(s, duplicate)
RETVAL_STRINGL(s, l, duplicate)
RETVAL_EMPTY_STRING()
RETVAL_ZVAL(zv, copy, dtor)
RETURN_FALSE
RETURN_TRUE
Complex Data
array_init()
add_(index|assoc)_long()
add_(index|assoc)_bool()
add_(index|assoc)_string()
object_init()
add_property_long()
add_property_bool()
add_property_string()
1. namespaces2. classes3. methods4. constants
Step 6. Make it shiny
Classes
1. name, parent, and flags2. hashtables of methods, default methods,
static methods3. hashtables of static properties, default
properties, and properties4. object handlers 5. union of either file information, or
internal structures (for internal classes)
Lifecycle
PHP stops
MSHUTDOWN – for each extension
RSHUTDOWN – for each request
GSHUTDOWN – for each thread
GINIT – for each thread
RINIT – for each request
MINIT – for each extension
PHP starts
Class Properties
Class Constants
Class Methods
Alter $this
Abstract, Interface, TraitClass Method
ZEND_ACC_IMPLICIT_ABSTRACT_CLASS ZEND_ACC_STATIC
ZEND_ACC_EXPLICIT_ABSTRACT_CLASS ZEND_ACC_ABSTRACT
ZEND_ACC_FINAL_CLASS ZEND_ACC_FINAL
ZEND_ACC_INTERFACE ZEND_ACC_PUBLIC
ZEND_ACC_TRAIT ZEND_ACC_PROTECTED
ZEND_ACC_PRIVATE
ZEND_ACC_CTOR
ZEND_ACC_DTOR
ZEND_ACC_CLONE
spl_ce_FilterIterator->ce_flags |= ZEND_ACC_EXPLICIT_ABSTRACT_CLASS;PHP_ME(DateTime, __construct, arginfo_date_create, ZEND_ACC_CTOR|ZEND_ACC_PUBLIC)
1. globals2. memory management3. custom objects4. object handlers5. thread safety
Step 7. Advanced topics
1. in your header – use ZEND_BEGIN|END_MODULE_GLOBALS
2. create the global access macro in your header (copy and paste)
3. ZEND_DECLARE_MODULE_GLOBALS in every file where you will use them
4. use the macro to access COUNTER_G(basic_counter_value)); }
5. Create ginit/gshutdown functions if your globals need initializing , etc
Global Variables (threads = evil)
emalloc( )• allocates the specified number of bytes
safe_emalloc()• like emalloc but adds a special protection against overflows
efree( )• releases the specified block of memory back to the system
estrdup( )• allocate a buffer and copy the string into that buffer
estrndup( )• same as estrdup when you already know the length of the string
ecalloc( )• allocates the number of bytes and initializes them to zero
erealloc( )• resizes the specified block of memory
https://wiki.php.net/internals/zend_mm
1. clean up what you emalloc (C level destructor)2. read wiki on how to make them extendable!
Object Handlers (black magic)
https://wiki.php.net/internals/engine/objects
TSRMthread safe resource
managerZTS
zend thread safety• tsrm_lsTSRMLS_C
• void ***tsrm_lsTSRMLS_D
• , tsrm_lsTSRMLS_CC
• , void ***tsrm_ls
TSRMLS_DC
1. http://edit.php.net 2. http://svn.php.net/viewvc/phpdoc/en/trunk/referenc
e/
3. PhD is awesomesauce• http://doc.php.net/phd/
4. email [email protected] 1. who you are2. what you wrote (with links to your code!)3. why you think it should be in pecl
5. poke me (or other devs)
Step 7. Document, PECL, release
Stuff I didn’t talk about
1. resources (use custom objects instead)2. ini entries (just DON’T)3. threading and parallel processing4. engine hooking
About Me
http://emsmith.net
https://joind.in/6337
IRC – freenode – auroraeosrose
#php-gtk #coapp and others
Questions?
HELP WITH DOCS!http://edit.php.nethttp://wiki.php.net/internals
lonestar
12Free codez 4 u!
Resources:http://devzone.zend.com/303/extension-writing-part-i-introduction-to-php-and-zend/ http://blog.golemon.com/2006/06/what-heck-is-tsrmlscc-anyway.html http://www.kchodorow.com/blog/2011/08/11/php-extensions-made-eldrich-installing-php/ http://php.net/manual/en/internals2.phphttps://wiki.php.net/internals http://conf.phpquebec.com/slides/2009/PHP_Extension_Writing-phpquebec_2009.pdf http://devzone.zend.com/1435/wrapping-c-classes-in-a-php-extension/http://lxr.php.net http://www.amazon.com/Extending-Embedding-PHP-Sara-Golemon/dp/067232704X