通过观看小甲鱼的视频学习,链接如下:
https://www.bilibili.com/video/av9285860/index_27.html#page=27
博客内部分截图来源于此。
本人新手,博客内容比较浅薄。
第1章。
1,壳是什么,当我们点击一个EXE文件,然后输入账号密码,如果不知道密码的话,那直接反汇编EXE文件,然后找到程序正确的入口。修改EXE文件,就可以只输入账号不输入密码登录上别人的账号,这里的壳就是,在关键的地方加密,加上一些和程序没有任何关系的东西,让你没有办法找到程序的入口。
2,cpu与各种内存(ram,寄存器,显存等)之间都是通过总线通信,总线:地址总线,数据总线,控制总线。如果数据是一个地址但是走的是数据总线,那它就会被当成是数据来处理,因为都是0101.3,如何达到64位的速度,要有3个东西,64位的cpu,64位的操作系统,64位的软件。64位的cpu是指:地址总线有64根线构成,可以直接找到从0开始到2的64次方的数据的地址。另外,地址总线的地址从由上到下是由低位到高位。无论是多少位的cpu,它能做的仅仅是可以在RAM找的数据的地址变大了(0-100还是0-10000),和数据是什么是多大并没有关系。
4,数据总线:一个有电线构成的东西,8根线则一次可以传1字节数据。如果是2字节就要传2次。
5,控制总线:是一个统称,1根线可以有2种情况,可以是读or写。线越多说明控制命令越多。如果有一个数据位00001010,它不是一个控制命令,而是对多个东西的不同命令,如低位0是对寄存器读,低位1是对RAM写。这8个位对应8个不同的元件。
图1
6,把一堆优化过的指令放在一起,叫做指令集。
7,ROM只读存储器,只读不写,断电数据依旧不变。HDD是磁盘存储器。如:显卡,网卡,主板都有ROM存储器,比如:打开电脑出现华硕的标志,那就是华硕主板的BIOS系统的ROM存储器提前写入的东西。且,主板运行时会做各种检查,如CUP,RAM是不是好的。比如显卡:显卡GPU进行计算,计算的公式就是按照ROM里面的固定的公式计算的。
8,如下图,在cup的眼里,所有的存储器都是连着一起的。从0开始到某个地址结束。
图2
第2章
以下不特殊说明都是8086cpu(16位,一个字)
1,cpu外部连接外部总线,内部连接叫内部总线。cpu有8个通用寄存器这个core i系列依旧没改吧,这个是核心,如果改变的话,操作系统也要改变。Core i系统相比8086其实是多出了浮点数寄存器,增加了一些指令集寄存器等。
图3
AX分高位AH和低位AL为了兼容8088(一个8位cpu),所以AH和AL是2个可以独立使用的寄存器。X86是划时代的,因为现在的cpu都是一样的架构,都使用了段位偏移来拿到真实的物理地址。
2,用H表示16进制,B表示2进制,2进制每4个就是一个16进制数,每3个就是一个8进制数。一般有一个bin文件夹,代表的就是程序的2进制源代码。
mov就是=,add 就是+=,sub就是-=。
图4
10*10=100,数据10向左移动1位,16进制数*16也是向左移动1位,换成2进制就是移动4位。
内存是连续的,不存在段这个东西,只是8086寻址是20位但寄存器却又是16位的,所以没办法只能靠2个16位,所以引入了段这个概念。
Code segment(段),data s,stack s,extra(额外的)s 。
IP是偏移地址的寄存器。
图5,6
Jmp是无条件跳转,由于JMP不具有判断等原因,所以一般不建议用JMP指令,除非特殊情况。如何使用:
图7
使用CS:IP指向代码段就可以执行代码。主要是CS,如果用DS就会被当成是数据。
7,debug的命令,在cmd下可以操作寄存器的命令。
图8
第3章
1,8086入栈和出栈都是以字(2个字节)为单位进行的。
图9
当执行push时,sp会先减,然后才是数据入栈。Pop一样是先把数据拿出来,在增加。如果push不先减,那数据1000E,1000F就会被覆盖掉。Pop数据其实还是存在的,只是下一次push会将其覆盖而已。
例如:硬盘格式化,其实修改的只是存储地址的索引而已。
注意当没有元素时就没有栈顶元素的说法。
2,Cpu并不知道一个栈的空间有多大,也没有检查机制,一个栈有多大是由编译器来决定的,cpu只知道,ss:sp指向的内存是栈顶。对于cs:ip也是一样。
3,栈的大小是由编译器来决定的,编译器信不过程序员啊。程序可以自主操作的是堆。堆是一些零碎的被线性表操作的内存,操作堆时要小心内存泄漏。
4,对cs,ds,ss的思考。同一个内存,cpu并不知道是代码还是数据。
当我们要执行代码时,需要将cs:ip设置为我们代码的地址。
当我们要操作内存单元时,需要设置ds:[]。
当我们将内存单元当做stack时,需要设置好想要stack的地址,ss:sp。cpu并不知道什么是栈段,cpu只知道栈顶在哪里。
图10
第4章,写一个程序。简略过。
图11
单任务:聊QQ时音乐就自动不播了。切到音乐时,qq就停止了。但不是关闭。比如:在cmd下运行程序A,A运行时cmd暂停,cmd运行时,A暂停。
图12,13
dos中的shell就是cmd
如下图:1.exe文件被加载进入内存之后,DS和CS是差了段地址10的,即:100H。如下图:DS=075A,CS=076A。当1.exe加载如内存后,程序是从SA+10开始执行的,即:100H。而SA是指向PSP的,PSP是程序与操作系统通信的接口。另外100H=256(10进制)。另外:SA+10H处:0是因为程序处理0更加方便,所以使用段位偏移。
图14,15
第5章
1,
A:在debug模式下直接编写汇编代码,然后修改相应的寄存器的值调试,是一种方式。
B:使用debug调试exe文件,然后修改相应寄存器是一种方式,默认的cs:ip就已经指向了程序,且,[0]这种取内存数据方式将没有作用。使用[bx]做为中介使用。
C:直接执行exe文件是一种方式。
图16
通过观察发现,先执行一次add,然后再将cx-1再判断是否大于0.即:cx为多少就,loopPrtMy:对应的指令就执行多少次。
loop执行3种可能,1,让cx-=1。2,判断cx与0的大小。3,决定往下还是继续循环。
图17
2,debug其实就是vs中的debug,本身是一个程序。
Debug使用G命令跳到想要的位置,类似于vs里的断点。
使用p指令直接跳出循环。