Day 27 - Pwn 0x1

先欢迎各位来到整体难度最高的领域
在听这里之前
前面的逆向组语要先学好
还有对 OS 以及计算机概论要有一些认识会比较好

Pwn

Pwn 念作胖或碰 (?
是一个骇客界用语
意思为完全击败对方、完全占领对方拥有的东西这样的意思
那在这个类型中的行为也差不多
最後的目的就是夺得对方主机的控制权

而 pwn 的攻击方式
通常是针对程序中
对於记忆体使用或是分配不当所产生的漏洞
该漏洞可以让攻击者利用精心设计的一串字串
使得本应该产生程序崩溃的行为
却变成了可任意对系统执行指令

关於记忆体

在打 pwn 之前
我们需要先对记忆体有些认识
当一支程序被运行起来时
作业系统会分配一块记忆体供其使用
而这块记忆体有着一个固定的结构

这边注意一下
越往下记忆体位置越多
往上越少

+------------------+ 0x00000000
|                  |
+------------------+
|                  |
|       Text       | >存放程序指令码
|                  |
+------------------+
|                  |
|       Data       | >存放已经初始化过的变数
|                  |
+------------------+
|                  |
|       BSS        | >存放未初始化的变数 or 全域变数 or const 变数
|                  |
+------------------+
|                  |
|       Heap       | >当使用到 malloc 时会使用到
|                  |  heap 会往 stack 的方向长
+------------------+
|         .        |
|         .        |
|         .        |
+------------------+
|                  |
|       Stack      | >所有区域变数、参数都会存在於此,也包括函数返回地址
|                  |  stack 会往 heap 方向长
+------------------+
|                  |
|     OS Kernal    | >作业系统的区域
|                  |
+------------------+ 0x80000000

关於组语

就拿昨天逆向那题 CTF 当例子吧~

昨天本来直接说从第四行开始
那前面两行语法是在做什麽的呢
其实在组语中
对於函数有两个重要的区块

Prologue

push ebp
mov  ebp, esp

在每次进入一个 function 之前
都会先对 stack 重新划区
上面有说到 stack 是用来放区域变数或是一些参数的地方

+---------+ 
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+ < 前一个 func 的 ESP
|   ret   |
+---------+

从上限可以看到前一个 func 的 ESP 以下都是前一个 function 的范围
我们现在要新进到一个 function 了
所以先将旧的 EBP push 到 stack 中存起来变成
push 完成後 ESP 会往上一格

这边还有一件事就是那个 ret
在我们 call 这个 func 时
其实会先将当时下一行指令的位置先 push 进来
以便之後该函数执行完成时
要跳回原本的位置继续执行
这个 ret 位置非常重要是 stack pwn 的精随

+---------+ 
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+ < 前一个 func 的 ESP
|   旧EBP |
+---------+
|   ret   |
+---------+

接着将 esp 给到 ebp

+---------+ 
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+ < EBP, ESP
|  旧EBP  |
+---------+
|   ret   |
+---------+

从这里可以看到 ESP 跟 EBP 都在同一个位置上了
EBP 以上就代表着新的 function 的区块
所以对新的 function 来说
ret旧 EBP 永远都会在 EBP 的前两个位置上

Epilogue

接着来看到程序码最後两行

pop ebp
ret

到了这边
一个函数的执行也到了尾声
因此在离开前
要先清理自己刚刚的 stack frame

+---------+ 
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+ < EBP, ESP
|  旧EBP  |
+---------+
|   ret   |
+---------+

会先将旧的EBP pop 回去原本的 EBP 中
让程序知道自己现在的 stack frame 回到了原本那个函数中

+---------+ 
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+
|         |
+---------+ < ESP
|   ret   |
+---------+

接着上面有说到这个 stack 中 ret 的功能
也会透过 ret 这个指令将这个值放回 EIP
让程序知道接下来该去哪里执行


<<:  安能取熊掌而舍鱼? 便捷初始化器语法

>>:  好想工作室 web camp JS 怎麽 training

[Day4] Flutter - 水平布局容器 ( Row )

前言 Hi, 我是鱼板伯爵今天要教大家 Row 这个容器,教学内容只会撷取片段程序码,建议大家搭配完...

仿Trello - 前端 Apollo Client 串接 GraphQL API

本系列文以制作专案为主轴,纪录小弟学习React以及GrahQL的过程。主要是记下重点步骤以及我觉...

DAY30-结语

终於!!!最後一天啦!!!今天什麽范例都不会讲哈哈哈!!!我想讲一下我做完这三十天的感想!!! 我觉...

[D01]试用期从零开始的k8s

前言 写在前面 这是一个记录自己成长的三十天挑战 进入公司原本说要做 data 结果进来之後才发现很...

【Day 16】Function 函式(续)

前言 函式用於结构化程序,将需要重复用到的功能独立出来,透过函式的呼叫,传入资料与回传处理後的资料。...