moe图床

发布时间 2023-10-03 17:05:18作者: 努力的大魔王

打开链接就文件上传,直接文件上传题目

而且只能上传后缀为png的文件

 

 刚好最近学了文件上传漏洞的各种形式复现,刚好这把就来试试不找源码直接破解

1. 先F12看看有没有客户端检查函数

 发现没有。看来并不是简单的前端检测

 

2. bp抓包改后缀名

 检测出来了

 

 

3. 文件后缀加“.”绕过,失败

 

 

4. Windows与PHP双态叠加绕过,即加.php:.png,还是上传失败

 

 

……

试了很多都失败了……

算了不试了,看看能不能在别的地方有突破吧

继续查看网页原代码

 进行翻译

 1 <!DOCTYPE html>
 2 <html>
 3 <head>
 4     <meta charset="utf-8">
 5     <title>moe图床</title>
 6 </head>
 7 <body>
 8     <input type="file" id="fileInput">
 9     <button onclick="uploadFile()">上传</button>
10     <div id="uploadResult"></div>
11     <script>
12         // 上传文件的函数
13         function uploadFile() {
14             // 获取文件输入框和选择的文件
15             const fileInput = document.getElementById('fileInput');
16             const file = fileInput.files[0];
17             
18             // 检查是否选择了文件
19             if (!file) {
20                 alert('请选择一个文件进行上传!');
21                 return;
22             }
23             
24             // 检查文件后缀名是否为png
25             const allowedExtensions = ['png'];
26             const fileExtension = file.name.split('.').pop().toLowerCase();
27             if (!allowedExtensions.includes(fileExtension)) {
28                 alert('只允许上传后缀名为png的文件!');
29                 return;
30             }
31             
32             // 创建一个 FormData 对象,将文件添加到其中
33             const formData = new FormData();
34             formData.append('file', file);
35 
36             // 使用 fetch 发送 POST 请求上传文件
37             fetch('upload.php', {
38                 method: 'POST',
39                 body: formData
40             })
41             .then(response => response.json())
42             .then(result => {
43                 // 处理上传结果
44                 if (result.success) {
45                     const uploadResult = document.getElementById('uploadResult');
46                     const para = document.createElement('p');
47                     para.textContent = ('地址:');
48                     const link = document.createElement('a');
49                     link.textContent = result.file_path;
50                     link.href = result.file_path;
51                     link.target = '_blank';
52                     para.append(link);
53                     uploadResult.appendChild(para);
54 
55                     alert('文件上传成功!');
56                 } else {
57                     alert('文件上传失败:' + result.message);
58                 }
59             })
60             .catch(error => {
61                 console.error('文件上传失败:', error);
62             });
63         }
64     </script>
65 </body>
66 </html>
View Code
获取用户选择的文件。
检查是否选择了文件以及文件后缀名是否为 .png,如果不符合要求,会弹出相应的警告对话框。
创建一个 FormData 对象并将选中的文件添加到其中,以便于之后的上传操作。
使用 fetch 函数发送 POST 请求到 upload.php,将文件数据作为请求体(body)发送。
处理上传结果:当上传成功时,将文件地址显示在页面上,同时弹出成功的提示对话框;当上传失败时,弹出失败的提示对话框,并将错误信息显示在其中。
请注意,这段代码中使用了一个名为 upload.php 的文件来处理文件上传的后台逻辑。在实际使用时,需要编写 upload.php 文件来接收并处理文件上传请求,并返回相应的结果。

 

从里面可以得知有一个upload.php的文件在规范上传的规则,直接获取看看会不会有结果(用GET方式上传也会显示该代码)

 获取成功,直接分析函数

 1 首先定义了变量 $targetDir,该变量指定了上传文件的目标目录,即 uploads/ 目录。注意,这个目录路径是相对于当前脚本文件所在的目录。
 2 定义了数组 $allowedExtensions,包含允许上传的文件扩展名。在该示例中,只允许上传扩展名为 png 的文件。
 3 通过 $_SERVER['REQUEST_METHOD'] 判断是否为 POST 请求,并且判断是否存在一个名为 file 的文件字段。
 4 如果满足上传条件,则获取上传的文件相关信息,包括临时路径 $tmp_path 和文件名 $fileName。
 5 使用 $file['type'] 检查文件类型是否为 'image/png',如果不是,则返回错误消息。
 6 使用 filesize() 函数检查文件大小是否超过 512KB 的限制,如果超过,则返回错误消息。
 7 使用 explode() 函数将文件名 $fileName 拆分为多个部分,并检查第二个部分是否为 'png',如果不是,则返回错误消息。这样做是为了避免伪装成 PNG 文件的恶意文件。
 8 使用 dirname(__FILE__) 获取当前脚本文件所在的目录,并将目标目录和文件名拼接起来,得到上传后的文件路径 $uploadFilePath。
 9 使用 move_uploaded_file() 函数将临时文件移动到目标目录,如果移动成功,则返回成功的 JSON 响应。否则,返回文件上传失败的错误消息。
10 如果不是 POST 请求或未提供文件字段,则使用 highlight_file() 函数将当前脚本文件的源代码展示出来。
11 总而言之,这段代码负责接收通过 POST 请求上传的 PNG 格式图片文件,并进行一系列验证,包括文件类型、文件大小和文件名后缀等,然后将文件移动到指定的目录。最后,根据上传结果返回相应的 JSON 响应。如果不是上传请求,就展示代码本身。

关键判断在这里,这里只判断文件的后缀是否为png,那我们就可以用xxx.png.php的方式来绕过了

 试一下

 上传成功

 

 

连接蚁剑

 连接不了就只能直接访问了

后面发现是文件路径错了

 在根目录找到flag