The Security State of Open Source PHP Applications Dr. Johannes - - PowerPoint PPT Presentation

the security state of
SMART_READER_LITE
LIVE PREVIEW

The Security State of Open Source PHP Applications Dr. Johannes - - PowerPoint PPT Presentation

The Security State of Open Source PHP Applications Dr. Johannes Dahse, RIPS Technologies GmbH Introduction About Johannes Dahse Master IT Security at RUB, Germany (2006 - 2012) Capture The Flag (CTF) Contests Security Consultant


slide-1
SLIDE 1

The Security State of Open Source PHP Applications

  • Dr. Johannes Dahse, RIPS Technologies GmbH
slide-2
SLIDE 2

About

Introduction

Johannes Dahse

  • Master IT Security at RUB, Germany (2006 - 2012)
  • Capture The Flag (CTF) Contests
  • Security Consultant
  • Developer of RIPS open source security scanner (2009 - 2011)
  • PhD in „Static Code Analysis“ at RUB (2013 - 2016)
  • CEO & Co-Founder RIPS Technologies GmbH
slide-3
SLIDE 3

Why care about PHP security?

Introduction

$3.8M

average data breach costs

#1 Choice

  • f cyber criminals

90%

use open source libraries

22 Attacks/Day

  • n an average website
slide-4
SLIDE 4

The Security State of

Introduction

Top 5 PHP Applications Top 50 PHP Applications PHP Application Extensions Top 6 PHP Frameworks

slide-5
SLIDE 5

Top 5 PHP Applications

The Security State of the

slide-6
SLIDE 6

Top 5 PHP Applications

The Security State of the

60% 7% 5% 2% 1% 25%

CMS Market Share

WordPress Joomla! Drupal Magento Typo3 Other

Source: w3techs.com

slide-7
SLIDE 7

Security Features

Top 5 PHP Applications

Application (latest version) Prepared Statements Template Engine CSRF Protection Password Hashing Security Team Auto Update* Bug Bounty Program WordPress vsprintf() none yes phpass yes yes yes Joomla! MySQLi custom yes bcrypt yes no no Drupal PDO Twig yes salted sha-512 yes no 2015 Magento PDO custom yes salted sha-256 yes no yes Typo3 Doctrine Fluid yes pbkdf2 yes yes no

*Pro/Con Discussion: https://www.drupal.org/node/2367319

slide-8
SLIDE 8

Vulnerabilities

Top 5 PHP Applications

5 10 15 20 25 30 35 40 45 2010 2011 2012 2013 2014 2015 2016 2017

Number of Vulnerabilities per Year

WordPress Joomla! Drupal Magento Typo3

Source: cvedetails.com

slide-9
SLIDE 9

Vulnerabilities

Top 5 PHP Applications

1 2 3 4 5 6 7 8 2010 2011 2012 2013 2014 2015 2016 2017

Number of Critical Vulnerabilities per Year (CVSS Score > 7)

WordPress Joomla! Drupal Magento Typo3

Source: cvedetails.com

slide-10
SLIDE 10

Vulnerability Example #1

Top 5 PHP Applications

CVE-2015-3438 – Persistent XSS in Wordpress 4.1.2

https://cedricvb.be/post/wordpress-stored-xss-vulnerability-4-1-2/

  • MySQL‘s utf8 charset only supports 3-byte characters
  • Strings with 4-byte characters will be truncated when inserted into utf8 columns
  • Solution: Use MySQL strict mode or latin1 charset

Insert: test𝌇123 Result: test

slide-11
SLIDE 11

Vulnerability Example #1

Top 5 PHP Applications

CVE-2015-3438 – Persistent XSS in Wordpress 4.1.2

https://cedricvb.be/post/wordpress-stored-xss-vulnerability-4-1-2/

slide-12
SLIDE 12

Vulnerability Example #1

Top 5 PHP Applications

CVE-2015-3438 – Persistent XSS in Wordpress 4.1.2

https://cedricvb.be/post/wordpress-stored-xss-vulnerability-4-1-2/

<div class="comment" id="comment-1"> <div class="comment-content"> <a title='test𝌇123'>click</a> </div> </div>

slide-13
SLIDE 13

Vulnerability Example #1

Top 5 PHP Applications

CVE-2015-3438 – Persistent XSS in Wordpress 4.1.2

https://cedricvb.be/post/wordpress-stored-xss-vulnerability-4-1-2/

<div class="comment" id="comment-1"> <div class="comment-content"> <a title='test </div> </div>

slide-14
SLIDE 14

Vulnerability Example #1

Top 5 PHP Applications

CVE-2015-3438 – Persistent XSS in Wordpress 4.1.2

https://cedricvb.be/post/wordpress-stored-xss-vulnerability-4-1-2/

<div class="comment" id="comment-1"> <div class="comment-content"> <a title='test </div> </div> <div class="comment" id="comment-2"> <div class="comment-content"> hack' onmouseover='alert(1)' style='width:100%;height:100%;…' </div> </div>

slide-15
SLIDE 15

Vulnerability Example #2

Top 5 PHP Applications

CVE-2017-14596 – LDAP Injection in Joomla! 1.5 - 3.7.5

https://blog.ripstech.com/2017/joomla-takeover-in-20-seconds-with-ldap-injection-cve-2017-14596/

slide-16
SLIDE 16

Vulnerability Example #2

Top 5 PHP Applications

CVE-2017-14596 – LDAP Injection in Joomla! 1.5 - 3.7.5

https://blog.ripstech.com/2017/joomla-takeover-in-20-seconds-with-ldap-injection-cve-2017-14596/

class LoginController extends JControllerLegacy { public function login() { ⋮ $app = JFactory::getApplication(); ⋮ $model = $this->getModel('login'); $credentials = $model->getState('credentials'); ⋮ $app->login($credentials, array('action' => 'core.login.admin')); }

slide-17
SLIDE 17

Vulnerability Example #2

Top 5 PHP Applications

CVE-2017-14596 – LDAP Injection in Joomla! 1.5 - 3.7.5

https://blog.ripstech.com/2017/joomla-takeover-in-20-seconds-with-ldap-injection-cve-2017-14596/

class JApplicationCms extends JApplicationWeb { public function login($credentials, $options = array()) { ⋮ $authenticate->authenticate($credentials, $options); } } class JAuthentication extends Jobject { public function authenticate($credentials, $options = array()) { ⋮ $plugin->onUserAuthenticate($credentials, $options, $response); }

slide-18
SLIDE 18

Vulnerability Example #2

Top 5 PHP Applications

CVE-2017-14596 – LDAP Injection in Joomla! 1.5 - 3.7.5

https://blog.ripstech.com/2017/joomla-takeover-in-20-seconds-with-ldap-injection-cve-2017-14596/

class PlgAuthenticationLdap extends JPlugin { public function onUserAuthenticate($credentials, $options, &$response){ ⋮ $userdetails = $ldap->simple_search( str_replace( '[search]', $credentials['username'], $this->params->get('search_string') // uid=[search] ) ); }

slide-19
SLIDE 19

XXX;(&(uid=Admin)(userPassword=A*)) XXX;(&(uid=Admin)(userPassword=B*)) XXX;(&(uid=Admin)(userPassword=C*)) ... XXX;(&(uid=Admin)(userPassword=s*)) ... XXX;(&(uid=Admin)(userPassword=se*)) ... XXX;(&(uid=Admin)(userPassword=sec*)) ... XXX;(&(uid=Admin)(userPassword=secretPassword))

Vulnerability Example #2

Top 5 PHP Applications

CVE-2017-14596 – LDAP Injection in Joomla! 1.5 - 3.7.5

https://blog.ripstech.com/2017/joomla-takeover-in-20-seconds-with-ldap-injection-cve-2017-14596/

slide-20
SLIDE 20

Vulnerability Demo #2

Top 5 PHP Applications

slide-21
SLIDE 21

Conclusion

Top 5 PHP Applications

  • Good security features by default
  • Great security teams
  • Bug bounty programs
  • But very attractive targets
  • Average 14 security issues reported per year
  • Average 1-2 critical issues reported per year
  • As secure/insecure as any other popular software

https://codex.wordpress.org/Hardening_WordPress https://docs.joomla.org/Security_Checklist/en https://www.drupal.org/docs/8/security https://magento.com/security/best-practices https://docs.typo3.org/typo3cms/SecurityGuide/

slide-22
SLIDE 22

Top 50 PHP Applications

The Security State of the

slide-23
SLIDE 23

Top 50 PHP Applications

The Security State of the

  • PHP Applications within the list of popular CMS (w3techs.com)
  • E.g. PrestaShop, phpBB, SugarCRM
  • Popular PHP Applications with a similar high google trend
  • E.g. phpMyAdmin, Piwik, Roundcube
  • 50 Applications, 13.2 MLOC total (300 KLOC average)
  • Automated code analysis
slide-24
SLIDE 24

Security State

Top 50 PHP Applications

56% 44%

Security Contact Available

Yes No 58% 42%

Critical Detected by RIPS

Yes No 39% 28% 33%

Time To Fix (if)

2 weeks 6 weeks 3 month

slide-25
SLIDE 25

Attack Vectors

Top 50 PHP Applications

SQL Injection PHP Object Injection Cross-Site Scripting Command Execution File Upload Path Traversal Code Execution File Inclusion

slide-26
SLIDE 26

Critical Examples

Software Attack Vector detected by RIPS Roundcube Command Execution via Email FreePBX Command Execution via Cross-Site Scripting Coppermine Command Execution via SQL Injection

  • sClass

Command Execution via Local File Inclusion Expression Engine Command Execution via PHP Object Injection KLIQQI CMS Command Execution via Cross-Site Request Forgery Redaxo CMS Command Execution via Cross-Site Request Forgery Precurio Command Execution via Path Traversal Serendipity Command Execution via Logical Flaw

Top 50 PHP Applications

https://demo.ripstech.com

slide-27
SLIDE 27

Vulnerability Example #1

Top 50 PHP Applications

https://blog.ripstech.com/2016/roundcube-command-execution-via-email/

CVE-2016-9920 – Remote Command Execution in Roundcube 1.2.2

slide-28
SLIDE 28

Vulnerability Example #1

Top 50 PHP Applications

https://blog.ripstech.com/2016/roundcube-command-execution-via-email/

CVE-2016-9920 – Remote Command Execution in Roundcube 1.2.2

$from = rcube_utils::get_input_value('_from', rcube_utils::INPUT_POST); $RCMAIL->deliver_message($MAIL, $from, $mailto, $error); public function deliver_message(&$message, $from, $mailto, &$error) { ⋮ if (filter_var(ini_get('safe_mode'), FILTER_VALIDATE_BOOLEAN)) $sent = mail($to, $subject, $msg_body, $header_str); else $sent = mail($to, $subject, $msg_body, $header_str, "-f$from");

slide-29
SLIDE 29

Vulnerability Example #1

Top 50 PHP Applications

https://blog.ripstech.com/2016/roundcube-command-execution-via-email/

CVE-2016-9920 – Remote Command Execution in Roundcube 1.2.2

$from = rcube_utils::get_input_value('_from', rcube_utils::INPUT_POST); $RCMAIL->deliver_message($MAIL, $from, $mailto, $error); public function deliver_message(&$message, $from, $mailto, &$error) { ⋮ if (filter_var(ini_get('safe_mode'), FILTER_VALIDATE_BOOLEAN)) $sent = mail($to, $subject, $msg_body, $header_str); else $sent = mail($to, $subject, $msg_body, $header_str, "-f$from");

slide-30
SLIDE 30

Vulnerability Example #1

Top 50 PHP Applications

https://blog.ripstech.com/2016/roundcube-command-execution-via-email/

CVE-2016-9920 – Remote Command Execution in Roundcube 1.2.2

rperaglie@ripstech.com -OQueueDirectory=/tmp -X/var/www/html/rce.php

04731 <<< To: contact@ripstech.com 04731 <<< Subject: <?php phpinfo(); ?> 04731 <<< X-PHP-Originating-Script: 1000:rcube.php 04731 <<< MIME-Version: 1.0 04731 <<< Content-Type: text/plain; charset=US-ASCII; 04731 <<< Content-Transfer-Encoding: 7bit 04731 <<< Date: So, 20 Nov 2016 04:02:52 +0100 04731 <<< From: rperaglie@ripstech.com -OQueueDirectory=/tmp 04731 <<< -X/var/www/html/rce.php …

slide-31
SLIDE 31

Vulnerability Demo #1

Top 50 PHP Applications

slide-32
SLIDE 32

Vulnerability Disclosure

Top 50 PHP Applications

Software Affected Version CVE Patch Date Roundcube <= 1.2.2 CVE-2016-9920 2016-11-28 MediaWiki < 1.29 2016-12-10 Zend Framework < 2.4.11 CVE-2016-10034 2016-12-20 PHPMailer <= 5.2.18 CVE-2016-10033 2016-12-28 SwiftMailer <= 5.4.5-DEV CVE-2016-10074 2016-12-29 SquirrelMail <= 1.4.23 CVE-2017-7692

I was reading https://blog.ripstech.com/2016/roundcube-command- execution-via-email/. We don't do escaping of the fifth argument to mail() either.

https://phabricator.wikimedia.org/T152717

slide-33
SLIDE 33

Vulnerability Example #2

Top 50 PHP Applications

switch ($this->action) { case 'error_plugin': … include( osc_plugins_path() . Params::getParam('plugin') ); Plugins::install(Params::getParam('plugin'));

Local File Inclusion in osClass 1.2.2

https://blog.ripstech.com/2016/osclass-remote-code-execution-via-image-file/

slide-34
SLIDE 34

Vulnerability Example #2

Top 50 PHP Applications

switch ($this->action) { case 'error_plugin': … include( osc_plugins_path() . Params::getParam('plugin') ); Plugins::install(Params::getParam('plugin')); $original = pathinfo($uploader->getOriginalName()); … $filename = uniqid("qqfile") . "." . $original['extension']; $result = $uploader->handleUpload('uploads/temp/' . $filename); $img = ImageResizer::fromFile('uploads/temp/' . $filename)->autoRotate();

Local File Inclusion in osClass 1.2.2

https://blog.ripstech.com/2016/osclass-remote-code-execution-via-image-file/

slide-35
SLIDE 35

Vulnerability Example #2

Top 50 PHP Applications

shell.jpg

slide-36
SLIDE 36

Vulnerability Example #2

Top 50 PHP Applications

shell.jpg

include('plugins/../uploads/temp/shell.jpg');

slide-37
SLIDE 37

Vulnerability Demo #2

Top 50 PHP Applications

slide-38
SLIDE 38

Vulnerability Example #2

Top 50 PHP Applications

switch ($this->action) { case 'error_plugin': … include( osc_plugins_path() . Params::getParam('plugin') ); Plugins::install(Params::getParam('plugin'));

Local File Inclusion in osClass 1.2.2

https://blog.ripstech.com/2016/osclass-remote-code-execution-via-image-file/

slide-39
SLIDE 39

Security Indicators

Top 50 PHP Applications

40% 24% 16% 16%

Template Engine

None Smarty Custom Twig Other 15% 20%

Password Hash

bcrypt pbkdf2 php-crypt phpass salted hash md5/sha 86% 14%

CSRF Protection

Yes No 59% 41%

Prepared Statements

Yes No 65%

slide-40
SLIDE 40

Conclusion

Top 50 PHP Applications

  • Many security issues, although reviewed by the community
  • 58% fail the OWASP Top 10
  • 66% fail security best practices
  • Use at own risk
  • Less popular PHP applications than the Top 50 are considered worse
  • RIPS Advent of PHP Application Vulnerabilities (APAV)

https://blog.ripstech.com/2016/apav-advent-of-php-application-vulnerabilities/

slide-41
SLIDE 41

PHP Application Extensions

The Security State of

slide-42
SLIDE 42

PHP Application Extensions

The Security State of

5000 10000 15000 20000 25000 30000 35000 40000 45000 50000

Number of Extensions

WordPress Joomla! Drupal Magento Typo3

slide-43
SLIDE 43

Analysis Approach

WordPress Plugins

  • Downloaded 41K plugins from the WordPress plugin directory with active installs
  • More plugins exist but were not included into analysis (e.g. commercial)
  • Analysis with RIPS
  • magic_quotes_gpc enabled
  • WordPress-specific configuration enabled
  • No need for WordPress core analysis

https://api.wordpress.org/plugins/info/1.1/?action=query_plugins

slide-44
SLIDE 44

By Size and Detection

WordPress Plugins

50 100 150

LOC of Top 250 plugins

1-100 101-500 501-1K 1K-5K >5K 5000 10000 15000 20000

LOC of 41K plugins

1-100 101-500 501-1K 1K-5K >5K

slide-45
SLIDE 45

By Size and Detection

WordPress Plugins

50 100 150

LOC of Top 250 plugins

1-100 101-500 501-1K 1K-5K >5K 5000 10000 15000 20000

LOC of 41K plugins

1-100 101-500 501-1K 1K-5K >5K

47% 53%

Vulnerability detected Nothing detected

32% 68%

Vulnerability detected Nothing detected

slide-46
SLIDE 46

By Size and Detection

WordPress Plugins

50 100 150

LOC of Top 250 plugins

1-100 101-500 501-1K 1K-5K >5K 5000 10000 15000 20000

LOC of 41K plugins

1-100 101-500 501-1K 1K-5K >5K

45% 55%

Vulnerability detected Nothing detected

53% 47%

Vulnerability detected Nothing detected

slide-47
SLIDE 47

By Vulnerability Type

WordPress Plugins

52% 10% 3% 2% 2% 1% 1% 29%

All 41K Plugins

Cross-Site Scripting SQL Injection Resource Injection File Create Path Traversal File Delete PHP Object Injection Other

slide-48
SLIDE 48

Conclusion

WordPress Plugins

  • Assumption from statistics:
  • Every second WP plugin has a security issue
  • 18% of all WP plugins are prone to XSS
  • 5% of all WP plugins are prone to SQLi
  • Use actively maintained and popular plugins
  • Keep your plugins up to date
slide-49
SLIDE 49

PHP Frameworks

The Security State of

slide-50
SLIDE 50

Popular PHP Frameworks

The Security State of

  • Laravel
  • Symfony
  • CodeIgniter
  • CakePHP
  • Yii
  • Zend Framework

Source: trends.google.com

slide-51
SLIDE 51

Security Features

Popular PHP Frameworks

Framework Analyzed Version Template Engine Database Abstraction CSRF Protection Password Hash Security Contact Laravel 5.5.0 Blade Eloquent ORM yes bcrypt yes Symfony 3.3.10 PHP, Twig, … Doctrine ORM yes bcrypt yes CodeIgniter 3.1.6 custom Query Builder yes bcrypt yes CakePHP 3.5.3 PHP Cake ORM yes bcrypt no Yii 2.0.12 PHP Query Builder Yes bcrypt yes Zend Framework 3.0.1 PHP Query Builder Yes bcrypt yes

slide-52
SLIDE 52

Security Vulnerabilities

Popular PHP Frameworks

1 2 3 4 5 6 7 2010 2011 2012 2013 2014 2015 2016 2017

Number of Vulnerabilities per Year

Laravel Symfony CodeIgniter CakePHP Yii Zend

slide-53
SLIDE 53

Pitfall Example #1

Popular PHP Frameworks

Doctrine Query Builder

$qb = $em->createQueryBuilder(); $qb->select('u')->from('User', 'u')->where("u.id = $id");

slide-54
SLIDE 54

Pitfall Example #1

Popular PHP Frameworks

Doctrine Query Builder

$qb = $em->createQueryBuilder(); $qb->select('u')->from('User', 'u')->where("u.id = $id");

slide-55
SLIDE 55

Pitfall Example #1

Popular PHP Frameworks

Doctrine Query Builder

$qb = $em->createQueryBuilder(); $qb->select('u')->from('User', 'u')->where("u.id = $id"); /** @var \Doctrine\DBAL\Connection $con */ $connection = $doctrine->getConnection(); $connection->update('users', array('name'=>$_GET['name']), array('id'=>1));

slide-56
SLIDE 56

Pitfall Example #1

Popular PHP Frameworks

Doctrine Query Builder

$qb = $em->createQueryBuilder(); $qb->select('u')->from('User', 'u')->where("u.id = $id"); /** @var \Doctrine\DBAL\Connection $con */ $connection = $doctrine->getConnection(); $connection->update('users', array('name'=>$_GET['name']), array('id'=>1)); $connection = $doctrine->getConnection(); $connection->update('users', array($_GET['name']=>'rips'), array('id'=>1)); $connection->update('users', $_POST, array('id'=>1));

slide-57
SLIDE 57

Pitfall Example #2

Popular PHP Frameworks

Html::secureLink($_GET['url']);

https://laravel.com/api/5.5/Illuminate/Html/HtmlBuilder.html

slide-58
SLIDE 58

Pitfall Example #2

Popular PHP Frameworks

Html::secureLink($_GET['url']);

https://laravel.com/api/5.5/Illuminate/Html/HtmlBuilder.html

class HtmlBuilder { public function secureLink($url, $title=null) { return $this->link($url, $title, true); } public function link($url, $title=null, $secure=null) { $url = $this->url->to($url, array(), $secure); return '<a href="'.$url.'">'.$this->entities($title).'</a>‘; } }

slide-59
SLIDE 59

Pitfall Example #2

Popular PHP Frameworks

Html::secureLink( mailto:"><script>alert(1)</script> );

https://laravel.com/api/5.5/Illuminate/Html/HtmlBuilder.html

<a href="mailto:"><script>alert(1)</script>

class HtmlBuilder { public function secureLink($url, $title=null) { return $this->link($url, $title, true); } public function link($url, $title=null, $secure=null) { $url = $this->url->to($url, array(), $secure); return '<a href="'.$url.'">'.$this->entities($title).'</a>‘; } }

slide-60
SLIDE 60

Conclusion

Popular PHP Frameworks

  • Separation of concerns
  • Enforce security best practices
  • Help to build secure applications from the ground up
  • Use them
  • But be careful how you use them
slide-61
SLIDE 61

Summary

The Security State

slide-62
SLIDE 62

Summary

The Security State

Plugins & Extensions PHP applications PHP frameworks

slide-63
SLIDE 63

PHP Application Security

What can I do for my

  • The more third-party code you deploy, the greater the attack surface
  • Remove unnecessary libraries
  • Avoid/Protect unpopular open source applications
  • Keep all dependencies up-to-date (composer)
  • Train developers for security best practices
  • Join our Advent Calendar 2017: blog.ripstech.com
  • Integrate automated code analysis into your SDLC
slide-64
SLIDE 64

Questions?

Thank you for your attention

jdahse@ripstech.com