Date post: | 26-Dec-2015 |
Category: |
Documents |
Upload: | maurice-bennett |
View: | 217 times |
Download: | 1 times |
Twin Cities Java User Group
Introduction to Writing Secure Web Applications
March 9th, 2009Jason Dean
Minnesota Department of Health
Who am I?
Web Application Developer with the Minnesota Department of Health (MDH)
Chairperson and User Group Manager of the MDH ColdFusion User Group
Web Development Blogger (http://www.12robots.com)
Veteran of the U.S. Coast Guard
What is Application Security?
Measures taken to prevent the exploitation of an application or the system that runs the
application through defects in the design, development or deployment of the application
Threats
• The basics– Cross-Site Scripting XSS
– Cookie Misuse/Exploits
– SQL Injection
– Request Forgeries (on-site and cross-site)
– Input Validation Exploits
– File Uploads
• The Advanced– Session Management Attacks– Authorization/Authentication– Access Control Attacks– Parameter Manipulation
The less obvious Ignorance Assumptions Laziness Internal threats
Countermeasures
Countermeasures mitigate attacks Out-Of-The-Box Custom Test and Retest Do not touch Certify
What are we going to talk about?
The Basic: SQL Injection Cross-Site Scripting (XSS) Cookies Request Forgeries
The less obvious: Ignorance Assumptions Laziness
Ignorance
A long habit of not thinking a thing wrong gives it a superficial appearance of being right.
- Thomas Paine
Assumptions about users
Two things are infinite: the universe and human stupidity; and I'm not sure about the universe.
- Albert Einstein
Assumptions About Hackers Why would a hacker have any
interest in your site? Vandalism Identity Theft Activism
Hackers will not use your site as you intend, either
Assumptions about administrator/host
Configured correctly? Settings enabled? Work together to
review configuration Control at the
application level Hire an Expert
Assumptions about how the server/environment work
Secret URLs Firewall Google Web Server Logs Internal Traffic Hidden Fields Javascript
SQL Injection
Obtain, Change or Destroy Data Execute System Commands Easy to do Easy to stop Any DBMS
SQL Injection Examples
String query = "SELECT * FROM users WHERE userid = " + userid;
http://www.12robots.com/?userid=1303
URL, Form and Cookie parameters can be used as part of a SQL statement.
Would probably be used in a query like this:
SQL Injection Examples
www.12robots.com/?userid=1303
http://www.12robots.com/?userid=1303;+DELETE+FROM+users;--
Would Become
SQL Injection Examples (cont)
http://www.12robots.com/?userid=1303;+DELETE+FROM+users;--
SELECT username, firstnameFROM usersWHERE userid = 1303;DELETE FROM customers;--
Would result in this query
SQL Injection Examples (cont)
http://www.12robots.com/?userid=1303%20OR%201=1;--
SELECT username, firstnameFROM usersWHERE userid = 1303 OR 1=1;--
Would result in this query
Stopping SQL Injection Example
http://www.12robots.com/?username=Jason&password=myPass I know we don’t send passwords in the URL, this is a demo, this would work just as well in a form field
http://www.12robots.com/?username=Jason'-&password=noPass
SELECT username, firstnameFROM usersWHERE username = 'jason'-- ' AND password = ‘myPass’
SELECT username, firstnameFROM usersWHERE username = 'jason''-- ' AND password = 'myPass'
So if you had a URL for login in that looked like
And a hacker tried to inject a single quote and double-dash
If you did not have a parameterized query, you'd get hacked
But with a parameterized query, you'd be safe
Prepared Statements in ActionColdFusion<cfqueryparam> on an Integer
OR
<cfqueryparam> on an String
<cfquery name="qMyQuery" datasource="myDSN">SELECT username, firstnameFROM usersWHERE userid = <cfqueryparam value="#url.userid#" cfsqltype="cf_sql_integer">
</cfquery>
<cfquery name="qMyQuery" datasource="myDSN">SELECT username, firstnameFROM usersWHERE userid = <cfqueryparam value="#url.username#" cfsqltype="cf_sql_varchar">
</cfquery>
Prepared Statements in ActionJavaPrepare a string:
Prepare an Integer:
String query = "SELECT id, fname, lname FROM authors WHERE fname = ? and lname = ?";PreparedStatement pstmt = connection.prepareStatement( query );pstmt.setString( 1, fname );pstmt.setString( 2, lname );ResultSet results = pstmt.execute( );
String query = "SELECT id, fname, lname FROM authors WHERE id = ?”;PreparedStatement pstmt = connection.prepareStatement( query );pstmt.setInt( 1, id );ResultSet results = pstmt.execute( );
Prepared Statements in ActionC#Prepare a string:
IDbCommand cmdUserInputText = conn.CreateCommand();
cmdUserInputText.CommandType= System.Data.CommandType.Text;
cmdUserInputText.CommandText = "SELECT * FROM titles WHERE title_id=@title_id";
IDbDataParameter userParam = cmdUserInputText.CreateParameter();
userParam.Value = "myTitleID";
userParam.DbType = System.Data.DbType.String;
cmdUserInputText.Parameters.Add(userParam);
Prepared Statements in ActionPHP with MySQLiPrepare an Integer:
Prepare a String
$db_conn = new mysqli("localhost", "user", "pass", "db");
$statement = $db_conn->prepare("SELECT username FROM users WHERE id = ?");
$statement->bind_param("i", $id);
$statement->execute();
$db_conn = new mysqli("localhost", "user", "pass", "db");
$statement = $db_conn->prepare("SELECT id FROM users WHERE username = ?");
$statement->bind_param("s", $username);
$statement->execute();
What about other Dynamic Elements in SQL?
<cfquery name="qMyQuery" datasource="myDSN">SELECT username, firstnameFROM usersORDER BY username #sortOrder#
</cfquery>
<cfquery name="qMyQuery" datasource="myDSN">SELECT username, firstnameFROM usersORDER BY username <cfif sortOrder EQ "ASC">ASC<cfesle>DESC</cfif>
</cfquery>
Cross-Site Scripting (XSS)
Injection Attack One user attacks another Many uses Any user input Usually JavaScript
XSS Example You have a comments text box, like so:
And some joker decides to inject some Javascript:
Then when someone views the page that displays that comment, they get:
XSS iFrame Example
When another user views the output of that comment later, they will see a form prompting for their user/pass, if they enter and hit “submit” the form will be posted to the evil site.
XSS Prevention
So how do we protect against this type of attack? Turn on script protection (ColdFusion)
Use character encoding functions on all dynamic output
User Input validation
Use a security API or Framework for your specific language
Character Encoding
<script type=”text/javascript”>alert('Hacked!');</script>
<script type=”text/javascript”>alert('Hacked!');</script>
This: This is <strong>Bold Text</strong>
Would become: This is <strong>Bold Text</strong>
And when displayed: This is <strong>Bold Text</strong>
Instead of like: This is Bold Text
Character Encoding Function ColdFusion
Java
Java ESAPI
PHP
C#
import org.w3c.tidy.servlet.util.HTMLEncode //jTidyencode(String);
<cfoutput>#HTMLEncodedFormat(String)#</cfoutput>
ESAPI.encoder().encodeForHTML(String);
Server.HtmlEncode(String);
<?php echo htmlentities(String, ENT_QUOTES) ?>
Cookie Domain and Path www.awesomebloggers.com 12robots.awesomebloggers.com domain=”.awesomebloggers.com” hacker.awesomebloggers.com domain=”.12robots.awesomebloggers.com”
www.awesomebloggers.com/12robots Path=”/” www.awesomeblogers.com/hacker path=”/12robots”
Setting the HTTPOnly Flag
response.setHeader("Set-Cookie", "name=value; HTTPOnly");
<cfheader name="Set-Cookie" value="name=value;HttpOnly">
HttpCookie myCookie = new HttpCookie("myCookie");myCookie.HttpOnly = true;Response.AppendCookie(myCookie);
<?php setcookie("name", "value", [expire], [path], [domain], [secure], TRUE); ?>
ColdFusion
Java
PHP
C#
What is a Request Forgery?
A request forgery, also sometimes called a Cross-Site (or On-Site) Request Forgery(XSRF), is an attack that is perpetrated against the user of a site who has authenticated access to that site
That was confusing How about an Example?
Delete page/function
single parameter
PageID
Admin Only
All is good, right?
So what can we do about it?
It probably:
Receives the request Checks to make sure the user is logged in Confirms that the ID is valid Performs the action
<form action="deletePage.cfm" method="post"><input type="hidden" name="pageid" value="1" /><input type="submit" name="btnSubmit" value="Delete Page 1" />
</form>
How do we fix it?
//pseudo-codesession.add(“key”, createUUID());session.add(“keyExpires”, DateAdd('m', 10, Now());
<form action="deletePage.cfm" method="post"><input type="hidden" name="pageid" value="1" /><input type="submit" name="btnSubmit" value="Delete Page 1" /><input type="hidden" name="key" value="#session.key#" />
</form>
How do we fix it?
Pseudo-code
If (exists(sessionkey) && exists(formkey) && !(isExpired(formKey, keyExpires)) && sessionkey == formKey) {
//Delete the key from the session so it can't be reuseddelete(sessionkey);
} else {//Relocate the request if the key is not present or doesn't matchlog(securityInfo);request.location(webroot); //or throw an Exception
}
//Finish Processing the request
Questions?
Please ask your questions now Comments?
Jason Dean [email protected] http://www.12robots.com