PHP Injection after hacker attack

We are huge fans of Elgg, and we used to use it with our Cooperative Social Network called Coolmeia.

We suffer a hacker attack and now several (most of) .php files are with some sort of code injected:

http://net.coolmeia.org/groups/profile/805/horta-coletiva/

Is there a fast or efficient way to get rid of it to put website online again (after changing ftp/cpanel/etc passwords)

  • Got that. Now the error goes to line 69: Fatal error: Call to undefined function widget_manager_sort_widgets()

    Here is the: 
    "/home/coolmeia/public_html/net/mod/widget_manager/views/default/page/layouts/widgets/add_panel.php"

     

    <?php
    elgg_load_js('lightbox');
    elgg_load_css('lightbox');

    $context = $vars["context"];

    if($md_guid = get_input("multi_dashboard_guid")){
        $params = array(
                    'name' => 'widget_context',
                    'value' => $context . "_" . $md_guid
        );
    } else {
        $params = array(
                'name' => 'widget_context',
                'value' => $context
        );
    }
    echo elgg_view('input/hidden', $params);

    ?>
    <script type="text/javascript">

        $(document).ready(function(){
            $("#widgets-add-panel").fancybox({ 
                autoDimensions: false, 
                width: 600, 
                height: "80%"
            });    
        });

        function widget_manager_widget_add_init(){
            
            $("#elgg-widget-col-1").ajaxSuccess(function(e, xhr, settings) {
                
                if (settings.url == elgg.normalize_url('/action/widgets/add')) {
                    // move new widget to a new position if needed
                    if($(this).find('.elgg-state-fixed').size() > 0){
                        $widget = $(this).find('.elgg-module-widget:first');
                        $widget.insertAfter($(this).find('.elgg-state-fixed:last'));
                        
                        // first item is the recently moved widget, because fixed widgets are not part of the sortable
                        var index = $(this).find('.elgg-module-widget').index($widget);
                        var guidString = $widget.attr('id');
                        guidString = guidString.substr(guidString.indexOf('elgg-widget-') + "elgg-widget-".length);

                        elgg.action('widgets/move', {
                            data: {
                                widget_guid: guidString,
                                column: 1,
                                position: index
                            }
                        });
                        
                    }
                }
            });
        }

        elgg.register_hook_handler('init', 'system', widget_manager_widget_add_init);

    </script>
    <?php 
        
        $widget_context = str_replace("default_", "", $context);
        
        $available_widgets_context = elgg_trigger_plugin_hook("available_widgets_context", "widget_manager", array(), $widget_context);
        
        $widgets = elgg_get_widget_types($available_widgets_context, $vars["exact_match"]);
        widget_manager_sort_widgets($widgets);

        $current_handlers = array();
        if(!empty($vars["widgets"])){
            // check for already used widgets
            foreach ($vars["widgets"] as $column_widgets) {
                // foreach column
                foreach ($column_widgets as $widget) {
                    // for each widgets
                    $current_handlers[] = $widget->handler;
                }
            }
        }
        
        $title = "<div id='widget_manager_widgets_search'>";
        $title .= "<input title='" . elgg_echo("search") . "' type='text' value='" . elgg_echo("search") . "' onfocus='if($(this).val() == \"" . elgg_echo("search") .  "\"){ $(this).val(\"\"); }' onkeyup='widget_manager_widgets_search($(this).val());'></input>";
        $title .= "</div>";
        $title .= elgg_echo("widget_manager:widgets:lightbox:title:" . $context);
        
        $body = "";
        if(!empty($widgets)){
            
            foreach($widgets as $handler => $widget){
                $can_add = widget_manager_get_widget_setting($handler, "can_add", $widget_context);
                $allow_multiple = $widget->multiple;
                $hide = widget_manager_get_widget_setting($handler, "hide", $widget_context);
                
                if($can_add && !$hide){
                    $body .= "<div class='widget_manager_widgets_lightbox_wrapper'>";
                    
                    if(!$allow_multiple && in_array($handler, $current_handlers)){
                        $class = 'elgg-state-unavailable';
                    } else {
                        $class = 'elgg-state-available';
                    } 
                    
                    if ($allow_multiple) {
                        $class .= ' elgg-widget-multiple';
                    } else {
                        $class .= ' elgg-widget-single';
                    }
                    
                    $body .= "<span class='widget_manager_widgets_lightbox_actions'>";
                    $body .= '<ul><li class="' . $class . '" id="elgg-widget-type-'. $handler . '">';
                    $body .= "<span class='elgg-quiet'>" . elgg_echo('widget:unavailable') . "</span>";
                    $body .= elgg_view("input/button", array("class" => "elgg-button-submit", "value" => elgg_echo("widget_manager:button:add")));
                    $body .= "</li></ul>";
                    $body .= "</span>";
                    
                    $description = $widget->description;
                    if(empty($description)){
                        $description = "&nbsp;"; // need to fill up for correct layout
                    }
                    
                    $body .= "<div><b>" . $widget->name . "</b></div>";
                    $body .= "<div class='elgg-quiet'>" . $description . "</div>";
                    
                    $body .= "</div>";
                }
            }        
        } else {
            $body = elgg_echo("notfound");
        }
        
        $module_type = "info";
        if(elgg_in_context("admin")){
            $module_type = "inline";
        } 

        echo "<div class='elgg-widgets-add-panel hidden'>" . elgg_view_module($module_type, $title, $body, array("id" => "widget_manager_widgets_select")) . "</div>";

  • Make sure you have not deleted/removed the function widget_manager_sort_widgets() defined in lib/functions.php file of the plugin while editing.

  • So, has it been a hacker attack at all or are the problems either due to bugs in plugins or faulty server config or both?

    Code analysis / comparison from the elgg install directory with a clean and freshly created install directory where you also add all the 3rd party plugins (unmodified) can help to find out both what files might have changed by someone else and what changed you have done yourself in the past. Do the comparison locally with some diff / dirdiff tool and you should get a good overview what files differ at all.

    If you don't see any strange modifications made in the code I would say the reason for the problem is not a hacker but just some buggy installation. If it has been really a hacker then you would not only need to reinstall Elgg but also the complete server to make sure there are no open backdoors. But if there are no indications that a hacker has been on the server you might better start with clean and unmodified files of Elgg and all additional plugins nevertheless and then disable all 3rd party plugins for the start and only enable then one by one again while fixing any issues showing up due to this plugin alone before trying it wil many plugins that might have issues you had previously fixed because then you would have been a hard time already locating the faulty code.

  • It happened an the same time in subdomains like salsinha.coolmeia.org that run Wordpress, so it seems that is not something to do with Elgg alone, but with whole php based services on the directory /home/coolmeia/

    As I run several other sites in /home/abc and /home/def etc. and they got spared, i think it was a directed attack - because we announced (in the main domain from /home/coolmeia/ 2 day earlier that we would provide free internet streaming to libertary radios. 

    I'll share your insights with the developers and return soon with more news. We appreciate your help!

  • Who are you hosting with? I'm gonna assume your host might've changed some upper level settings.

  • We host with Micfo.com. Will double check with them.

  • "Code analysis / comparison from the elgg install directory with a clean and freshly created install directory where you also add all the 3rd party plugins (unmodified) can help to find out both what files might have changed by someone else and what changed you have done yourself in the past. Do the comparison locally with some diff / dirdiff tool and you should get a good overview what files differ at all."

    Thanks for this iionly. This is the actual step we are doing.