>[info]Json劫持漏洞
Json劫持漏洞主要是針對接口返回JSONP或JSON這類數據處理不夠存在的安全隱患。
當前政務內網安全評測監測JSON劫持主要是通過canllback handle傳入特殊構造的非法字符,例如傳入callback=jsonp9527,如果在返回的結果中匹配到特征碼^jsonp9527999\(|^\[.*(\];|\])$|^.{1,50}\([\[\{]+".*[\]\}]+\);$則認為存在JSON劫持。當前規則下無法完全根除檢測報告中出現JSON劫持特征碼,但是建議從下面幾個方面入手:
(1)、強化JSONP輸出的handle部分的驗證處理
需要修改\thinkphp\library\think\response\Hsonp.php 24行 output函數
~~~
protected function output($data)
{
try {
// 返回JSON數據格式到客戶端 包含狀態信息 [當url_common_param為false時是無法獲取到$_GET的數據的,故使用Request來獲取<xiaobo.sun@qq.com>]
$Request =Request::instance();
$var_jsonp_handler = $Request->param($this->options['var_jsonp_handler'], "");
$handler = !empty($var_jsonp_handler) ? $var_jsonp_handler : $this->options['default_jsonp_handler'];
//訪問來路驗證
$reffer =$Request->server('HTTP_REFERER');
if(!$reffer){//訪問來路為空(直接輸入URL訪問則不輸出JSPNP數據)
return '非法請求方式';
}else{
$parseInfo =parse_url($reffer);
$host =strtolower($parseInfo['host']);
$domains =parse_url($Request->domain());
if(strtolower($domains['host'])!=strtolower($parseInfo['host'])){
return '非法請求方式!';
}
}
//為了應對安全評測強加的callback handle 規則
if(!preg_match('/^([a-z]+)$/iS',$handler)){
//$handler =$this->options['default_jsonp_handler'];
return '非法的jsonp handle'; //不符合規則時不返回jsonp數據
}
$data = json_encode($data, $this->options['json_encode_param']);
if ($data === false) {
throw new \InvalidArgumentException(json_last_error_msg());
}
$data =escapeshellcmd($handler) . '(' . $data . ');';
return $data;
} catch (\Exception $e) {
if ($e->getPrevious()) {
throw $e->getPrevious();
}
throw $e;
}
}
~~~
此段代碼主要是驗證了訪問來路驗證和輸出的callback handle處理。
(2)、在入口文件中增加防止跨域訪問的驗證處理
~~~
$origins =['yuanan2.demo.neikongcn.com','localhost','api.n3.cn','10.27.29.1','jgfw.yichang.gov.cn'];
$allowOrigin ='localhost';
if(isset($_SERVER['HTTP_ORIGIN']) && in_array($_SERVER['HTTP_ORIGIN'],$origins)){
$allowOrigin =$_SERVER['HTTP_ORIGIN'];
}
header("Access-Control-Allow-Origin: ".$allowOrigin);
~~~
[注意]:hader的設置必須在有任何輸出之前完成。
(3)、盡量要求所有需要返回JSON或者JSONP的接口或控制器先驗證登錄權限后再有數據輸出。