获取用户Ip地址通用方法与常见安全隐患(HTTP_X_FORWARDED_FOR)


Posted in PHP onJune 01, 2013

分析过程
这个来自一些项目中,获取用户Ip,进行用户操作行为的记录,是常见并且经常使用的。 一般朋友,都会看到如下通用获取IP地址方法。

function getIP() { 
if (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) { 
$realip = $_SERVER['HTTP_X_FORWARDED_FOR']; 
} elseif (isset($_SERVER['HTTP_CLIENT_IP'])) { 
$realip = $_SERVER['HTTP_CLIENT_IP']; 
} else { 
$realip = $_SERVER['REMOTE_ADDR']; 
} 
return $realip; 
}

这个是网上常见获取,ip函数,用这些值获取IP,我们首先要弄清楚,这些数据是从那个地方传过来的。

IP获取来源

1.'REMOTE_ADDR' 是远端IP,默认来自tcp 连接是,客户端的Ip。可以说,它最准确,确定是,只会得到直接连服务器客户端IP。如果对方通过代理服务器上网,就发现。获取到的是代理服务器IP了。

如:a->b(proxy)->c ,如果c 通过'REMOTE_ADDR' ,只能获取到b的IP,获取不到a的IP了。

另外:该IP想篡改将很难实现,在传递知道生成php server值,都是直接生成的。

2.'HTTP_X_FORWARDED_FOR','HTTP_CLIENT_IP' 为了能在大型网络中,获取到最原始用户IP,或者代理IP地址。对HTTp协议进行扩展。定义了实体头。

HTTP_X_FORWARDED_FOR = clientip,proxy1,proxy2 所有IP用”,”分割。 HTTP_CLIENT_IP 在高级匿名代理中,这个代表了代理服务器IP。既然是http协议扩展一个实体头,并且这个值对于传入端是信任的,信任传入方按照规则格式输入的。以下以x_forword_for例子加以说明,正常情况下,这个值变化过程。

获取用户Ip地址通用方法与常见安全隐患(HTTP_X_FORWARDED_FOR)

分析Bug风险点:

通过刚刚分析我们发现,其实这些变量,来自http请求的:x-forword-for字段,以及client-ip字段。 正常代理服务器,当然会按rfc规范来传入这些值。但是,当一个用户直接构造该x-forword-for值,发送给用户用户,那将会怎么样呢?

获取用户Ip地址通用方法与常见安全隐患(HTTP_X_FORWARDED_FOR)图(1)

第2步,修改x-forword-fox值,我们看看结果

获取用户Ip地址通用方法与常见安全隐患(HTTP_X_FORWARDED_FOR)

 

第三步,我们再修改下看看会怎么样?

获取用户Ip地址通用方法与常见安全隐患(HTTP_X_FORWARDED_FOR)

 

哈哈,看到上面结果没,x-forwarded-for不光可以自己设置值,而且可以设置任意格式值。 这样一来,好比就直接有一个可以写入任意值的字段。并且服务器直接读取,或者写入数据库,或者做显示。它将带来危险性,跟一般对入输入没有做任何过滤检测,之间操作数据源结果一样。 并且容易带来隐蔽性。

结论:

上面getip函数,除了客户端可以任意伪造IP,并且可以传入任意格式IP。 这样结果会带来2大问题,其一,如果你设置某个页面,做IP限制。 对方可以容易修改IP不断请求该页面。 其二,这类数据你如果直接使用,将带来SQL注册,跨站攻击等漏洞。至于其一,可以在业务上面做限制,最好不采用IP限制。 对于其二,这类可以带来巨大网络风险。我们必须加以纠正。

需要对getip 进行修改,得到安全的getip函数。

这类问题,其实很容易出现,以前我就利用这个骗取了大量伪装投票。有它的隐蔽性,其实只要我们搞清楚了,某些值来龙去脉的话。理解了它的原理,修复该类bug将是非常容易。

题外话,做技术,有三步,先要会做,会解决;后要思考为什么要这么做,原因原理是什么;最后是怎么样做,有没有其它方法。多问问自己,你发现距离技术真理越来越近。你做事会越来越得心应手的!

作者:chengmo QQ:8292669

PHP 相关文章推荐
用php来检测proxy
Oct 09 PHP
从网上搜到的phpwind 0day的代码
Dec 07 PHP
php安装xdebug/php安装pear/phpunit详解步骤(图)
Dec 22 PHP
smarty简单入门实例
Nov 28 PHP
PHP中调用SVN命令更新网站方法
Jan 07 PHP
JSON两种结构之对象和数组的理解
Jul 19 PHP
php is_writable判断文件是否可写实例代码
Oct 13 PHP
php加密解密字符串示例
Oct 13 PHP
掌握PHP垃圾回收机制详解
Mar 13 PHP
TP5框架model常见操作示例小结【增删改查、聚合、时间戳、软删除等】
Apr 05 PHP
TP5框架model常见操作示例小结【增删改查、聚合、时间戳、软删除等】
Apr 05 PHP
安装PHP扩展时解压官方 tgz 文件后没有configure文件无法进行配置编译的问题
Aug 26 PHP
php源代码安装常见错误与解决办法分享
May 28 #PHP
如何批量替换相对地址为绝对地址(利用bat批处理实现)
May 27 #PHP
php 深入理解strtotime函数的使用详解
May 23 #PHP
如何使用PHP计算上一个月的今天
May 23 #PHP
解析php二分法查找数组是否包含某一元素
May 23 #PHP
PHP下打开phpMyAdmin出现403错误的问题解决方法
May 23 #PHP
php设计模式之观察者模式的应用详解
May 21 #PHP
You might like
PHP array 的加法操作代码
2010/07/24 PHP
ThinkPHP模板判断输出Defined标签用法详解
2014/06/30 PHP
PHP查看当前变量类型的方法
2015/07/31 PHP
PHP如何使用Memcached
2016/04/05 PHP
php远程下载类分享
2016/04/13 PHP
Yii框架引用插件和ckeditor中body与P标签去除的方法
2017/01/19 PHP
javascript 单选框,多选框美化代码
2008/08/01 Javascript
微博@符号的用户名提示效果。(想@到谁?)
2010/11/05 Javascript
js中关于new Object时传参的一些细节分析
2011/03/13 Javascript
关于query Javascript CSS Selector engine
2013/04/12 Javascript
红米手机抢购的js代码
2014/03/10 Javascript
jQuery入门介绍之基础知识
2015/01/13 Javascript
js实现正则匹配中文标点符号的方法
2015/12/23 Javascript
大型JavaScript应用程序架构设计模式
2016/06/29 Javascript
轻松掌握JavaScript单例模式
2016/08/25 Javascript
百度地图JavascriptApi Marker平滑移动及车头指向行径方向
2017/03/13 Javascript
BootStrap Table前台和后台分页对JSON格式的要求
2017/06/28 Javascript
原生js 封装get ,post, delete 请求的实例
2017/08/11 Javascript
js 毫秒转天时分秒的实例
2017/11/17 Javascript
three.js中文文档学习之创建场景
2017/11/20 Javascript
如何将HTML字符转换为DOM节点并动态添加到文档中详解
2018/08/19 Javascript
最适应的vue.js的form提交涉及多种插件【推荐】
2018/08/27 Javascript
vue使用openlayers实现移动点动画
2020/09/24 Javascript
Python中操作mysql的pymysql模块详解
2016/09/13 Python
Python中最大最小赋值小技巧(分享)
2017/12/23 Python
Python 字符串转换为整形和浮点类型的方法
2018/07/17 Python
python游戏地图最短路径求解
2019/01/16 Python
详解Python下载图片并保存本地的两种方式
2019/05/15 Python
python覆盖写入,追加写入的实例
2019/06/26 Python
Python 实现平台类游戏添加跳跃功能
2020/03/27 Python
Python通过文本和图片生成词云图
2020/05/21 Python
Python2与Python3关于字符串编码处理的差别总结
2020/09/07 Python
GUESS Factory加拿大:牛仔裤、服装及配饰
2019/09/20 全球购物
大学生个人简历中的自我评价
2013/12/27 职场文书
广告传媒专业应届生求职信
2014/03/01 职场文书
自荐信怎么写
2015/03/04 职场文书