In doing work on a website I don’t often touch, I wanted to verify none of the modules had been hacked. A golden rule of Drupal is “Don’t hack Core!” (or community modules!). I wanted to scan my site for problems. Luckily I found the Hacked module.
Upon enabling the hacked module with drush en hacked -y. The Hacked module fetches local copies of all installed modules, at exactly the same version your site is using, in-use on your website and Diffs the remote copy with the copy in-use on your site. The Hacked module gives us 3 commands hacked-list-projects, hacked-details and hacked-diff.
This process for a full website looks like:
$> drush en hacked The following extensions will be enabled: hacked Do you really want to continue? (y/n): y hacked was enabled successfully. [ok] hacked defines the following permissions: view diffs of changed files $> drush hacked-list-projects Rebuilding Hacked! report Finished processing: Admin [ok] Finished processing: Automatic Entity Label [ok] Finished processing: Backup and Migrate [ok] Finished processing: Bean [ok] Finished processing: Drupal core [ok] Finished processing: Colorbox [ok] Finished processing: Field formatter for colorbox module [ok] Finished processing: Conditional Fields [ok] Finished processing: Context [ok] Finished processing: Chaos tool suite (ctools) [ok] Finished processing: Date [ok] Finished processing: Devel [ok] Finished processing: Diff [ok] WD hacked: Could not download project: eap_academics [error] WD hacked: Could not hash remote project: eap_academics [error] WD hacked: Could not download project: eap_academics [error] WD hacked: Could not hash remote project: eap_academics [error] WD hacked: Could not hash local project: eap_academics [error] Finished processing: eap_academics [ok] WD hacked: Could not download project: eap_alumni [error] WD hacked: Could not hash remote project: eap_alumni [error] WD hacked: Could not download project: eap_alumni [error] WD hacked: Could not hash remote project: eap_alumni [error] WD hacked: Could not hash local project: eap_alumni [error] Finished processing: eap_alumni [ok] WD hacked: Could not download project: eap_feedback_banking [error] WD hacked: Could not hash remote project: eap_feedback_banking [error] WD hacked: Could not download project: eap_feedback_banking [error] WD hacked: Could not hash remote project: eap_feedback_banking [error] WD hacked: Could not hash local project: eap_feedback_banking [error] Finished processing: eap_feedback_banking [ok] WD hacked: Could not download project: eap_feedback_communication [error] WD hacked: Could not hash remote project: eap_feedback_communication [error] WD hacked: Could not download project: eap_feedback_communication [error] WD hacked: Could not hash remote project: eap_feedback_communication [error] WD hacked: Could not hash local project: eap_feedback_communication [error] Finished processing: eap_feedback_communication [ok] WD hacked: Could not download project: eap_feedback_courses [error] WD hacked: Could not hash remote project: eap_feedback_courses [error] WD hacked: Could not download project: eap_feedback_courses [error] WD hacked: Could not hash remote project: eap_feedback_courses [error] WD hacked: Could not hash local project: eap_feedback_courses [error] Finished processing: eap_feedback_courses [ok] WD hacked: Could not download project: eap_feedback_culture [error] WD hacked: Could not hash remote project: eap_feedback_culture [error] WD hacked: Could not download project: eap_feedback_culture [error] WD hacked: Could not hash remote project: eap_feedback_culture [error] WD hacked: Could not hash local project: eap_feedback_culture [error] Finished processing: eap_feedback_culture [ok] WD hacked: Could not download project: eap_feedback_food [error] WD hacked: Could not hash remote project: eap_feedback_food [error] WD hacked: Could not download project: eap_feedback_food [error] WD hacked: Could not hash remote project: eap_feedback_food [error] WD hacked: Could not hash local project: eap_feedback_food [error] Finished processing: eap_feedback_food [ok] WD hacked: Could not download project: eap_feedback_host_city [error] WD hacked: Could not hash remote project: eap_feedback_host_city [error] WD hacked: Could not download project: eap_feedback_host_city [error] WD hacked: Could not hash remote project: eap_feedback_host_city [error] WD hacked: Could not hash local project: eap_feedback_host_city [error] Finished processing: eap_feedback_host_city [ok] WD hacked: Could not download project: eap_feedback_host_university [error] WD hacked: Could not hash remote project: eap_feedback_host_university [error] WD hacked: Could not download project: eap_feedback_host_university [error] WD hacked: Could not hash remote project: eap_feedback_host_university [error] WD hacked: Could not hash local project: eap_feedback_host_university [error] Finished processing: eap_feedback_host_university [ok] WD hacked: Could not download project: eap_feedback_housing [error] WD hacked: Could not hash remote project: eap_feedback_housing [error] WD hacked: Could not download project: eap_feedback_housing [error] WD hacked: Could not hash remote project: eap_feedback_housing [error] WD hacked: Could not hash local project: eap_feedback_housing [error] Finished processing: eap_feedback_housing [ok] WD hacked: Could not download project: eap_feedback_instructor [error] WD hacked: Could not hash remote project: eap_feedback_instructor [error] WD hacked: Could not download project: eap_feedback_instructor [error] WD hacked: Could not hash remote project: eap_feedback_instructor [error] WD hacked: Could not hash local project: eap_feedback_instructor [error] Finished processing: eap_feedback_instructor [ok] WD hacked: Could not download project: eap_feedback_language [error] WD hacked: Could not hash remote project: eap_feedback_language [error] WD hacked: Could not download project: eap_feedback_language [error] WD hacked: Could not hash remote project: eap_feedback_language [error] WD hacked: Could not hash local project: eap_feedback_language [error] Finished processing: eap_feedback_language [ok] WD hacked: Could not download project: eap_feedback_traveling [error] WD hacked: Could not hash remote project: eap_feedback_traveling [error] WD hacked: Could not download project: eap_feedback_traveling [error] WD hacked: Could not hash remote project: eap_feedback_traveling [error] WD hacked: Could not hash local project: eap_feedback_traveling [error] Finished processing: eap_feedback_traveling [ok] WD hacked: Could not download project: eap_foundation [error] WD hacked: Could not hash remote project: eap_foundation [error] WD hacked: Could not download project: eap_foundation [error] WD hacked: Could not hash remote project: eap_foundation [error] WD hacked: Could not hash local project: eap_foundation [error] Finished processing: eap_foundation [ok] WD hacked: Could not download project: eap_gcal_events [error] WD hacked: Could not hash remote project: eap_gcal_events[error] WD hacked: Could not download project: eap_gcal_events [error] WD hacked: Could not hash remote project: eap_gcal_events[error] WD hacked: Could not hash local project: eap_gcal_events [error] Finished processing: eap_gcal_events [ok] WD hacked: Could not download project: eap_newsletters [error] WD hacked: Could not hash remote project: eap_newsletters[error] WD hacked: Could not download project: eap_newsletters [error] WD hacked: Could not hash remote project: eap_newsletters[error] WD hacked: Could not hash local project: eap_newsletters [error] Finished processing: eap_newsletters [ok] WD hacked: Could not download project: eap_photo_contest [error] WD hacked: Could not hash remote project: eap_photo_contest [error] WD hacked: Could not download project: eap_photo_contest [error] WD hacked: Could not hash remote project: eap_photo_contest [error] WD hacked: Could not hash local project: eap_photo_contest [error] Finished processing: eap_photo_contest [ok] WD hacked: Could not download project: eap_student_feedback2 [error] WD hacked: Could not hash remote project: eap_student_feedback2 [error] WD hacked: Could not download project: eap_student_feedback2 [error] WD hacked: Could not hash remote project: eap_student_feedback2 [error] WD hacked: Could not hash local project: eap_student_feedback2 [error] Finished processing: eap_student_feedback2 [ok] WD hacked: Could not download project: eap_student_videos[error] WD hacked: Could not hash remote project: eap_student_videos [error] WD hacked: Could not download project: eap_student_videos[error] WD hacked: Could not hash remote project: eap_student_videos [error] WD hacked: Could not hash local project: eap_student_videos [error] Finished processing: eap_student_videos [ok] Finished processing: Empty paragraph killer [ok] Finished processing: Entity API [ok] Finished processing: External Links [ok] Finished processing: Features [ok] Finished processing: Field Permissions [ok] Finished processing: Media [ok] Finished processing: File (Field) Paths [ok] Finished processing: Fast Permissions Administration [ok] WD hacked: Could not download project: FullCalendar [error] WD hacked: Could not hash remote project: FullCalendar [error] WD hacked: Could not download project: FullCalendar [error] WD hacked: Could not hash remote project: FullCalendar [error] WD hacked: Could not hash local project: FullCalendar [error] Finished processing: FullCalendar [ok] Finished processing: Global Redirect [ok] Finished processing: Hacked! [ok] Finished processing: Libraries API [ok] WD hacked: Could not download project: Link [error] WD hacked: Could not hash remote project: Link [error] WD hacked: Could not download project: Link [error] WD hacked: Could not hash remote project: Link [error] WD hacked: Could not hash local project: Link [error] Finished processing: Link [ok] Finished processing: Linkit [ok] Finished processing: Media: YouTube [ok] Finished processing: Menu block [ok] Finished processing: Menu position [ok] Finished processing: Migrate [ok] Finished processing: Module Filter [ok] Finished processing: NodeSymlinks [ok] Finished processing: Override Node Options [ok] Finished processing: Panelizer[ok] Finished processing: Panels [ok] Finished processing: Pathauto [ok] Finished processing: Pathologic [ok] Finished processing: Piwik Web Analytics [ok] Finished processing: Rabbit Hole [ok] Finished processing: Rules [ok] Finished processing: Rules Link [ok] Finished processing: simplehtmldom API [ok] Finished processing: Social media [ok] Finished processing: Strongarm[ok] WD hacked: Could not download project: student_blogs [error] WD hacked: Could not hash remote project: student_blogs [error] WD hacked: Could not download project: student_blogs [error] WD hacked: Could not hash remote project: student_blogs [error] WD hacked: Could not hash local project: student_blogs [error] Finished processing: student_blogs [ok] WD hacked: Could not download project: student_story [error] WD hacked: Could not hash remote project: student_story [error] WD hacked: Could not download project: student_story [error] WD hacked: Could not hash remote project: student_story [error] WD hacked: Could not hash local project: student_story [error] Finished processing: student_story [ok] WD hacked: Could not download project: Taxonomy Edge [error] WD hacked: Could not hash remote project: Taxonomy Edge [error] WD hacked: Could not download project: Taxonomy Edge [error] WD hacked: Could not hash remote project: Taxonomy Edge [error] WD hacked: Could not hash local project: Taxonomy Edge [error] Finished processing: Taxonomy Edge [ok] Finished processing: Taxonomy Manager [ok] Finished processing: Token [ok] WD hacked: Could not download project: ucsbnetid_auth [error] WD hacked: Could not hash remote project: ucsbnetid_auth [error] WD hacked: Could not download project: ucsbnetid_auth [error] WD hacked: Could not hash remote project: ucsbnetid_auth [error] WD hacked: Could not hash local project: ucsbnetid_auth [error] Finished processing: ucsbnetid_auth [ok] Finished processing: Views [ok] WD hacked: Could not download project: Views RSS [error] WD hacked: Could not hash remote project: Views RSS [error] WD hacked: Could not download project: Views RSS [error] WD hacked: Could not hash remote project: Views RSS [error] WD hacked: Could not hash local project: Views RSS [error] Finished processing: Views RSS[ok] WD hacked: Could not download project: Webform [error] WD hacked: Could not hash remote project: Webform [error] WD hacked: Could not download project: Webform [error] WD hacked: Could not hash remote project: Webform [error] WD hacked: Could not hash local project: Webform [error] Finished processing: Webform [ok] Finished processing: Webform Entity [ok] Finished processing: Webform Validation [ok] Finished processing: Widgets [ok] Finished processing: Workbench[ok] Finished processing: Workbench Moderation [ok] Finished processing: Wysiwyg [ok] Finished processing: Zen [ok] Done.
As you can see some modules or themes produce Errors. These errors are actually custom made modules and themes in this case which do not exist on Drupal.org’s repository. In these instances I can safely ignore these Errors as I know these modules are accurate against their local Git history.
Upon completion of the generated project list Hacked then outputs a tabular view of the status of modules on your site, you can inspect this list by hand for modules which differ from the current remote source:
Done. Title Name Version Status Changed Deleted eap_academics eap_academics 7.x-1.0 Unchecked 0 0 eap_alumni eap_alumni 7.x-1.0 Unchecked 0 0 eap_feedback_banking eap_feedback_banking 7.x-1.0 Unchecked 0 0 eap_feedback_communication eap_feedback_communication 7.x-1.0 Unchecked 0 0 eap_feedback_courses eap_feedback_courses 7.x-1.0 Unchecked 0 0 eap_feedback_culture eap_feedback_culture 7.x-1.0 Unchecked 0 0 eap_feedback_food eap_feedback_food 7.x-1.0 Unchecked 0 0 eap_feedback_host_city eap_feedback_host_city 7.x-1.0 Unchecked 0 0 eap_feedback_host_university eap_feedback_host_university 7.x-1.0 Unchecked 0 0 eap_feedback_housing eap_feedback_housing 7.x-1.0 Unchecked 0 0 eap_feedback_instructor eap_feedback_instructor 7.x-1.0 Unchecked 0 0 eap_feedback_language eap_feedback_language 7.x-1.0 Unchecked 0 0 eap_feedback_traveling eap_feedback_traveling 7.x-1.0 Unchecked 0 0 eap_foundation eap_foundation 7.x-1.0 Unchecked 0 0 eap_gcal_events eap_gcal_events 7.x-1.0 Unchecked 0 0 eap_newsletters eap_newsletters 7.x-1.0 Unchecked 0 0 eap_photo_contest eap_photo_contest 7.x-2.0 Unchecked 0 0 eap_student_feedback2 eap_student_feedback2 7.x-1.0 Unchecked 0 0 eap_student_videos eap_student_videos 7.x-1.0 Unchecked 0 0 FullCalendar fullcalendar 7.x-2.0-beta3+5-dev Unchecked 0 0 Link link 7.x-1.0+28-dev Unchecked 0 0 student_blogs student_blogs 7.x-1.5 Unchecked 0 0 student_story student_story 7.x-1.0 Unchecked 0 0 Taxonomy Edge taxonomy_edge 7.x-1.8+12-dev Unchecked 0 0 ucsbnetid_auth ucsbnetid_auth 7.x-1.0 Unchecked 0 0 Views RSS views_rss 7.x-2.0-rc3+7-dev Unchecked 0 0 Webform webform 7.x-4.0-rc5+6-dev Unchecked 0 0 Admin admin 7.x-2.x-dev Changed 1 0 Conditional Fields conditional_fields 7.x-3.x-dev Changed 8 1 Drupal core drupal 7.31 Changed 4 2 Webform Entity webform_entity 7.x-1.x-dev Changed 3 0 Automatic Entity Label auto_entitylabel 7.x-1.2 Unchanged 0 0 Backup and Migrate backup_migrate 7.x-2.2 Unchanged 0 0 Bean bean 7.x-1.7 Unchanged 0 0 Colorbox colorbox 7.x-2.5 Unchanged 0 0 Field formatter for colorbox module colorbox_field_formatter 7.x-1.0 Unchanged 0 0 Context context 7.x-3.2 Unchanged 0 0 Chaos tool suite (ctools) ctools 7.x-1.4 Unchanged 0 0 Date date 7.x-2.8 Unchanged 0 0 Devel devel 7.x-1.3 Unchanged 0 0 Diff diff 7.x-3.2 Unchanged 0 0 Empty paragraph killer emptyparagraphkiller 7.x-1.0-beta1 Unchanged 0 0 Entity API entity 7.x-1.5 Unchanged 0 0 External Links extlink 7.x-1.12 Unchanged 0 0 Features features 7.x-1.0-rc3 Unchanged 0 0 Field Permissions field_permissions 7.x-1.0-beta2 Unchanged 0 0 File (Field) Paths filefield_paths 7.x-1.0-beta4 Unchanged 0 0 Fast Permissions Administration fpa 7.x-2.3 Unchanged 0 0 Global Redirect globalredirect 7.x-1.5 Unchanged 0 0 Hacked! hacked 7.x-2.0-beta5 Unchanged 0 0 Libraries API libraries 7.x-2.2 Unchanged 0 0 Linkit linkit 7.x-2.5 Unchanged 0 0 Media media 7.x-1.4 Unchanged 0 0 Media: YouTube media_youtube 7.x-2.0-rc3 Unchanged 0 0 Menu block menu_block 7.x-2.3 Unchanged 0 0 Menu position menu_position 7.x-1.1 Unchanged 0 0 Migrate migrate 7.x-2.6-rc1 Unchanged 0 0 Module Filter module_filter 7.x-1.7 Unchanged 0 0 NodeSymlinks nodesymlinks 7.x-1.0-beta2 Unchanged 0 0 Override Node Options override_node_options 7.x-1.12 Unchanged 0 0 Panelizer panelizer 7.x-2.0 Unchanged 0 0 Panels panels 7.x-3.3 Unchanged 0 0 Pathauto pathauto 7.x-1.2 Unchanged 0 0 Pathologic pathologic 7.x-2.3 Unchanged 0 0 Piwik Web Analytics piwik 7.x-2.3 Unchanged 0 0 Rabbit Hole rabbit_hole 7.x-2.22 Unchanged 0 0 Rules rules 7.x-2.7 Unchanged 0 0 Rules Link rules_link 7.x-1.0 Unchanged 0 0 simplehtmldom API simplehtmldom 7.x-1.12 Unchanged 0 0 Social media socialmedia 7.x-1.0-beta13 Unchanged 0 0 Strongarm strongarm 7.x-2.0 Unchanged 0 0 Taxonomy Manager taxonomy_manager 7.x-1.0 Unchanged 0 0 Token token 7.x-1.4 Unchanged 0 0 Views views 7.x-3.8 Unchanged 0 0 Webform Validation webform_validation 7.x-1.5 Unchanged 0 0 Widgets widgets 7.x-1.0-rc1 Unchanged 0 0 Workbench workbench 7.x-1.2 Unchanged 0 0 Workbench Moderation workbench_moderation 7.x-1.3 Unchanged 0 0 Wysiwyg wysiwyg 7.x-2.2 Unchanged 0 0 Zen zen 7.x-3.3 Unchanged 0 0
From this huuuge list of modules we can see that perhaps the Admin, Conditional Fields, Drupal Core and Webform Entity modules have alterations to them — we may want to inspect them for malicious or “hacked” changes.
Using hacked-details we can get an overall view of changes from the remote copy vs our own in-use copy:
$> drush hacked-details admin Details for project: Admin Total files: 28, files changed: 1, deleted files: 0 Detailed results: Status File Changed admin.info
By using hacked-diff we can explicitly see all the changes between the 2 versions of these modules — and scrutinize for malicious behavior:
$> drush hacked-diff admin diff -uprb a/admin.info b/admin.info --- admin.info 2013-09-30 07:52:13.000000000 -0700 +++ admin.info 2012-09-24 09:01:25.000000000 -0700 @@ -13,9 +13,9 @@ files[] = theme/admin-panes.tpl.php files[] = theme/admin-toolbar.tpl.php files[] = theme/theme.inc -; Information added by drupal.org packaging script on 2013-09-30 -version = "7.x-2.0-beta3+8-dev" +; Information added by drupal.org packaging script on 2011-09-30 +version = "7.x-2.x-dev" core = "7.x" project = "admin" -datestamp = "1380552733" +datestamp = "1317340920"
As you can see the differences between these files is inconsequential. It’s merely a system generated timestamp which differs between the 2 versions.
Ultimately for my full site the differences the Hacked module found were similar non-malicious alterations of code by packaging tools on Drupal.org. So I’m now confident I can resume a local update process to rollout changes to the Production site. Yay!
Looking for quality web hosting? Look no further than Arvixe Web Hosting!