Re: [PHP-DEV] simple solution to another namespace conundrum?
On Tue, 24 Jun 2008, Rasmus Lerdorf wrote: Derick Rethans wrote: On Tue, 24 Jun 2008, Alexey Zakhlestin wrote: it won't be a serious 'wtf', as on the top of the file, there would be some kind of use MySuperLibrary::DateTime; I know, but 400 lines down in the code you can't really see that. This addition might fix the immediate issue - but it doesn't make life easier for the developers that have to maintain the code. Even less if they're not aware that stuff is namespaced. If we don't allow it to work this way, then I really don't see the point in namespaces at all, which I assume is the point you are trying to make. Actually, the point that I was trying to make is that we instead of encouraging this confusion, we should put somewhere in our userland nameing guidelines that you still would need to provide a prefix to your (aliased) classnames in order to prevent confusion. But that then seriously means I see no real good reason still why people want namespaces with confusing resolving rules (concerning static methods like Greg points out). regards, Derick -- Derick Rethans http://derickrethans.nl | http://ezcomponents.org | http://xdebug.org -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
On 18.06.2008, at 14:17, Christian Seiler wrote: Now, upon execution of the code containing the closure, the new opcode just copies the zend_function structure into a copy, registers that copy as a resource and returns that resource. As soon as the resource is garbage collected (or explicitly unset), the op_array copy is destroyed. No modification of the actual class is done at all - the cache remains happy. So since a reference is stored, it means that the destructor of the enclosing object is only called once not only the variable holding the object, but also all lambda functions that were created inside of the class have been free'ed? regards, Lukas Kahwe Smith [EMAIL PROTECTED] -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
On Jun 26, 2008, at 4:06 AM, Lukas Kahwe Smith wrote: Now, upon execution of the code containing the closure, the new opcode just copies the zend_function structure into a copy, registers that copy as a resource and returns that resource. As soon as the resource is garbage collected (or explicitly unset), the op_array copy is destroyed. No modification of the actual class is done at all - the cache remains happy. So since a reference is stored, it means that the destructor of the enclosing object is only called once not only the variable holding the object, but also all lambda functions that were created inside of the class have been free'ed? I'm not up to date on the operation of the current patches to implement closures, but typically this is how it'd work, retaining references to what's needed as long as the closures exist. -- Gwynne, Daughter of the Code This whole world is an asylum for the incurable. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] Re: Using Network functions.
W liście Mangol Smith z dnia czwartek 26 czerwca 2008: But, doesn't this make my extension depend on Curl or any PEAR extension you are talking about? That is what I wan't to avoid. Are you sure you even need to write your own extension? If you just want to do HTTP requests, then curl or HTTP extension should be sufficient. -- Paweł Stradomski -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] Re: Using Network functions.
Are you sure you even need to write your own extension? If you just want to do HTTP requests, then curl or HTTP extension should be sufficient. Nope, I'm developing an extension. In which I require this functionality. Its not the entire purpose of my extension. Just a part of the functionality.
[PHP-DEV] [PATCH] ODBC_Pconnect should not Commit/Rollback database transactions of previous data
Hi We have a problem with the (ODBC) persistent database connection. We have found that every PHP-session, using the same dsn, user and password, are getting the same persistent connection by a reasonable chance. Also meaning that if a database transaction was not finished, other PHP-session can do a rollback or commit of that transaction. Due to resource problems with (temporarily) connections the persistent connections are used, so we do. But leftovers of database transactions were not intended. Also if one want to open an another connection in one PHP-session the result is the same connection. (E.g. we use a DB-log-file to log errors en warning, so you don't want to do a rollback on the DB-log-file, in peculiar.) To overcome these problems one has to tag the connections. I suggest to use a new parameter on ODBC_(p)connect: Tag, a string parameter. If used it tries to re-connect to the connection with the same tag, if not existing it creates a new-connection. For example the tag parameter is filled with the session_ID() to ensure that a connection is bounded to one PHP-session. But also an extension on this value is possible: (Session_ID() + 'Log') or (Session_ID() + 'Data'). And if somebody does not uses this tag parameter, it works in the old way, so these solution is downwards compatible. So the adjusted description will be: resource odbc_pconnect (string $dsn , string $user , string $password [, int $cursor_type [, string $tag ] ] ) Eg ODBC_pconnect( $dns, $user,, $password, SQL_CUR_DEFAULT, Session_ID()+ 'LOG') The change of the PHP source of the function odbc_do_connect is minimal: void odbc_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent) { char*db = NULL; char*uid = NULL; char*pwd = NULL; char*tag = NULL; zval **pv_db, **pv_uid, **pv_pwd, **pv_opt, **pv_tag; odbc_connection *db_conn; char *hashed_details; int hashed_len, cur_opt; /* Now an optional 4th parameter specifying the cursor type * defaulting to the cursors default */ switch(ZEND_NUM_ARGS()) { case 3: if (zend_get_parameters_ex(3, pv_db, pv_uid, pv_pwd) == FAILURE) { WRONG_PARAM_COUNT; } /* Use Default: Probably a better way to do this */ cur_opt = SQL_CUR_DEFAULT; tag = ''; break; case 4: if (zend_get_parameters_ex(4, pv_db, pv_uid, pv_pwd, pv_opt) == FAILURE) { WRONG_PARAM_COUNT; } convert_to_long_ex(pv_opt); cur_opt = Z_LVAL_PP(pv_opt); /* Confirm the cur_opt range */ if (! (cur_opt == SQL_CUR_USE_IF_NEEDED || cur_opt == SQL_CUR_USE_ODBC || cur_opt == SQL_CUR_USE_DRIVER || cur_opt == SQL_CUR_DEFAULT) ) { php_error_docref(NULL TSRMLS_CC, E_WARNING, Invalid Cursor type (%d), cur_opt); RETURN_FALSE; } tag = ''; break; case 5: if (zend_get_parameters_ex(5, pv_db, pv_uid, pv_pwd, pv_opt, pv_tag) == FAILURE) { WRONG_PARAM_COUNT; } convert_to_long_ex(pv_opt); cur_opt = Z_LVAL_PP(pv_opt); /* Confirm the cur_opt range */ if (! (cur_opt == SQL_CUR_USE_IF_NEEDED || cur_opt == SQL_CUR_USE_ODBC || cur_opt == SQL_CUR_USE_DRIVER || cur_opt == SQL_CUR_DEFAULT) ) { php_error_docref(NULL TSRMLS_CC, E_WARNING, Invalid Cursor type (%d), cur_opt); RETURN_FALSE; } convert_to_string_ex(pv_tag); tag = Z_STRVAL_PP(pv_tag); break; default: WRONG_PARAM_COUNT; break; } convert_to_string_ex(pv_db); convert_to_string_ex(pv_uid); convert_to_string_ex(pv_pwd); db = Z_STRVAL_PP(pv_db); uid = Z_STRVAL_PP(pv_uid); pwd = Z_STRVAL_PP(pv_pwd); if (ODBCG(allow_persistent) = 0) { persistent = 0; } hashed_len = spprintf(hashed_details, 0, %s_%s_%s_%s_%d_%s, ODBC_TYPE, db, uid, pwd, cur_opt, tag); Gomar Bijl Software Engineer BU400 CAL Consult Phone +31 (0) 318 - 691 300 Fax +31 (0) 318 - 691 301
Re: [PHP-DEV] Re: Using Network functions.
Mangol Smith escribió: Hey guys, someone suggested me to have a look at libcURL. I did, but its very complex. All I needed is lowlevel/network wrappers. like emalloc() pemalloc() as wrapper on malloc(). There might be some wrappers (platform independent used in php source code) which I can use to make a connection and then send HTTP requests. use the api provided by either pecl_http or curl extension, you dont reaaly want to do it in a different way. also. evaluate if you realy want to write a C extension for that, proper userspace code should do the trick just fine. -- Perhaps, my biggest pet peeve pertaining to safe_mode is that it is not really safe, merely offering an illusion of safety that does not stand to closer examination - Ilia on PHP safe_mode Cristian Rodríguez R. Platform/OpenSUSE - Core Services SUSE LINUX Products GmbH Research Development http://www.opensuse.org/ signature.asc Description: OpenPGP digital signature
[PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
2008/6/26 Derick Rethans [EMAIL PROTECTED]: On Tue, 24 Jun 2008, Rasmus Lerdorf wrote: Derick Rethans wrote: On Tue, 24 Jun 2008, Alexey Zakhlestin wrote: it won't be a serious 'wtf', as on the top of the file, there would be some kind of use MySuperLibrary::DateTime; I know, but 400 lines down in the code you can't really see that. This addition might fix the immediate issue - but it doesn't make life easier for the developers that have to maintain the code. Even less if they're not aware that stuff is namespaced. If we don't allow it to work this way, then I really don't see the point in namespaces at all, which I assume is the point you are trying to make. Actually, the point that I was trying to make is that we instead of encouraging this confusion, we should put somewhere in our userland nameing guidelines that you still would need to provide a prefix to your (aliased) classnames in order to prevent confusion. But that then seriously means I see no real good reason still why people want namespaces with confusing resolving rules (concerning static methods like Greg points out). regards, Derick -- Derick Rethans http://derickrethans.nl | http://ezcomponents.org | http://xdebug.org -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php How bad would it be to say that namespacing can only apply to classes and not normal functions? So. class::static(); namespace::class::static(); namespace::namespace::class::static(); they always work. namespace::function() would fail as namespace would be seen as class. If a class and a namespace share the same name ... namespace::function() vs class:static()... how is anyone, let alone PHP, going to know. It can't. If both forms relate to a valid entity, then it is always a guess as to which is intended. You could make namespace:: have a higher precedence than class:: (or the other way around). But that feels like a fudge rather than a fix. So, maybe, in the short tem, namespacing only applies to classes. It was my understanding that one of the primary reasons for introducing namespacing was to protect against userland_class vs builtin_class collision. Regards, Richard Quadling. -- - Richard Quadling Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498r=213474731 Standing on the shoulders of some very clever giants!
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
Richard Quadling wrote: How bad would it be to say that namespacing can only apply to classes and not normal functions? i don't see namespacing as an OO only feature, IMHO it is a perfectly valid and useful thing for pure procedural code, too not having namespacing for procedural functions would leave the old ugly concept of bundling functions as static methods within dummy wrapper classes as only option for procedural name space emulation ... which AFAIR was one of the things we wanted to get rid of way back when the whole namespace idea first materialized? -- Hartmut Holzgraefe, MySQL Regional Support Manager EMEA Sun Microsystems GmbH, Sonnenallee 1, 85551 Kirchheim-Heimstetten Amtsgericht Muenchen: HRB161028 Geschaeftsfuehrer: Thomas Schroeder, Wolfgang Engels, Dr. Roland Boemer Vorsitzender des Aufsichtsrates: Martin Haering -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
2008/6/26 Hartmut Holzgraefe [EMAIL PROTECTED]: Richard Quadling wrote: How bad would it be to say that namespacing can only apply to classes and not normal functions? i don't see namespacing as an OO only feature, IMHO it is a perfectly valid and useful thing for pure procedural code, too not having namespacing for procedural functions would leave the old ugly concept of bundling functions as static methods within dummy wrapper classes as only option for procedural name space emulation ... which AFAIR was one of the things we wanted to get rid of way back when the whole namespace idea first materialized? Ok. I see your point and the idea of grouping related functionality into a dummy class full of statics does feel wrong when there is no other benefit, but from a userland code's perspective namespace::function() looks JUST like ugly_bundled_class::static() Internally, sure, they are completely different, but from a users perspective, they are the same thing. Same amount of typing. Same syntax. Nothing to differentiate. So the issue to namespace::function() vs class::static() remains. As I see it either precedence is the answer (user namespaces first, internal namespaces next and global namespace being last) or a different symbol for namespace. Maybe namespace:::function() vs class::static(). Would that be enough? Richard. -- - Richard Quadling Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498r=213474731 Standing on the shoulders of some very clever giants!
Re: [PHP-DEV] cleaning up the functions - any volunteers?
The attached patch may also help both core and PECL extensions, emiting a deprecation compile warning when those functions are used. A bit late to answer but very good idea :) -- Slan, David -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
How bad would it be to say that namespacing can only apply to classes and not normal functions? Lame, very lame. It would make them unusable for many distributed projects that are not 100% OOP. Wordpress comes to mind. My own Phorum as well. It was my understanding that one of the primary reasons for introducing namespacing was to protect against userland_class vs builtin_class collision. No, that is the OOP propaganda machine at work. Don't listen to the OOP machine. It lies. =) Brian. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
How bad would it be to say that namespacing can only apply to classes and not normal functions? Lame, very lame. It would make them unusable for many distributed projects that are not 100% OOP. Wordpress comes to mind. My own Phorum as well. I agree, namespaces need to work for all definition types. I don't see a problem here: 1) ns1::ns2::class::static() and ns1::ns2::namespace::func() is a collision 2) why is it a collision? because we have a class and subnamespace in the same namespace, with the same names. 3) solution therefore is to NOT allow this collision, and end with an error. [Example 1] namespace a::b::c; function foo() {} namespace a::b; class c {} // FATAL ERROR: class collision with existing namespace a::b::c [Example 2] namespace a::b; class c {} namespace a::b::c; // FATAL ERROR: namespace collision with existing class a::b::c function foo() {} So now, while the syntax may still be ambiguos if a codeline is cut and pasted alone in a blank text file, at least *in context* it can do only one thing: call whatever the user defined/imported/included. If there's a collision, he'll see the error, and take action. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
Hi Dmitry, I'm fine if you'll improve my patch (It's mainly yours :) I updated my closures RFC: http://wiki.php.net/rfc/closures I have based my new version of the patch on yours (Dmitry), but I made some changes to that: * Objects instead of resources are used, two new files zend_closures.[ch] are added where the new Closure class is defined. Currently, it contains a dummy __toString method that in future may be extended to provide enhanced debugging info, also further additional cool stuff could be added to such a class later on. But I prefer to only add the basic closure functionality at first - you can always extend it once it's there. * I have *not* added any __invoke() magic to normal objects. This is mainly due to the simple reason that adding that would not help a closure implementation at all. Closures need some engine internal magic (use a dynamically created op_array instead of looking one up, setting the correct class scope and setting the correct EG(this). And as I said: I want to stick with the closure basics for now. That said, I do like the possibility of invoking objects directly, so I suggest someone created an additional proposal for that? * I've added a patch for PHP HEAD (PHP 6.0). This is due to the fact that Dmitry's variant of my patch has far less intersections with the unicode functionality than my original patch, so it was quite straight-forward to do so. * Lexical vars are now copied instead of referenced by default. Using in front of the var, the behaviour may be changed. I added that in order to demonstrate that both was possible and that a simply change of grammar suffices. In my eyes this is the main issue where a discussion has to take place (i.e. copy or reference by default? possibility to change default via syntax? which lexical syntax?) before the proposal can be accepted. * I provided patches for both lexical $var and use ($var) syntaxes. * I provided a patch variant that only stores $this if $this is explicitely used inside a closure (or a nested closure of that closure). This works since it is possible to detect whether $this is used at compile time. For this, I have added a this_used flag to the op_array structure. * I added tests (Zend/tests/closures_*.phpt) that ensure the correct behaviour of closures. [Note that I created my own local SVN repos for developing these patches because I was fed up with CVS's inability to local diffs and locally mark files as added to include them in the diffs. Just to explain the format of the patch.] Anyway, feel free to discuss. In my eyes, the following questions should be answered: * Do you want closures in PHP? I have not seen a single negative reaction to my proposal, so I assume the answer to that is yes. ;-) * Which syntax should be used for lexical variables? Should references or copies be created by default? This is far trickier. First of all: There must *always* be the _possiblity_ to create references, else you can't call it closures. Second: I prefer the 'lexical' keyword, but I could live with the use solution [function () use ($...)]. Third: There are several arguments against default referencing: * (use syntax) As they look similar to parameters and normal parameters aren't passed by ref, this could be quite odd. * Loop index WTFs (see proposal) * Speed? (You always read that refs are slower in PHP than normal variable copies. Is that actually true?) * While it is possible to simply add an in front of the variable name to switch to refs in no refs default mode, there is no obvious syntax to use copies in refs default mode other than unsetting the variable in the parent scope immediately after closure creation. Fourth: There are several arguments for default referencing: * (lexical syntax) global also creates a reference, why shouldn't lexical? * Other languages *appear* to exhibit a very similar behaviour to PHP if PHP created references. This is due to the fact that other languages have a different concept of scope as PHP does. Although the list of against arguments appears to be longer, I do prefer using references by default nevertheless. But that's just my personal opinion. * Are you OK with the change that $this is only stored when needed? I don't see a problem. Dmitry seems to be very touchy (;-)) about changing op_arrays but in this case it's only a flag so I don't see a problem for opcode caches (in contrast to a HashTable where the opcode cache must actually add code to duplicate that table). * Do you want closures in PHP 5.3? Since the majority of core developers appear to be against it, I presume the answer is no. I will provide a revised patch that incorporates the results of
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
Hey all, honestly, it is not my intention to raise a new flamewar, but aren't most of these ambiguity problems we talk about due to the fact that :: is used as the namespace separator? Regards, Stefan -- e-novative - We make IT work for you. e-novative GmbH - HR: Amtsgericht München HRB 139407 Sitz: Wolfratshausen - GF: Dipl. Inform. Stefan Priebsch http://www.e-novative.de - GnuPG Key: 0x7DB67F7F -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] simple solution to another namespace conundrum?
I would agree, they seem to cause more problems and pollution than it would solve. I like the idea behind namespaces but what I've seen of the current implementations I would rather do without. Unfortunately I don't have any ideas or solutions to the problems. /James Dempster On Thu, Jun 26, 2008 at 8:38 AM, Derick Rethans [EMAIL PROTECTED] wrote: On Tue, 24 Jun 2008, Rasmus Lerdorf wrote: Derick Rethans wrote: On Tue, 24 Jun 2008, Alexey Zakhlestin wrote: it won't be a serious 'wtf', as on the top of the file, there would be some kind of use MySuperLibrary::DateTime; I know, but 400 lines down in the code you can't really see that. This addition might fix the immediate issue - but it doesn't make life easier for the developers that have to maintain the code. Even less if they're not aware that stuff is namespaced. If we don't allow it to work this way, then I really don't see the point in namespaces at all, which I assume is the point you are trying to make. Actually, the point that I was trying to make is that we instead of encouraging this confusion, we should put somewhere in our userland nameing guidelines that you still would need to provide a prefix to your (aliased) classnames in order to prevent confusion. But that then seriously means I see no real good reason still why people want namespaces with confusing resolving rules (concerning static methods like Greg points out). regards, Derick -- Derick Rethans http://derickrethans.nl | http://ezcomponents.org | http://xdebug.org -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] Using Network functions.
Hi! 2. What does streams has to do with this networking? Can it be done using streams? Yes, it can. Take the following simple, incomplete example without much error handling as a starting point: // in the header #include php_streams.h // PHP function: PHP_FUNCTION(simplehttp_fetch) { php_stream *stream; struct timeval tv; int err; char *errstr; char buf[8192]; tv.tv_sec = 30; tv.tv_usec = 0; stream = php_stream_xport_create(tcp://www.google.com:80, sizeof(tcp://www.google.com:80)-1, ENFORCE_SAFE_MODE | REPORT_ERRORS, TREAM_XPORT_CLIENT | STREAM_XPORT_CONNECT, NULL, tv, NULL, errstr, err); if (stream == NULL) { php_error(E_WARNING TSRMLS_CC, unable to connect to tcp://www.google.com:80: %s, errstr == NULL ? unknown error : errstr); RETURN_NULL(); } php_stream_write(stream, GET / HTTP/1.0\r\nHost: www.google.com\r\n\r\n, sizeof(GET / HTTP/1.0\r\nHost: www.google.com\r\n\r\n)-1); memset(buf, 0, 8192); php_stream_read(stream, buf, 8191); php_stream_close(stream); RETURN_STRING(buf, 1); } Basically, you want to look at main/php_streams.h and main/streams/php_stream_transport.h in the PHP source code. Userland fsockopen() essentially maps to php_stream_xport_create() and userland fread, fwrite, close, etc. essentially map to php_stream_read(), php_stream_write, php_stream_close, etc. Regards, Christian -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
2008/6/26 Stefan Priebsch [EMAIL PROTECTED]: Hey all, honestly, it is not my intention to raise a new flamewar, but aren't most of these ambiguity problems we talk about due to the fact that :: is used as the namespace separator? Regards, Stefan I think so. Considering this _IS_ a new facility I can't see why having 3 :'s wouldn't be a good solution. namespace:::class::static() namespace:::function() No confusion. Clearly defined. No collision. -- e-novative - We make IT work for you. e-novative GmbH - HR: Amtsgericht München HRB 139407 Sitz: Wolfratshausen - GF: Dipl. Inform. Stefan Priebsch http://www.e-novative.de - GnuPG Key: 0x7DB67F7F -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- - Richard Quadling Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498r=213474731 Standing on the shoulders of some very clever giants!
Re: [PHP-DEV] How bad would it be to say/enforce that namespacing can only apply to classes and not normal functions?
No confusion. Clearly defined. No collision. ... except possibly between the eyes... We had this discussion ad infinitum in the past. Please, not again? - Steph -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
Hello Christian, Thursday, June 26, 2008, 6:23:53 PM, you wrote: Hi Dmitry, I'm fine if you'll improve my patch (It's mainly yours :) I updated my closures RFC: http://wiki.php.net/rfc/closures I have based my new version of the patch on yours (Dmitry), but I made some changes to that: * Objects instead of resources are used, two new files zend_closures.[ch] are added where the new Closure class is defined. Currently, it contains a dummy __toString method that in future may be extended to provide enhanced debugging info, also further additional cool stuff could be added to such a class later on. But I prefer to only add the basic closure functionality at first - you can always extend it once it's there. * I have *not* added any __invoke() magic to normal objects. This is mainly due to the simple reason that adding that would not help a closure implementation at all. Closures need some engine internal magic (use a dynamically created op_array instead of looking one up, setting the correct class scope and setting the correct EG(this). And as I said: I want to stick with the closure basics for now. That said, I do like the possibility of invoking objects directly, so I suggest someone created an additional proposal for that? * I've added a patch for PHP HEAD (PHP 6.0). This is due to the fact that Dmitry's variant of my patch has far less intersections with the unicode functionality than my original patch, so it was quite straight-forward to do so. * Lexical vars are now copied instead of referenced by default. Using in front of the var, the behaviour may be changed. I added that in order to demonstrate that both was possible and that a simply change of grammar suffices. In my eyes this is the main issue where a discussion has to take place (i.e. copy or reference by default? possibility to change default via syntax? which lexical syntax?) before the proposal can be accepted. * I provided patches for both lexical $var and use ($var) syntaxes. * I provided a patch variant that only stores $this if $this is explicitely used inside a closure (or a nested closure of that closure). This works since it is possible to detect whether $this is used at compile time. For this, I have added a this_used flag to the op_array structure. * I added tests (Zend/tests/closures_*.phpt) that ensure the correct behaviour of closures. [Note that I created my own local SVN repos for developing these patches because I was fed up with CVS's inability to local diffs and locally mark files as added to include them in the diffs. Just to explain the format of the patch.] Anyway, feel free to discuss. In my eyes, the following questions should be answered: * Do you want closures in PHP? I have not seen a single negative reaction to my proposal, so I assume the answer to that is yes. ;-) yes * Which syntax should be used for lexical variables? Should references or copies be created by default? This is far trickier. First of all: There must *always* be the _possiblity_ to create references, else you can't call it closures. Second: I prefer the 'lexical' keyword, but I could live with the use solution [function () use ($...)]. 'use' becasue no new keyword has to be introduced which would brake stuff no matter what the keyword will be. Third: There are several arguments against default referencing: * (use syntax) As they look similar to parameters and normal parameters aren't passed by ref, this could be quite odd. * Loop index WTFs (see proposal) * Speed? (You always read that refs are slower in PHP than normal variable copies. Is that actually true?) * While it is possible to simply add an in front of the variable name to switch to refs in no refs default mode, there is no obvious syntax to use copies in refs default mode other than unsetting the variable in the parent scope immediately after closure creation. I like the new ability to reference if wanted. But then I don't like references at all. Along with the fact that in PHP objects are always references I slightly tend to not want reference functionality. Since it is handled in the parser you could submit with either version and check during evaluation periode if people disagree with your choice - or the list choice if that's what decides. Fourth: There are several arguments for default referencing: * (lexical syntax) global also creates a reference, why shouldn't lexical? * Other languages *appear* to exhibit a very similar behaviour to PHP if PHP created references. This is due to the fact that other languages have a different concept of scope as PHP
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
Hello Sebastian, ok, even though I just wrote differently. It appears to me, after reading the rest of the thread, that I shouuld maybe give in and favor a 5.4 instead. marcus Wednesday, June 25, 2008, 10:42:50 AM, you wrote: Lukas Kahwe Smith wrote: I am very sure we will see a 5.4. There is also the traits patch that is more or less ready And the switch from bison to lemon is also on the agenda for PHP 5.4. -- Sebastian Bergmann http://sebastian-bergmann.de/ GnuPG Key: 0xB85B5D69 / 27A7 2B14 09E4 98CD 6277 0E5B 6867 C514 B85B 5D69 Best regards, Marcus -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
* I added tests (Zend/tests/closures_*.phpt) that ensure the correct behaviour of closures. I'd like to propose an additional test to ensure closures can all themselves: ?php $i = 3; $lambda = function ($lambda) use ($i) { if ($i==0) return; echo $i--.\n; $lambda($lambda); }; $lambda($lambda); echo $i\n; ? Expected output: 3 2 1 3 I see exactly one problem with the patch, which is that the above script shouldn't work without use ($i). I find it counterintuitive that the creation of the lambda creates a copy of $i, but all invocations of $lambda use a reference to the same $i. For n calls to $lambda, there are only 2 copies of $i (one global, one static in $lambda) where I would expect n+1 copies. Gesundheit Wag -- Sieh dich, nimm Sorge. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
Hi Marcus, I like the new ability to reference if wanted. But then I don't like references at all. As I said: Without reference support, you can't call it closures. Closures must per definition have the possibility to change the values of used variables in the parent scope - and the only sensible PHP way to do that is references. If people here say: We want copy as default and references optional, that's fine with me since real closures can still be achieved and - let's face it - since PHP wasn't designed with closures in mind, the syntax will always be not 100% perfect, regardsless of how we'll do it. But I'm stronly against removing reference support entirely. * Are you OK with the change that $this is only stored when needed? I don't see a problem. Dmitry seems to be very touchy (;-)) about changing op_arrays but in this case it's only a flag so I don't see a problem for opcode caches (in contrast to a HashTable where the opcode cache must actually add code to duplicate that table). I see it dangerous eval comes to mind. Certain things don't work anyway as of now, see bug http://bugs.php.net/bug.php?id=43163 for example... And that's intended behaviour. Ok, eval() inside a closure still is a possible problem but we still could say ok, as soon as eval() appears, just assume $this is used. That will benefit those people who use neither $this nor eval() inside a closure with an optimization ($this will be GCed and not copied). And as far as I can see, eval() is the only thing you can do inside a normal class method that will allow you to access $this without the compiler knowing about it. But thanks for pointing eval out, I hadn't thought of that. And also, why create something special when the normal way of doing things that is done everywhere else would work too. What do you mean by that? Comments on the first patch version: - col, I am the listed author: Zend/zend_closures.c/h Oh, yeah, I just copied some header I found elsewhere. Should I put my name there or what's the policy for contributions? - you shouldn't be having a __destruct. Can you prevent that? But if I don't have a destructor, how do I garbage collect the op_array? - please drop __toString, with the new behavior only stuff that has something to say in a string context should have a __toString Somebody on the internals list suggested adding it to print out useful debugging info. But I'm fine with dropping it until there is actually a useful implementation. - a tiny optimization: +ZEND_API zend_closure *zend_get_closure(zval *obj TSRMLS_DC) /* {{{ */ +{ + zend_class_entry *ce = Z_OBJCE_P(obj); + if (instanceof_function(ce, zend_ce_closure TSRMLS_CC)) { + zend_closure *closure = (zend_closure *)zend_object_store_get_object(obj); + if (closure-initialized) return closure; + } + return NULL; +} Yes, good idea. - a faster way would be to: a) add a new type (probably not so good though) b) add a new ce_flag +#define ZEND_ACC_CLOSURE ... I'm quite indifferent to that change. On the one hand, it's a performance optimization, on the other hand, it digs deeper into current Zend code. - maybe even inline this function? Yes, good idea. As stated before, I'll keep all changes in mind and post and updated patch as soon as the discussion is done. Regards, Christian -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
Hi! I see exactly one problem with the patch, which is that the above script shouldn't work without use ($i). I find it counterintuitive that the creation of the lambda creates a copy of $i, but all invocations of $lambda use a reference to the same $i. For n calls to $lambda, there are only 2 copies of $i (one global, one static in $lambda) where I would expect n+1 copies. Yes, you're right. My solution for this would be: -- zend_compile.h - -void zend_do_fetch_static_variable(znode *varname, znode *static_assignment, int fetch_type TSRMLS_DC); +void zend_do_fetch_static_variable(znode *varname, znode *static_assignment, int fetch_type, int as_ref TSRMLS_DC); -- zend_compile.h - -- zend_compile.c - # in zend_do_fetch_lexical_variable: -zend_do_fetch_static_variable(varname, value, ZEND_FETCH_STATIC TSRMLS_CC); +zend_do_fetch_static_variable(varname, value, ZEND_FETCH_STATIC, is_ref TSRMLS_CC); ... -void zend_do_fetch_static_variable(znode *varname, znode *static_assignment, int fetch_type TSRMLS_DC) +void zend_do_fetch_static_variable(znode *varname, znode *static_assignment, int fetch_type, int as_ref TSRMLS_DC) ... - zend_do_assign_ref(NULL, lval, result TSRMLS_CC); + if (as_ref) { + zend_do_assign_ref(NULL, lval, result TSRMLS_CC); + } else { + zend_do_assign(NULL, lval, result TSRMLS_CC); + } # and make sure zend_do_assign can live with NULL for first param -- zend_compile.c - -- zend_language_parser.y - static_var_list: - static_var_list ',' T_VARIABLE { zend_do_fetch_static_variable($3, NULL, ZEND_FETCH_STATIC TSRMLS_CC); } - | static_var_list ',' T_VARIABLE '=' static_scalar { zend_do_fetch_static_variable($3, $5, ZEND_FETCH_STATIC TSRMLS_CC); } - | T_VARIABLE { zend_do_fetch_static_variable($1, NULL, ZEND_FETCH_STATIC TSRMLS_CC); } - | T_VARIABLE '=' static_scalar { zend_do_fetch_static_variable($1, $3, ZEND_FETCH_STATIC TSRMLS_CC); } + static_var_list ',' T_VARIABLE { zend_do_fetch_static_variable($3, NULL, ZEND_FETCH_STATIC, 1 TSRMLS_CC); } + | static_var_list ',' T_VARIABLE '=' static_scalar { zend_do_fetch_static_variable($3, $5, ZEND_FETCH_STATIC, 1 TSRMLS_CC); } + | T_VARIABLE { zend_do_fetch_static_variable($1, NULL, ZEND_FETCH_STATIC, 1 TSRMLS_CC); } + | T_VARIABLE '=' static_scalar { zend_do_fetch_static_variable($1, $3, ZEND_FETCH_STATIC, 1 TSRMLS_CC); } ; -- zend_language_parser.y - Any objections (in case copies are wanted at all)? Regards, Christian -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] Drop ext/mhash and add an emulation layer in ext/hash (5.3+), call for help
Pierre Joye wrote: On Mon, Jun 2, 2008 at 12:34 PM, Scott MacVicar [EMAIL PROTECTED] wrote: Pierre Joye wrote: On Mon, Jun 2, 2008 at 10:21 AM, Derick Rethans [EMAIL PROTECTED] wrote: On Mon, 2 Jun 2008, Pierre Joye wrote: While working on the windows ports, I asked Sara about the mhash status in regard of the new shiny ext/hash. The plan is to remove ext/hash completely and emulate it in ext/hash to keep the BC. It could even a configuration flag if one likes to be sure to clean his code to use only the hash APIs. The mhash extension features some more versions of some algorithms: http://mhash.sourceforge.net/ But why bother changing it? Which algo(s) (or algo version) is not supported by ext/hash? I did not spot one after a quick read. sha192 and sha224 snefru128 md2 I've not heard of any issues about ext/mhash. My main reasons would be to do not have to maintain ext/mhash and the libmhash Windows port. Cheers, I'm happy to see us removing a dependency, especially if it makes thigns easier to build on Windows. In case someone likes to do it, Scott has volunteered and has already added some of the missing algo in hash. He will also add the BC layer. Cheers, ext/mhash now wraps around ext/hash in 5.3 I'd like to recommend we add a E_DEPRECATED to anything mhash_* related and drop the extension for 6? I'll add the BC layer tomorrow to 6.0 regardless. Scott -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] [PATCH] [RFC] Closures and lambda functions in PHP
On Thursday 26 June 2008 11:23:53 am Christian Seiler wrote: Hi Dmitry, I'm fine if you'll improve my patch (It's mainly yours :) I updated my closures RFC: http://wiki.php.net/rfc/closures In my eyes, the following questions should be answered: * Do you want closures in PHP? I have not seen a single negative reaction to my proposal, so I assume the answer to that is yes. ;-) Yea. :-) * Which syntax should be used for lexical variables? Should references or copies be created by default? This is far trickier. First of all: There must *always* be the _possiblity_ to create references, else you can't call it closures. Second: I prefer the 'lexical' keyword, but I could live with the use solution [function () use ($...)]. Third: There are several arguments against default referencing: * (use syntax) As they look similar to parameters and normal parameters aren't passed by ref, this could be quite odd. * Loop index WTFs (see proposal) * Speed? (You always read that refs are slower in PHP than normal variable copies. Is that actually true?) * While it is possible to simply add an in front of the variable name to switch to refs in no refs default mode, there is no obvious syntax to use copies in refs default mode other than unsetting the variable in the parent scope immediately after closure creation. Fourth: There are several arguments for default referencing: * (lexical syntax) global also creates a reference, why shouldn't lexical? * Other languages *appear* to exhibit a very similar behaviour to PHP if PHP created references. This is due to the fact that other languages have a different concept of scope as PHP does. Although the list of against arguments appears to be longer, I do prefer using references by default nevertheless. But that's just my personal opinion. I see these two issues as related, actually. Consider: $foo = function($a, $b) { global $c; lexical $d; // ... } Since they look the same, you'd expect them to behave the same. However, global will import by reference and lexical by value. Hilarity ensues, and not the good kind. Naturally changing the behavior of global in this case is out of the question, and as you point out defaulting to reference and having an extra flag (a la ) to force it to value is unprecedented. I think most seem to agree that being able to pass by value or by reference at the developer's discretion is necessary. However, something in the function signature itself would naturally follow the behavior of function arguments: $foo = function($a, $b) lexical ($d, $e) { global $c; // ... } Here, $d and $e behave as you'd expect them to, with the same visual parsing semantics as $a and $b. That to me is a much lower wtf factor than having global and lexical keywords that look alike but behave differently. I would therefore favor the signature-based syntax. As an aside, I did use lexical in the second example above deliberately. Personally I don't think re-using use here is wise, as that will make it seem namespace related when in fact it is not. I suspect the instances of function or constant names of lexical will be pretty minimal (although I admit to having no evidence to back up that suspicion.) (I would much much rather have a closures implementation that used use than not one at all, mind you; I will still jump for joy if it lands using use, I just think it would be better using lexical.) * Are you OK with the change that $this is only stored when needed? Ignoring the compiler-level concerns, about which I know nothing useful, doesn't this introduce a bit of wtf? All lexically-imported variables must be explicit or they don't exist... oh yeah, except for $this because it's special. To which the question is: If you are able to magically determine if $this is used and optimize accordingly, why can't you for anything else? To which the response is, I think: Performance. That's still something of an inconsistency, however. Would it make the engine code any cleaner/messier if $this was required to be declared explicitly like everything else? * Do you want closures in PHP 5.3? As a PHP developer I'd love to have closures in 2 years when I'm able to use PHP 5.3 instead of 5 years when I'm able to use PHP 5.4 or PHP 6. :-) I do understand the need to draw a line somewhere and justbloodyshipit(tm), however, so if that's the decision I can accept that. Regards, Christian You so rock. :-) -- Larry Garfield [EMAIL PROTECTED] -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php