After releasing to the live server, the cron wouldn't index the documents anymore.
The cron would just die without leaving a message in the error logs.
I found that line 387 in apachesolr.module triggered a signal 11 (SIGSEGV) error in PHP 5.2.0-8+etch16.
PHP version 5.2.6-1+lenny4 (and higher) don't seem to suffer from this issue.
Backtrace: (sorry no php debug info)
Program terminated with signal 11, Segmentation fault.
#0 0x082beb03 in zend_object_store_get_object ()
(gdb) bt
#0 0x082beb03 in zend_object_store_get_object ()
#1 0x082bb75d in zend_objects_get_address ()
#2 0x082bcc60 in zend_std_read_property ()
#3 0x082f5ba4 in zend_get_zval_ptr_ptr ()
#4 0x082c0c88 in execute ()
#5 0x082d0c71 in execute ()
#6 0x082c0c88 in execute ()
#7 0x08297894 in zend_call_function ()
#8 0x082989da in call_user_function_ex ()
#9 0x081de97e in zif_call_user_func_array ()
#10 0x082d128f in execute ()
#11 0x082c0c88 in execute ()
#12 0x082d0c71 in execute ()
#13 0x082c0c88 in execute ()
#14 0x082d0c71 in execute ()
#15 0x082c0c88 in execute ()
#16 0x082a1e5c in zend_execute_scripts ()
#17 0x0825d0c2 in php_execute_script ()
#18 0x08330ffe in main ()
Since the backtrace mentions the zend_object_store_get_object, the array_walk_recursive function is called and the array on which this function is called contains objects, I figured that rewriting this line of code might solve the problem and it did!
I've attached my patch, but it need reviews because I didn't completely follow why the flattening of the array was called like this. See code below.
Questions I have are:
- Why is the temp data added to an object containing an array and not just an array?
- Is it even possible that the document array contains nested arrays? If not the code is redundant anyway.
code after patch:
// line 385
/**
* Old code triggers signal 11 (SIGSEGV) in PHP 5.2.0-8+etch16.
*/
// $tmp = (object) array('a' => array());
// array_walk_recursive($documents, create_function('&$v, $k, &$t', '$t->a[] = $v;'), $tmp);
// $documents = $tmp->a;
// Flatten $documents
$tmp = array();
apachesolr_flatten_documents_array($documents, &$tmp);
$documents = $tmp;
[...]
// line 431
/**
* Function to flatten documents array recursively.
* @param array $documents The documents array.
* @param array $tmp The placeholder for the flat array.
*/
function apachesolr_flatten_documents_array($documents, &$tmp) {
foreach ($documents AS $index => $item) {
if (is_array($item)) {
apachesolr_flatten_documents_array($item, $tmp);
}
else {
$tmp[] = $item;
}
}
}
| Comment | File | Size | Author |
|---|---|---|---|
| #7 | apachesolr_719356.patch | 377 bytes | drewish |
| #4 | flatten.patch | 1.46 KB | robertdouglass |
| #3 | flatten.patch | 1.46 KB | robertdouglass |
| #1 | apachesolr-719356.patch | 1.29 KB | mathieu |
Comments
Comment #1
mathieu commentedI had the same issue (segfault) and this patch fixed the issue. I'm attaching a patch file with the code above.
Comment #2
flk commentedI can confirm this resolves my issue mentioned #711666: apachesolr_search failing to index on cron.php or batch index which is very much same as the original poster mentioned (same php ver.) and now data is being indexed :)
Thanks.
Comment #3
robertdouglass commentedSlight adjustment to comments.
Comment #4
robertdouglass commentedWhitespace.
Comment #5
robertdouglass commentedThanks!
#719356 by robertDouglass, mathieu | flk: Fixed Indexing cron triggers sigsegv in apachesolr.module line 387.
Comment #6
comat0se commentedThis seems to cause this error:
PHP Warning: Call-time pass-by-reference has been deprecated in sites/all/modules/apachesolr/apachesolr.module on line 380
which is this line: apachesolr_flatten_documents_array($documents, &$tmp);
I think this was a problem that was patched in the past?
Comment #7
drewish commentedThe patch on comment #4 just needs a minor tweak. We can drop the ampersand before $tmp.
Comment #8
robertdouglass commentedYeah, I removed the ampersand in a followup issue.
Comment #9
robertdouglass commented