受影响系统:
phpShop phpShop 0.6.1-b
详细描述:
phpShop是一款基于PHP的电子商务程序,可方便的扩展WEB功能。phpShop存在多个安全问题,远程攻击者可以利用这些漏洞攻击数据库,获得敏感信息,执行任意脚本代码。
具体问题如下:
1、SQL注入漏洞:
当更新会话时存在一个SQL注入问题,可以对"page"变量提交恶意SQL命令而修改原有SQL逻辑,同样对"product_id"和"offset"变量进行注入也存在同样问题。
2、用户信息泄露漏洞:
通过查询"account/shipto"模块,可获得大量客户信息。如果用户以合法帐户登录,也可能查看管理员信息。这些信息包括客户的地址,公司名等等信息。
3、跨站脚本执行攻击:
多个参数对用户提交的URI参数缺少充分过滤,提交包含恶意HTML代码的数据,可导致触发跨站脚本攻击,可能获得目标用户的敏感信息。
目前厂商还没有提供补丁或者升级程序。
通过一个小时的研究和设置.实现了最新的 PHP 5.0 + MYSQL 5.0 + WIN2003.
个人认为还是有必要写个教程出来.因为很多方面和老版本的不尽相同.
说实话自己也是查阅了很多官方文档才解决了很多怪异问题.
=========================
相关软件均可以在 WWW.SKYCN.NET 下载.
MYSQL 5.0 FOR WINDOWS
PHP 5.0 FOR WINDOWS
PHPMYADMIN
WINDOWS SERVER 2003
=========================
首先安装 MYSQL .本来以为新版本的安装界面应该会花哨点.
但是仍然只看到老土的海豚.除了安装时间比 4.0 长.当然咯.因为 5.0 比 4.0 体积大很多.
推荐安装在独立的 NTFS 分区上.比如我服务器的 F盘.只放服务器软件.
路径为: F:\MYSQL\
然后进入 F:\MYSQL\BIN\ 鼠标双点 winmysqladmin.exe
首次运行会提示输入超级用户和密码.就输入 root 密码 root
注意啊.如果是对外服务器请设置超级复杂.比如 Wjwsfjn29szjwh~mysql
翻译过来就是: 我叫魏舒芬.今年29岁至今未婚.
到这里.MYSQL就安装完毕了.如果不明白请参看深空同学的相关文章.
=========================
下面安装 PHP 5.0 其实没什么安装不安装的.解压缩文件.推荐放到
路径为: F:\PHP\
到这里就应该进入关键步骤了.
首先复制 PHP 目录下的 Php.ini-dist 到 C:\Windows\ 并将文件名修改成为 Php.ini
COPY F:\PHP\Php.ini-dist C:\Windows
Ren Php.ini-dist Php.ini
如果是 WINDOWS 2000 就是: C:\WINNT\
如果是 WIN9X / 2003 就是: C:\Windows\
然后复制 PHP 目录下 DLLS 目录里的所有文件到 SYSTEM32 目录.
COPY F:\PHP\dlls\*.* C:\Windows\System32\
如果是 WINDOWS 2000 就是: C:\WINNT\System32\
如果是 WIN9X / 2003 就是: C:\Windows\System32\
继续.复制PHP目录下 php4ts.dll 文件到 System32 目录里.
COPY F:\PHP\php4ts.dll C:\Windows\System32\
=========================
到这里复制工作全部完成.下面修改 C:\Windows\Php.ini 文件.
请注意.5.0的版本修改与4.0并不完全相同.需要注意的如下.
查找 extension_dir 字串.修改为你 PHP 目录里 extensions 的路径.
; Directory in which the loadable extensions (modules) reside.
extension_dir = F:\PHP\extensions
相关官方技术资料:
Edit your php.ini file:
You will need to change the 'extension_dir' setting to
point to your php-install-dir, or where you have placed
your 'php_*.dll' files. ex: c:\php
If you are using OmniHTTPd, do not follow the next step.
Set the 'doc_root' to point to your webservers
document_root. ex: c:\apache\htdocs or c:\webroot
Choose which extensions you would like to load when PHP
starts, noting that several extensions are already built
into the Windows release, see the section about
Windows extensions for details of the built-in extensions.
You can uncomment the: 'extension=php_*.dll' lines
in php.ini to load these extensions.
Note that on a new installation it is advisable to first get
PHP working and tested without any extensions before enabling
them in php.ini.
On PWS and IIS, you can set the browscap.ini
to point to: 'c:\windows\system\inetsrv\browscap.ini' on
Windows 9x/Me and 'c:\winnt\system32\inetsrv\browscap.ini'
on NT/2000/XP Server.
More information on the capabilities of browscap can be found here:
www.php.net/manual/en/function.get-browser.php
Note that the mibs directory supplied with the Windows distribution
contains support files for SNMP. This directory should be moved to
DRIVE:\usr\mibs (DRIVE being the drive where PHP is installed.)
然后与 PHP 4.0 不同的是.需要修改 Php.ini 文件里的如下内容:
查找 cgi.force_redirect 字串.默认值为1.将其修改为0.并取消前面的;号.
即:
; cgi.force_redirect is necessary to provide security running PHP as a CGI under
; most web servers. Left undefined, PHP turns this on by default. You can
; turn it off here AT YOUR OWN RISK
; **You CAN safely turn this off for IIS, in fact, you MUST.**
cgi.force_redirect = 0
切记如上修改的地方.否则PHP 5.0是无法运行的.会有如下提示.
Security Alert! The PHP CGI cannot be accessed directly.
相关官方技术资料:
!NOTE!: Since 4.1.2, the php.ini setting cgi.force_redirect defaults to '1'
which effectively prevents the cgi from working within IIS. You need to set
up at least a minimal php.ini file with the following directive:
cgi.force_redirect = 0
If it doesn't work immidiately, make sure you have the php.ini file in the
right place (%SYSTEMROOT%\php.ini).
接下来修改 Php.ini 文件关于 MYSQL 5.0 的设置.
查找 [MySQL] 字段内的内容.修改如下.
mysql.default_port = 3306
// 这里是MYSQL的端口.
mysql.default_host = localhost
// 这里是本地主机.
mysql.default_user = root
// 这里是用户
mysql.default_password = Wjwsfjn29szjwh~mysql
// 这里是密码
修改到这里就可以让 Php 与 MYSQL 关联了.
最后启动 PHP 对 MYSQL 模块支持.
查找 extension=php_mysql.dll 字串.删除掉前面的 ; 号
extension=php_mysql.dll
请注意.如果不启动 PHP 对 MYSQL 模块支持.将无法使 PHPMYADMIN 正常工作.将提示:
cannot load MySQL extension, please check PHP Configuration
无法装入 MySQL 扩展,请检查 PHP 的配置。
相关官方技术资料:
To connect to a MySQL server, PHP needs a set of MySQL functions called "MySQL extension".
This extension may be part of the PHP distribution (compiled-in), otherwise it needs to be loaded dynamically.
Its name is probably mysql.so or php_mysql.dll. phpMyAdmin tried to load the extension but failed.
=========================
到这里应该就没有很大问题了.如果有配置基础的朋友应该完全可以理解了.
本人在实际配置的时候也遇到了很多问题.最后都是耐心查询官方文档得到了解决.
这是在看太平洋网的评论时看到的,太平洋网是用jsp做为后台语言,用来产生xml文件.然后在把数据绑定到html上的.我就用php也做了一个以下是源文件.
-----------------xml.htm------------------
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312">
<title>xml</title>
</head>
<body>
<xml id="ShopList" src="/blog_article/xml.html"></xml>
<script>
function jump(form)
{
if (form.pageNum.value>parseInt(pageCount.innerHTML)) return false;
if (form.pageSize.value>parseInt(recordCount.innerHTML)) return false;
ShopList.src="/blog_article/xml/pageNo/.html"+form.pageNum.value+"&pageSize="+form.pageSize.value+"&time="+(new Date()).getTime();
}
function pageCount_onpropertychange(form)
{
if (form.pageNum.value>parseInt(pageCount.innerHTML)) form.pageNum.value=parseInt(pageCount.innerHTML);
if (form.pageSize.value>parseInt(recordCount.innerHTML)) form.pageSize.value=parseInt(recordCount.innerHTML);
if(form.pageNum.value==1)
{
form.firstPage.disabled=true;
form.previousPage.disabled=true;
}
else
{
form.firstPage.disabled=false;
form.previousPage.disabled=false;
}
if(form.pageNum.value==form.pageCount.value)
{
form.nextPage.disabled=true;
form.lastPage.disabled=true;
}
else
{
form.nextPage.disabled=false;
form.lastPage.disabled=false;
}
}
</script>
<table width="100%" height="25" border="0" cellpadding="2" cellspacing="1" id="shopTbl" datasrc=#ShopList datafld=商铺>
<thead>
<tr>
<td height="25" colspan="4"><span >店铺列表</span></td>
</tr>
<tr>
<td width="30%">商铺名称</td>
<td width="20%">经营者</td>
<td width="20%">店铺级别</td>
<td width="30%">店铺简介</td>
</tr>
</thead>
<tbody>
<tr #EFEFEF':'#FFFFFF')">
<td><a datafld="连接地址"><span datafld="名称">名称</span></a></td>
<td><span datafld="经营人">经营人</span></td>
<td><span datafld="级别">级别</span></td>
<td><span datafld="简介">简介</span></td>
</tr>
</tbody>
</table>
<form return onsubmit="jump(this);return false">
<div align="right">
每页显示
<input name=pageSize datasrc=#ShopList datafld=页大小 size=2>条,
<input type=submit value="" >
共<span id="pageCount" datasrc=#ShopList datafld=页数量></span>页
<span id="recordCount" datasrc=#ShopList datafld=数量 ></span>条
<input name=firstPage type=submit value=首页 onclick="pageNum.value=1">
<input name=previousPage type=submit value=上页 onclick="pageNum.value=pageNum.value-1">
第<input name=pageNum datasrc=#ShopList datafld=页号码 size=2>页
<input name=nextPage type=submit value=下页 onclick="pageNum.value=(pageNum.value-0)+1">
<input name=lastPage type=submit value=尾页 onclick="pageNum.value=pageCount.value" >
<input name=pageCount type=hidden datasrc=#ShopList datafld=页数量 onpropertychange="pageCount_onpropertychange(form)">
</div> </form>
</body>
</html>
-----------------xml.php------------------
<?php
//require_once "Source/Global.php";
function getVars($get_vars, $post_vars) {
$i = count($get_vars);
$j = count($post_vars);
if ($i > 0 && $j > 0 ) {
while(list($key, $val) = each($get_vars)) {
$Vars[$key] = $val;
}
while(list($key2, $val2) = each($post_vars)) {
$Vars[$key2] = $val2;
}
} elseif ($i > 0) {
while(list($key, $val) = each($get_vars)) {
$Vars[$key] = $val;
}
} elseif ($j > 0) {
while(list($key2, $val2) = each($post_vars)) {
$Vars[$key2] = $val2;
}
} else {
$Vars = array();
}
return $Vars;
}
$vars = getVars($HTTP_GET_VARS, $HTTP_POST_VARS);
//class shoplist_res extends iGlobal{
class shoplist_res{
function shoplist_res($vars,$cookie){
//$this->iGlobal($vars,$cookie);
$this->outPut($vars,$cookie);
}
//function _shoplist_res(){
// $this->db->Close();
//}
function outPut($vars,$cookie){
/*$strQuery = "select count(*) as rc from ".$this->db_c->Db_Pre."pshop order by id desc";
$this->db->Query($strQuery);
$RecordCount = $this->db->Assoc();
$RecordCount = $RecordCount['rc'];
@$this->db->freeResult();*/
$RecordCount = 25;
if (empty($vars['pageNo'])) $vars['pageNo']= 1;
if (empty($vars['pageSize'])) $vars['pageSize']= 10;
$PageCount = ceil($RecordCount/$vars['pageSize']);
if ($vars['pageSize']>$RecordCount) $vars['pageSize']=$RecordCount;
if ($vars['pageNo']>$PageCount) $vars['pageNo']=$PageCount;
$xmlStr.= "<?xml version=\"1.0\" encoding=\"GBK\" ?>"."\n";
$xmlStr.= "<商铺列表>"."\n";
$xmlStr.= "\t<翻页工具 pageNo=\"".$vars['pageNo']."\" pageSize=\"".$vars['pageSize']."\" total=\"".$RecordCount."\"></翻页工具>"."\n";
$xmlStr.= "\t<页号码>".$vars['pageNo']."</页号码>"."\n";
$xmlStr.= "\t<页大小>".$vars['pageSize']."</页大小>"."\n";
$xmlStr.= "\t<数量>".$RecordCount."</数量>"."\n";
$xmlStr.= "\t<页数量>".$PageCount."</页数量>"."\n";
//$strQuery = "select t1.*,t2.* from ".$this->db_c->Db_Pre."pshop as t1,".$this->db_c->Db_Pre."shoptype as t2 where t1.typenum=t2.typenum order by id desc "
// ."limit ".($vars['pageNo']-1)*$vars['pageSize'].",".$vars['pageSize'];
//die($strQuery);
//$this->db->Query($strQuery);
/*while($result = $this->db->Assoc()){
$xmlStr.= "\t"."\n";
$xmlStr.= "\t<商铺>"."\n";
$xmlStr.= "\t\t<名称><![CDATA[".$result['shopname']."]]></名称>"."\n";
$xmlStr.= "\t\t<经营人><![CDATA[".$result['shopmaster']."]]></经营人>"."\n";
$xmlStr.= "\t\t<级别><![CDATA[".$result['shoptype']."]]></级别>"."\n";
$xmlStr.= "\t\t<简介><![CDATA[".$result['shopintro']."]]></简介>"."\n";
$xmlStr.= "\t\t<连接地址><![CDATA[personal_shop.php?id=".$result['id']."]]></连接地址>"."\n";
$xmlStr.= "\t</商铺>"."\n";
}*/
$sc= $vars['pageNo']*$vars['pageSize'];
if ($sc>$RecordCount) $sc = $RecordCount;
for($i=($vars['pageNo']-1)*$vars['pageSize'];$i<$sc;$i++){
$xmlStr.= "\t"."\n";
$xmlStr.= "\t<商铺>"."\n";
$xmlStr.= "\t\t<名称><![CDATA[这是名称:".$i."]]></名称>"."\n";
$xmlStr.= "\t\t<经营人><![CDATA[这是经营人:".$i."]]></经营人>"."\n";
$xmlStr.= "\t\t<级别><![CDATA[这是级别:".$i."]]></级别>"."\n";
$xmlStr.= "\t\t<简介><![CDATA[这是简介:".$i."]]></简介>"."\n";
$xmlStr.= "\t\t<连接地址><![CDATA[personal_shop.php?id=".$i."]]></连接地址>"."\n";
$xmlStr.= "\t</商铺>"."\n";
}
$xmlStr.= "</商铺列表>"."\n";
header("Content-type: text/xml\n\n");
echo $xmlStr;
}
}
$shoplist = new shoplist_res($vars,$HTTP_COOKIE_VARS);
//$shoplist->_shoplist_res();
unset($sthoplist);
?>
以上的php,注释的是我连接数据库取得的数据,既然放上来测试,也没有数据库连接,所以改了一下.偶也是刚接解xml不久,很多地方还是不很懂.见笑了......