[BJDCTF2020]ZJCTF,不过如此1 [php://filter][正则表达式get输入数据][捕获组反向引用][php中单双引号]

news/2025/3/5 5:35:19/

题目: 

 我仿佛见到了一位故人。。。也难怪,题目就是ZJCTF

按要求提交/?text=data://,I have a dream&file=next.php后: 

......不太行,好像得用file=php://filter/convert.base64-encode/resource=next.php 

耶?那 file=php://filter/convert.base64-encode/resource=next.php 和 file=next.php在这里有啥区别啊 

file=php://filter/convert.base64-encode/resource=next.php 和 file=next.php

示例:如果next.php为 <?php echo "hello"; ?>

1.file=next.php: 直接输出hello(include函数会将括号内的文件内容当作php来解析)

2.file=php://filter/convert.base64-encode/resource=next.php

  • php://filter 是PHP的流包装器,允许在读取文件时对内容进行过滤处理。
  • convert.base64-encode 过滤器会将文件内容转换为Base64编码格式。
  • 当使用 include 包含此路径时,PHP会先读取 next.php 的内容,经过Base64编码后,再尝试将编码后的内容作为PHP代码执行。

关键点在于base64编码后的东西不再是有效代码,php无法解析,在面对无效代码这种情况下php可能会将编码后的内容作为“原始输出”返回

这样就能直接返回next.php的源代码了 

 源代码

<?php
$id = $_GET['id'];
$_SESSION['id'] = $id;function complex($re, $str) {return preg_replace('/(' . $re . ')/ei','strtolower("\\1")',$str);
}foreach($_GET as $re => $str) {echo complex($re, $str). "\n";
}function getFlag(){@eval($_GET['cmd']);
}

代码一些地方需要注意:

preg_replace('/(' . $re . ')/ei','strtolower("\\1")',$str);

preg_replace($要搜索的正则表达式的模式, $用于替换匹配项的字符串, $被进行搜索和替换的字符串); 所以关于这里的正则表达式模块:'/('.$re.')/ei',

注意preg_replace在调用的时候需要将参数用 ' ' 括起来

其中$re代表用户传入的正则表达式模式,通过字符串拼接的方式,将$re嵌入到整体正则表达式中  / 用于表示正则表达式的开始和结束,( 和 ):是捕获组的符号,用于将匹配到的内容捕获起来,以便后续引用,e 修饰符会使 preg_replace 在替换字符串时执行其中的 PHP 代码,i 修饰符表示不区分大小写进行匹配。

strtolower("\\1")

\\1:这是对捕获组的引用,代表第一个捕获组匹配到的内容。strtolower用于将字符串转换为小写。所以这句话意思是将捕获到的内容转换成小写

捕获组和反向引用

主要用于引用之前匹配的捕获组的内容。它允许在同一个正则表达式中复用已匹配的文本,常用于模式重复匹配或替换操作。

捕获组:()括起来的内容就是捕获组,比如说(\d+)匹配一个或者多个内容,并记录匹配的内容

反向引用:\n 表示引用第n个捕获组的内容

foreach函数触发漏洞

遍历$_GET数组,键名作为$re,键值作为$str,并将这两个值传入complex函数中

foreach($_GET as $re => $str) {echo complex($re, $str). "\n";
}

对于php中双引号和单引号的区别

双引号:

<?php echo "{${phpinfo()}}"; ?>

会返回phpinfo的界面 

因为双引号里面如果包含有变量,php解释器会将其替换为变量解释后的结果(允许变量解析)。任何 ${...} 内的表达式会被执行,其返回值作为变量名

具体实现:

  1. phpinfo() 函数会被立即执行,输出PHP配置信息(返回值为 true,即 1)。
  2. PHP尝试解析 ${phpinfo()} 的结果(即 1),等价于变量 $1
  3. 由于变量名 $1 非法(不能以数字开头),会触发一个 Notice级错误(若未关闭错误提示),最终输出空字符串。

实际效果

输出 phpinfo() 的完整信息。输出空字符串(因 $1 未定义),并可能伴随错误提示。

单引号:

<?php echo '{${phpinfo()}}'; ?>

单引号内不解析变量,所以内容按字面量输出  {${phpinfo()}}

再返回到next.php中,其基本思路就是get个键名键值都是自己输入的东西&cmd命令,其中get内容要触发getflag()函数进而触发eval()函数,cmd才有用武之地

php会将传入的非法的参数名转成下滑线

当非法字符为首字母时,只有点号会被替换成下划线 

 上传的$re=$str,传入  .*=${getflag()}   代入代码中就是:

preg_replace('/(.*)/ei','strtolower("\\1")',${getflag()});

getflag() 是一个函数调用,意味着会先执行 getflag 函数,然后将该函数的返回值作为目标字符串传递给 preg_replace 进行处理。

也就是说会这样

好傻啊这个函数,还会先跑去执行一下代码然后再匹配,怪不得e被弃用了 

残留几个问题:

1.为什么要加上${  }? ,这个东西有什么用?

${ }用于变量替换、字符串模板、表达式嵌入

这里${getflag()}外面套上一个${ }就表示执行函数,如果不套这个${ }那么就变成

strtolower("getflag()")

此时单纯把这个当成字符串,而不能把他当成函数去解析

2.为什么 \S* 能表示 .? ?

因为大写表示取反操作

这里\s 表示匹配任意空白字符,而\S表示匹配任意非空白字符(等价于 [^\s]

3.捕获组和反向引用干什么用的?

主要是为了匹配重复的字符,比如说

\b(\w+)\b\s+\1\b

\b表示单词边界,\w表示任意一个单词字符,+是个量词,表示前面的 \w 可以出现很多次,\s+表示任意一个或多个空白符号

这里就能匹配到诸如"pig pig"这样的字符串

也可以匹配标签,这里的 < 和 > 都代表真实的<>

<([a-z]+)>(.*?)</\1>

反向引用还在输出! 


http://www.ppmy.cn/news/1576743.html

相关文章

android接入rocketmq

一 前言 RocketMQ 作为一个功能强大的消息队列系统&#xff0c;不仅支持基本的消息发布与订阅&#xff0c;还提供了顺序消息、延时消息、事务消息等高级功能&#xff0c;适应了复杂的分布式系统需求。其高可用性架构、多副本机制、完善的运维管理工具&#xff0c;以及安全控制…

关于常规模式下运行VScode无法正确执行“pwsh”问题

前言&#xff1a; pwsh在系统环境中正确配置&#xff0c;且可以运行在cmd&#xff0c; powshell&#xff08;5.1&#xff09;--- 都需要在管理员权限下运行 &#xff08;打开setting&#xff09; 打开setting.json &#xff08;在vscode中添加 powershell 7 路径&…

字节旗下两款AI编程工具

Trae 和 MarsCode 是字节跳动推出的两款 AI 编程工具,旨在通过人工智能技术提升开发效率和质量。以下是它们的详细介绍: 1 Trae Trae 是字节跳动于 2025 年 1 月推出的 AI 原生集成开发环境(IDE),由旗下新加坡公司 SPRING PTE 开发。它主打“用自然语言生成代码”,具备…

贪心算法+题目

贪心算法 跳跃游戏跳跃游戏2 跳跃游戏 题目 拿到题目就暴力穷举&#xff0c;我用的是dfs&#xff0c;加上备忘录之后还是超出时间限制。就考虑一下贪心算法。你想 我在[0,n-2]位置遍历求出可以跳跃的最远距离&#xff0c;用farthest更新最大值&#xff0c;如果>终点就返回t…

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_conf_read_token

ngx_conf_read_token 定义在src\core\ngx_conf_file.c static ngx_int_t ngx_conf_read_token(ngx_conf_t *cf) {u_char *start, ch, *src, *dst;off_t file_size;size_t len;ssize_t n, size;ngx_uint_t found, need_space, last_space, sharp_comm…

7.1.2 计算机网络的分类

文章目录 分布范围交换方式 分布范围 计算机网络按照分布范围可分为局域网、广域网、城域网。局域网的范围在10m~1km&#xff0c;例如校园网&#xff0c;网速高&#xff0c;主要用于共享网络资源&#xff0c;拓扑结构简单&#xff0c;约束少。广域网的范围在100km&#xff0c;例…

Windows10 Xming6 + Xshell7 实现远程 ubuntu-24.04.1-desktop gui 界面本地展示

Windows10 Xming6 + Xshell7 实现远程 ubuntu-24.04.1-desktop gui 界面本地展示 1 运行环境2 实现思路3 XMing3.1 工具下载安装与配置3.2 XMing 配置3.3 XMing配置4 Xshell 7 配置5 远程机器配置6 测试1 运行环境 本地Windows系统:Windows10 专业版 远程Linux系统: ubuntu-…

AI本地化部署强劲驱动GPU,LPU等AI芯片和服务器的爆发性寻求

人工智能技术正在经历从云端到边缘的深刻变革&#xff0c;这一转变催生了AI基础设施建设的全新需求。在数据安全、实时响应和成本优化的多重驱动下&#xff0c;AI本地化部署已成为不可逆转的趋势&#xff0c;推动GPU、LPU等AI芯片及配套服务器系统进入爆发性增长周期。这场变革…