学 Win32 汇编[20]: 洞察标志寄存器
?
1514131211109876543210 NTIOPLOFDFIFTFSFZF AF PF CF未使
用嵌
套
标
志I/O
权限
标志
占2位溢
出
标
志方
向
标
志中
断
允
许
标
志单
步
标
志符
号
标
志零
标
志未
使
用辅
助
标
志未
使
用奇
偶
标
志未
使
用进
位
标
志
上表是 32 位寄存器 EFLAGS 的低 16 位.
不能直接读写 EFLAGS, 但有些方便的指令, 如:
LAHF: 读取EFLAGS 低 8 位到 AH; SAHF 是 LAHF 的反向操作.
指令 STC、CLC、CMC 分别是给 CF(进位标志) 置位、复位、取反
; Test20_1.asm.386.model flat, stdcallinclude windows.incinclude kernel32.incinclude masm32.incinclude debug.incincludelib kernel32.libincludelib masm32.libincludelib debug.lib.data? szBin1 db 8 dup(?), 0? szBin2 db 8 dup(?), 0? szBin3 db 8 dup(?), 0? szBin4 db 8 dup(?), 0.codemain proc? stc ;置位 CF, CF = 1? lahf? invoke byt2bin_ex, ah, addr szBin1? ? clc ;复位 CF, CF = 0? lahf? invoke byt2bin_ex, ah, addr szBin2? ? stc? cmc ;取反 CF, CF = not CF? lahf? invoke byt2bin_ex, ah, addr szBin3? ? clc? cmc ;取反 CF, CF = not CF? lahf? invoke byt2bin_ex, ah, addr szBin4? PrintString szBin1 ;xxxxxxx1? PrintString szBin2 ;xxxxxxx0? PrintString szBin3 ;xxxxxxx0? PrintString szBin4 ;xxxxxxx1? retmain endpend main
如果要观察整个 EFLAGS 的 32 个位, 可用 PUSHFD 和 POPFD 指令让 EFLAGS 进栈、出栈
; Test20_2.asm.586p.model flat, stdcallinclude windows.incinclude kernel32.incinclude masm32.incinclude debug.incincludelib kernel32.libincludelib masm32.libincludelib debug.lib.data? szBin db 32 dup(?), 0.codemain proc? stc? pushfd? invoke dw2bin_ex, dword ptr [esp+4], addr szBin? popfd? PrintString szBin ;00000000000000000000001001000111? ? clc? pushfd? invoke dw2bin_ex, dword ptr [esp+4], addr szBin? popfd? PrintString szBin ;00000000000000000000001010000110? retmain endpend main
发现标志寄存器里的数据有点捉摸不定, 看来不应该是这么观察的; 以后慢慢留意吧.