萌新带你开车上p站(三)
本文作者:萌新
前情回顾:
0x08
题目给的提示是和运算符优先级有关
登录后直接看源码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 | mistake@pwnable:~$ ls flag mistake mistake.c password mistake@pwnable:~$ cat mistake.c #include <stdio.h> #include <fcntl.h> #define PW_LEN 10 #define XORKEY 1 void xor( char * s, int len){ int i; for (i=0; i<len; i++){ s[i] ^= XORKEY; } } int main( int argc, char * argv[]){ int fd; if (fd=open( "/home/mistake/password" ,O_RDONLY,0400) < 0){ printf( "can't open password %d\n" , fd); return 0; } printf( "do not bruteforce...\n" ); sleep(time(0)%20); char pw_buf[PW_LEN+1]; int len; if (!(len=read(fd,pw_buf,PW_LEN) > 0)){ printf( "read error\n" ); close(fd); return 0; } char pw_buf2[PW_LEN+1]; printf( "input password : " ); scanf( "%10s" , pw_buf2); // xor your input xor(pw_buf2, 10); if (!strncmp(pw_buf, pw_buf2, PW_LEN)){ printf( "Password OK\n" ); system( "/bin/cat flag\n" ); } else { printf( "Wrong Password\n" ); } close(fd); return 0; } |
看关键:
main调用的xor函数:
将长度给len的字符串与1异或
main中的主要逻辑
从/home/mistake/password读10个字节数据放到pw_buf,我们手动输入10字节数据放在pw_buf2,如果pw_buf2与1异或的结果如果与pw_buf相等,则打印flag
那么关键就是pw_buf的数据,先直接读password看看
没有权限
题目的提示是和运算符优先级有关
我们仔细分析源码,看看问题出在哪里
问题在这里
if(fd=open("/home/mistake/password",O_RDONLY,0400) < 0){
open函数里权限检查是没问题的,O_RDONLY表示以只读方式打开
0400表示文件所有者具有可读取的权限
由于权限通过检查,所以open函数返回值为0
有因为0<0不成立
所有比较结果为0
然后赋值给fd
即fd为0,表示标准输入,也就是说fd现在是我们可控的
结合之前分析,pw_buf也为我们控制
那就很简单了
第一次输入10个1,存入pw_buf
第二次输入10个0,存入pw_buf2,与1异或后覆盖pw_buf2,此时buf2的值也为10个1,满足打印flag的逻辑
0x09shellshock
查看权限
可以看到shellshock程序的所属组的权限位上有s,表示sgid,也就是说在执行shellshock时,用户将获得shellshcok所属组的权限,即执行shellshock后将获得root所在用户组的权限,而由flag这一行的权限位可知,该权限可以读取flag
这一点从源码中也可以看出来
getegid()返回进程执行有效组识别码。在这里getegid()返回的就是root所在用户组的id
setresuid用于设置ruid,euid,seuid,在这里就是统统都设置为进程当前的egid
setresgid用于设置rgid,egid,sgid,这里也是统统设置为进程当前的egid
因为s标志,所以egid实际上是root所在用户组的id
再根据题目提示的shellshock
这是著名的bash破壳漏洞
直接在网上找到poc修改下即可
解释一下发生了什么
首先在当前环境下定义了X函数,函数体由{}括起来,然后在函数体外加了一条额外的语句/bin/cat ./flag即打印flag的命令,这条语句会在后面执行./shellshock时被调用,由于执行shellshock时会有root权限,所以自然就有权限来打印flag了
想知道怎么操作吗?点击开始实践——破壳漏洞实践:http://www.hetianlab.com/expc.do?ec=ECID172.19.105.222014092915250400001
0x10
按照要求连接服务器
这是一个小游戏
大意是一堆货币里有真币假币,两者重量不同,真币10g,假币9g。给你N个硬币,C次机会,让你猜哪一个是假币。需要在30s的时间里才对100次。
这题其实考的是算法。
分治法解决
举个例子。
一共100个硬币,其中1个是假的,先称重1-49,如果结果整除10,则假币在50-100.
第二轮称50-75,如果不整除10,则假币在其中
第三轮称50-62.。。。。
其实就是简单的二分法
编程
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | import time from pwn import * conn = remote( '0' , 9007) conn.recv(10000) for _ in range(100): //猜100次 line = conn.recv(1024).decode( 'UTF-8' ).strip().split( ' ' ) print(line) n = int (line[0].split( '=' )[1]) //读出给的n,c c = int (line[1].split( '=' )[1]) left = 0 right = n //共n个硬币 for _ in range(c): //二分法猜解 guess = ' ' . join (str(left) for left in range(left, int ((left+right)/2))) conn.sendline(guess) //给出需要猜测的货币 output = int (conn.recv(1024).decode( 'UTF-8' ).strip()) //读取返回称重的结果 if (output % 10 == 0): //整除10的情况 left = int ((left+right)/2) else : //不整除的情况 right = int ((left+right)/ 2) conn.sendline(str(left)) print(conn.recv(1024).decode( 'UTF-8' )) //打印一轮的结果 print(conn.recv(1024).decode( 'UTF-8' )) conn.close() |
以上一关的shellshock登录服务器,在tmp目录下新建一个python 脚本
按照提示
用pwntools编写的时候,注意remote(‘0’,9007)
执行如下
0x11 blackjack
em...源码有点长,直接看关键部分
这里会校验我们输入的金额
如果比cash大则会报错,并要求再次输入
不过再次输入的时候不会报错了
考虑到要赚够1000000,而输的几率比较大
我们可以输入-的金额,比如-1000000,只要输了就可以拿到flag
然后选择y就打印出flag了
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· .NET10 - 预览版1新功能体验(一)