Normal userspace variables (zvals) are allocated "non-persistently". This means that, for example, creating a string variable consists of emalloc() calls:

foo = emalloc(sizeof(zval));
foo->value.str.val = emalloc(sizeof("bar"));

emalloc()'d pointers are forcibly freed between requests (as part of Zend's garbage collection), so even though you've taken care of all the other bits or placing the zval* into your map in regards to reference counting and creating a true copy, the zval itself is allocated non-persistently and will be quietly killed by the engine at the end of your request. (Well, no so quietly if you have --enable-debug turned on).

So that means that all the zval * I store in my map simply point to invalid memory once the request is completed? Well, that would explain some of the strange behaviour I have observed (such as string changing content between requests). The solution to this would be to allocate the zval struct using pemalloc and allocate memory for the data the zval (whatever type it is) uses with pemalloc as well?


In order to hold a zval between requests you'll have to make a persistent copy of it (using pemalloc() which, I'm afraid, is a bit more complicated than it sounds). Take a look at apc_store() and apc_fetch() which do...well....pretty much what you're talking about here.

As far as I can tell, the APC extension doesn't use pemalloc but rather malloc. Furthermore, pemalloc simply seems to be a macro which uses malloc to allocate memory. This means that my memory allocations using c++ new should allocate persistent memory chunks. So the persistent/non-persistent memory issue doesn't explain why my std::map simply is empty. The fact that it contain zval pointers pointing to invalid memory I understand but I don't get why it gets emptied. Any ideas?

Best regards
David Olsson

-- 
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to