#3 working with data stored in files && securing your application (PART II)
Security problems is more and more important on the internet today. You can see the problems .
This chapter is really exciting, you can learn serveral ways of attacking the web application and the method to
protecting the websites. Somehow, you can be a hacker after studying.
1. Attack on the Admin page.
The last project, we can easy control to the admin user by accessing the admin page by URLs.
Thats the problem, if a hack can have the access to the admin user, it must be very bad.
Its also very simple to solve this problem. Using HTTP authentication to password protect the Admin page.
When a page is secured using HTTP authentication. a window pops up requesting the user name and password
before access is allowed to the protected page. we can limit access to the Admin page to a few peple as you
want.
you need to insert authorize.php script before you can visit the admin page.
/*** authorize.php ***/
<?php
// User name and password for authentication
$username = 'rock';
$password = 'roll'; if (!isset($_SERVER['PHP_AUTH_USER']) || !isset($_SERVER['PHP_AUTH_PW']) ||
($_SERVER['PHP_AUTH_USER'] != $username) || ($_SERVER['PHP_AUTH_PW'] != $password)) {
// The user name/password are incorrect so send the authentication headers
header('HTTP/1.1 401 Unauthorized');
header('WWW-Authenticate: Basic realm="Guitar Wars"');
exit('<h2>Guitar Wars</h2>Sorry, you must enter a valid user name and password to access this page.');
}
?>
2. The URL attacks
If the hacker has remembered the URLS of the removescore.php , he doesnt need to visit this page through
the admin Page, he can visit it directly by the URLs. so to avoid this happening, you just need to add the
authorize.php script to every page you want to protect. Just a little change can be done.
<?php
require_once('authorize.php');
?>
add the codes at the front of each page you want to protect .
3. Attack on the high socres clones
this requires the humans to get all the datas available. we need to change the database and add some authorize
to the adminstrator. so he can decides if the data is valuable or not.
4. SQL injection.
This is really cool tech in hacks. You can even attack some websites that didnt have a protection. Lets see how
to do the SQL injection. I think this is really interesting. So I trace the code by PHP debug, you can see more clearly :
1) at first, the index page looks just right :

2) you can click the link to add your score :

3) we use the PHP debug to see what is going on here : what was posted to the server just as follows :

4) the query just looks like this :

5) then quering this query , and bad things just happened :

check the database , you will see the record was insert into the database susccess.

6) lets go back to the index.php, you will see the bad results : this is what SQL injection doing :

It is also quite easy to avoid the SQL Injection using PHP, you can use the trim() function
to gets rid of leading and trailing spaces in the form data.
just ran all form data through the trim() function before using it in an SQL query.
And you also need another built-in function, mysqli_real_escape_string()
this function converts dangerous characters into an escaped format that wont adversely affect SQL queries.
the project files as follows :
/*** index.php ***/
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Guitar Wars - High Scores</title>
<link rel="stylesheet" type="text/css" href="style.css" />
</head>
<body>
<h2>Guitar Wars - High Scores</h2>
<p>Welcome, Guitar Warrior, do you have what it takes to crack the high score list? If so, just <a href="addscore.php">add your own score</a>.</p>
<hr /> <?php
require_once('appvars.php');
require_once('connectvars.php'); // Connect to the database
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME); // Retrieve the score data from MySQL
$query = "SELECT * FROM guitarwars WHERE approved=1 ORDER BY score DESC, DATE ASC";
$data = mysqli_query($dbc, $query); // Loop through the array of score data, formatting it as HTML
echo '<table>';
$i = 0;
while ($row = mysqli_fetch_array($data)) {
// Display the score data
if ($i == 0) {
echo '<tr><td colspan="2" class="topscoreheader">Top Score: ' . $row['score'] . '</td></tr>';
}
echo '<tr><td class="scoreinfo">';
echo '<span class="score">' . $row['score'] . '</span><br />';
echo '<strong>Name:</strong> ' . $row['name'] . '<br />';
echo '<strong>Date:</strong> ' . $row['date'] . '</td>';
if (is_file(GW_UPLOADPATH . $row['screenshot']) && filesize(GW_UPLOADPATH . $row['screenshot']) > 0) {
echo '<td><img src="' . GW_UPLOADPATH . $row['screenshot'] . '" alt="Score image" /></td></tr>';
}
else {
echo '<td><img src="' . GW_UPLOADPATH . 'unverified.gif' . '" alt="Unverified score" /></td></tr>';
}
$i++;
}
echo '</table>'; mysqli_close($dbc);
?> </body>
</html>
/*** addscore.php ***/
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Guitar Wars - Add Your High Score</title>
<link rel="stylesheet" type="text/css" href="style.css" />
</head>
<body>
<h2>Guitar Wars - Add Your High Score</h2> <?php
require_once('appvars.php');
require_once('connectvars.php'); if (isset($_POST['submit'])) {
// Connect to the database
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME); // Grab the score data from the POST
$name = mysqli_real_escape_string($dbc, trim($_POST['name']));
$score = mysqli_real_escape_string($dbc, trim($_POST['score']));
$screenshot = mysqli_real_escape_string($dbc, trim($_FILES['screenshot']['name']));
$screenshot_type = $_FILES['screenshot']['type'];
$screenshot_size = $_FILES['screenshot']['size']; if (!empty($name) && is_numeric($score) && !empty($screenshot)) {
if ((($screenshot_type == 'image/gif') || ($screenshot_type == 'image/jpeg') || ($screenshot_type == 'image/pjpeg') || ($screenshot_type == 'image/png'))
&& ($screenshot_size > 0) && ($screenshot_size <= GW_MAXFILESIZE)) {
if ($_FILES['screenshot']['error'] == 0) {
// Move the file to the target upload folder
$target = GW_UPLOADPATH . $screenshot;
if (move_uploaded_file($_FILES['screenshot']['tmp_name'], $target)) {
// Write the data to the database
$query = "INSERT INTO guitarwars (date, name, score, screenshot) VALUES (NOW(), '$name', '$score', '$screenshot')";
mysqli_query($dbc, $query); // Confirm success with the user
echo '<p>Thanks for adding your new high score! It will be reviewed and added to the high score list as soon as possible.</p>';
echo '<p><strong>Name:</strong> ' . $name . '<br />';
echo '<strong>Score:</strong> ' . $score . '<br />';
echo '<img src="' . GW_UPLOADPATH . $screenshot . '" alt="Score image" /></p>';
echo '<p><a href="index.php"><< Back to high scores</a></p>'; // Clear the score data to clear the form
$name = "";
$score = "";
$screenshot = ""; mysqli_close($dbc);
}
else {
echo '<p class="error">Sorry, there was a problem uploading your screen shot image.</p>';
}
}
}
else {
echo '<p class="error">The screen shot must be a GIF, JPEG, or PNG image file no greater than ' . (GW_MAXFILESIZE / 1024) . ' KB in size.</p>';
} // Try to delete the temporary screen shot image file
@unlink($_FILES['screenshot']['tmp_name']);
}
else {
echo '<p class="error">Please enter all of the information to add your high score.</p>';
}
}
?> <hr />
<form enctype="multipart/form-data" method="post" action="<?php echo $_SERVER['PHP_SELF']; ?>">
<input type="hidden" name="MAX_FILE_SIZE" value="<?php echo GW_MAXFILESIZE; ?>" />
<label for="name">Name:</label>
<input type="text" id="name" name="name" value="<?php if (!empty($name)) echo $name; ?>" /><br />
<label for="score">Score:</label>
<input type="text" id="score" name="score" value="<?php if (!empty($score)) echo $score; ?>" /><br />
<label for="screenshot">Screen shot:</label>
<input type="file" id="screenshot" name="screenshot" />
<hr />
<input type="submit" value="Add" name="submit" />
</form>
</body>
</html>
/*** authorize.php ***/
<?php
// User name and password for authentication
$username = 'rock';
$password = 'roll'; if (!isset($_SERVER['PHP_AUTH_USER']) || !isset($_SERVER['PHP_AUTH_PW']) ||
($_SERVER['PHP_AUTH_USER'] != $username) || ($_SERVER['PHP_AUTH_PW'] != $password)) {
// The user name/password are incorrect so send the authentication headers
header('HTTP/1.1 401 Unauthorized');
header('WWW-Authenticate: Basic realm="Guitar Wars"');
exit('<h2>Guitar Wars</h2>Sorry, you must enter a valid user name and password to access this page.');
}
?>
/*** approvescore.php ***/
<?php
require_once('authorize.php');
?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Guitar Wars - Approve a High Score</title>
<link rel="stylesheet" type="text/css" href="style.css" />
</head>
<body>
<h2>Guitar Wars - Approve a High Score</h2> <?php
require_once('appvars.php');
require_once('connectvars.php'); if (isset($_GET['id']) && isset($_GET['date']) && isset($_GET['name']) && isset($_GET['score'])) {
// Grab the score data from the GET
$id = $_GET['id'];
$date = $_GET['date'];
$name = $_GET['name'];
$score = $_GET['score'];
$screenshot = $_GET['screenshot'];
}
else if (isset($_POST['id']) && isset($_POST['name']) && isset($_POST['score'])) {
// Grab the score data from the POST
$id = $_POST['id'];
$name = $_POST['name'];
$score = $_POST['score'];
}
else {
echo '<p class="error">Sorry, no high score was specified for approval.</p>';
} if (isset($_POST['submit'])) {
if ($_POST['confirm'] == 'Yes') {
// Connect to the database
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME); // Approve the score by setting the approved column in the database
$query = "UPDATE guitarwars SET approved = 1 WHERE id = $id";
mysqli_query($dbc, $query);
mysqli_close($dbc); // Confirm success with the user
echo '<p>The high score of ' . $score . ' for ' . $name . ' was successfully approved.';
}
else {
echo '<p class="error">Sorry, there was a problem approving the high score.</p>';
}
}
else if (isset($id) && isset($name) && isset($date) && isset($score)) {
echo '<p>Are you sure you want to approve the following high score?</p>';
echo '<p><strong>Name: </strong>' . $name . '<br /><strong>Date: </strong>' . $date .
'<br /><strong>Score: </strong>' . $score . '</p>';
echo '<form method="post" action="approvescore.php">';
echo '<img src="' . GW_UPLOADPATH . $screenshot . '" width="160" alt="Score image" /><br />';
echo '<input type="radio" name="confirm" value="Yes" /> Yes ';
echo '<input type="radio" name="confirm" value="No" checked="checked" /> No <br />';
echo '<input type="submit" value="Submit" name="submit" />';
echo '<input type="hidden" name="id" value="' . $id . '" />';
echo '<input type="hidden" name="name" value="' . $name . '" />';
echo '<input type="hidden" name="score" value="' . $score . '" />';
echo '</form>';
} echo '<p><a href="admin.php"><< Back to admin page</a></p>';
?> </body>
</html>
/*** appvars.php ***/
<?php
// Define application constants
define('GW_UPLOADPATH', 'images/');
define('GW_MAXFILESIZE', 32768); // 32 KB
?>
/*** connectvars.php ***/
<?php
// Define database connection constants
define('DB_HOST', 'localhost');
define('DB_USER', 'root');
define('DB_PASSWORD', 'root');
define('DB_NAME', 'gwdb');
?>
/*** admin.php ***/
<?php
require_once('authorize.php');
?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Guitar Wars - High Scores Administration</title>
<link rel="stylesheet" type="text/css" href="style.css" />
</head>
<body>
<h2>Guitar Wars - High Scores Administration</h2>
<p>Below is a list of all Guitar Wars high scores. Use this page to remove scores as needed.</p>
<hr /> <?php
require_once('appvars.php');
require_once('connectvars.php'); // Connect to the database
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME); // Retrieve the score data from MySQL
$query = "SELECT * FROM guitarwars ORDER BY score DESC, date ASC";
$data = mysqli_query($dbc, $query); // Loop through the array of score data, formatting it as HTML
echo '<table>';
echo '<tr><th>Name</th><th>Date</th><th>Score</th><th>Action</th></tr>';
while ($row = mysqli_fetch_array($data)) {
// Display the score data
echo '<tr class="scorerow"><td><strong>' . $row['name'] . '</strong></td>';
echo '<td>' . $row['date'] . '</td>';
echo '<td>' . $row['score'] . '</td>';
echo '<td><a href="removescore.php?id=' . $row['id'] . '&date=' . $row['date'] .
'&name=' . $row['name'] . '&score=' . $row['score'] .
'&screenshot=' . $row['screenshot'] . '">Remove</a>';
if ($row['approved'] == '0') {
echo ' / <a href="approvescore.php?id=' . $row['id'] . '&date=' . $row['date'] .
'&name=' . $row['name'] . '&score=' . $row['score'] . '&screenshot=' .
$row['screenshot'] . '">Approve</a>';
}
echo '</td></tr>';
}
echo '</table>'; mysqli_close($dbc);
?> </body>
</html>
/*** removescore.php ***/
<?php
require_once('authorize.php');
?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Guitar Wars - Remove a High Score</title>
<link rel="stylesheet" type="text/css" href="style.css" />
</head>
<body>
<h2>Guitar Wars - Remove a High Score</h2> <?php
require_once('appvars.php');
require_once('connectvars.php'); if (isset($_GET['id']) && isset($_GET['date']) && isset($_GET['name']) && isset($_GET['score']) && isset($_GET['screenshot'])) {
// Grab the score data from the GET
$id = $_GET['id'];
$date = $_GET['date'];
$name = $_GET['name'];
$score = $_GET['score'];
$screenshot = $_GET['screenshot'];
}
else if (isset($_POST['id']) && isset($_POST['name']) && isset($_POST['score'])) {
// Grab the score data from the POST
$id = $_POST['id'];
$name = $_POST['name'];
$score = $_POST['score'];
}
else {
echo '<p class="error">Sorry, no high score was specified for removal.</p>';
} if (isset($_POST['submit'])) {
if ($_POST['confirm'] == 'Yes') {
// Delete the screen shot image file from the server
@unlink(GW_UPLOADPATH . $screenshot); // Connect to the database
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME); // Delete the score data from the database
$query = "DELETE FROM guitarwars WHERE id = $id LIMIT 1";
mysqli_query($dbc, $query);
mysqli_close($dbc); // Confirm success with the user
echo '<p>The high score of ' . $score . ' for ' . $name . ' was successfully removed.';
}
else {
echo '<p class="error">The high score was not removed.</p>';
}
}
else if (isset($id) && isset($name) && isset($date) && isset($score)) {
echo '<p>Are you sure you want to delete the following high score?</p>';
echo '<p><strong>Name: </strong>' . $name . '<br /><strong>Date: </strong>' . $date .
'<br /><strong>Score: </strong>' . $score . '</p>';
echo '<form method="post" action="removescore.php">';
echo '<input type="radio" name="confirm" value="Yes" /> Yes ';
echo '<input type="radio" name="confirm" value="No" checked="checked" /> No <br />';
echo '<input type="submit" value="Submit" name="submit" />';
echo '<input type="hidden" name="id" value="' . $id . '" />';
echo '<input type="hidden" name="name" value="' . $name . '" />';
echo '<input type="hidden" name="score" value="' . $score . '" />';
echo '</form>';
} echo '<p><a href="admin.php"><< Back to admin page</a></p>';
?> </body>
</html>
/*** style.css ***/
.error {
font-weight: bold;
color: #FF0000;
}
.topscoreheader {
text-align: center;
font-size: 200%;
background-color: #36407F;
color: #FFFFFF;
}
.score {
font-size:150%;
color: #36407F;
}
.scoreinfo {
vertical-align: top;
padding-right:15px;
}
#3 working with data stored in files && securing your application (PART II)的更多相关文章
- #3 working with data stored in files && securing your application
This chapter reveals that you can use files and databases together to build PHP application that waa ...
- Enabling granular discretionary access control for data stored in a cloud computing environment
Enabling discretionary data access control in a cloud computing environment can begin with the obtai ...
- 安装mysql时出现initialize specified but the data directory has files in in.Aborting.该如何解决
eclipse中写入sql插入语句时,navicat中显示的出现乱码(???). 在修改eclipse工作空间编码.navicate中的数据库编码.mysql中my.ini中的配置之后还是出现乱码. ...
- The multi-part request contained parameter data (excluding uploaded files) that exceeded the limit for maxPostSize set on the associated connector.
springboot 表单体积过大时报错: The multi-part request contained parameter data (excluding uploaded files) tha ...
- Springboot 上传报错: Failed to parse multipart servlet request; nested exception is java.lang.IllegalStateException: The multi-part request contained parameter data (excluding uploaded files) that exceede
Failed to parse multipart servlet request; nested exception is java.lang.IllegalStateException: The ...
- MYSQL常见安装错误集:[ERROR] --initialize specified but the data directory has files in it. Abort
1.[ERROR] --initialize specified but the data directory has files in it. Abort [错误] -初始化指定,但数据目录中有文件 ...
- 启动MySQL5.7时报错:initialize specified but the data directory has files in it. Aborting.
启动MySQL5.7时报错:initialize specified but the data directory has files in it. Aborting 解决方法: vim /etc/m ...
- Data caching per request in Owin application
Data caching per request in Owin application 解答1 Finally I found OwinRequestScopeContext. Very simpl ...
- Fast data loading from files to R
Recently we were building a Shiny App in which we had to load data from a very large dataframe. It w ...
随机推荐
- 原生css3作响应式布局
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <m ...
- Java图形界面开发—简易记事本
在学习了Java事件之后,自己写了一个极其简单的记事本.用到了MenuBar,Menu,MenuITem等控件,事件包括ActionListener以及KeyListener. 代码如下: ...
- [转] eclipce使用vim 开启装逼模式
原文:http://blog.csdn.net/fatal360/article/details/12321613 1.在eclipse中使用vi模式的插件Vrapper打开eclipse,在Help ...
- 菜鸟 学注册机编写之 “sha1”
1. 首先运行程序随便输入用户与注册码如下图所示: 2.将程序载入OD, 下MessageBoxA函数断点, F9运行程序, 程序运行后随便输入用户名与注册码,点"OK"后断下,F ...
- 【Android开发笔记】生命周期研究
启动 onCreate onStart onResume 退出键 onPause onStop onDestroy 锁屏 & 按住 home键 & 被其他Activity覆盖(Sing ...
- 服网LNMP集群 w/ MySQL PaaS-1.0
平台: arm 类型: ARM 模板 软件包: haproxy linux mysql nginx application server arm basic software fuwang infra ...
- sql server 2016新特性 查询存储(Query Store)的性能影响
前段时间给客户处理性能问题,遇到一个新问题, 客户的架构用的是 alwayson ,并且硬件用的是4路96核心,内存1T ,全固态闪存盘,sql server 2016 . 问题 描述 客户经常出现 ...
- nginx 升级为最新版 nginx -1.12.0
标签:nginx 公司目前使用的nginx版本比较低(nginx-1.0.12),请网络安全公司做了一下“远程安全评估”,发现有下列漏洞: nginx URI处理安全限制绕过漏洞(CVE-2013-4 ...
- Python爬虫实战:爬糗事百科的段子
一个偶然的机会接触了Python,感觉很好用,但是一直在看c++啥的,也没系统学习.用过之后也荒废了许久.之前想建个公众号自动爬糗事百科的段子,但是没能建起来,真是尴尬,代码上传的服务器上之后,不能正 ...
- HDU5200 数据离线处理
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5200 ,数据离线处理. 这是BestCoder Round #36的C题,比赛时自己用线段树做,姿势不 ...