고급 언어는 데이터를 변수나 클래스에 저장한다.
어셈블러는 데이터를 스택, 레지스터, 메모리에 저장한다. (변수X)
스택 - 넣고, 빼는 기능만
레지스터 - 숫자와 용량 정해져 있다.
메모리 - 주소를 통한 직접 접근
어셈블러 명령어는 최대 3개의 인자를 받아들일 수 있다.
명령어 | 사용법 | 설명 | 예시 |
MOV | MOV dst, src | src 내용을 dst로 복사 | MOV EAX, ECX before: EAX(00400020), ECX(00400030) after: EAX(00400030), ECX(00400030) |
MOVZX | MOVZX dst(32bit), src(16bit) MOVZX dst(16bit), src(8bit) |
src 내용을 dst로 복사하고, dst 나머지 부분을 0으로 채운다. dst에 32bit 레지스터가 오면 src 내용을 dst로 복사하고, dst 나머지 부분을 0으로 채운다. dst에 32bit 레지스터가 오면 src에는 16bit 레지스터가 온다. |
MOVZX EAX, CX before: EAX(89ABCDEF), ECX(12345678) AFTER: EAX(00005678), ECX(12345678) |
MOVSX | MOVSX dst(32bit), src(16bit) MOVSX dst(16bit), src(8bit) |
src의 내용을 dst로 복사하고, dst 나머지 부분을 src의 맨 처음 비트로 채운다. dst에 32bit 레지스터가 오면 src에 16bit 레지스터가 온다. | MOVSVX EAX, CX BEFORE: EAX(89ABCDEF), ECX(12345678) AFTER: EAX(00005678), ECX(12345678) |
LEA | LEA dst(레지스터), src | src의 주소를 dst로 복사 dst에는 레지스터만 가능 |
LEA EAX, [ESP-4] BEFORE: EAX(89ABCDEF), ESP(0018FF88) AFTER: EAX(0018FF88), ESP(0018FF88) |
명령어 | 사용법 | 설명 | 예시 |
ADD | ADD DST, SRC | DST와 SRC 내용 더해서 DST에 저장 | ADD EAX, ECX BEFORE: EAX(00000002), ECX(00000001) AFTER: EAX(00000003), ECX(00000001) |
SUB | SUB DST, SRC | DST = DST - SRC | SUB EAX, ECX BEFORE: EAX(00000004), ECX(00000001) AFTER: EAX(00000003), ECX(00000001) |
MUL | MUL SRC | 부호 없는 곱셈 EAX 레지스터에 SRC 내용 곱해서 EAX 레지스터에 저장. 결과 값이 커서 목적지에 다 들어가지 않으면 EDX 레지스터에 넘치는 상위 비트 값 저장 |
MUL ECX BEFORE: EAX(00077777), ECX(00077777), EDX(00000000) AFTER: EAX(4861D951), ECX(00077777), EDX(000037C0) |
IMUL | 1. IMUL DST 2. IMUL DST, SRC 3. IMUL DST, SRC, 정수 |
부호 있는 곱셈 1. EAX = EAX * DST (EDX 레지스터에 결과 값이 커서 넘친 값을 저장) 2. DST = DST * SRC (EDX 레지스터에 결과 값이 커서 넘친 값을 저장) 3. DST = SRC * 정수 (EDX 레지스터에 결과 값이 커서 넘친 값을 저장) |
IMUL ECX, EBX, -4 BEFORE: ECX(00000003), EBX(00000004) AFTER: ECX(FFFFFFF0), EBX(00000004) |
DIV | DIV SRC(레지스터) | 부호 없는 나눗셈 EAX = EAX / SRC EDX = 나머지 (DIV 연산 전 EDX를 0으로 초기화한다.) |
DIV ECX BEFORE: EAX(0000000A), ECX(00000003), EDX(00000000) AFTER: EAX(00000003), ECX(00000003), EDX(00000001) |
IDIV | 1. IDIV SRC(8BIT 레지스터) 2. IDIV SRC(16BIT 레지스터) 3. IDIV SRC(32BIT 레지스터) |
부호 있는 나눗셈 1. AX = AX / SRC, AL = 몫, AH = 나머지 2. 크기 커서 AX에 다 못 담으면 DX에 나누어 저장 DX와 AX 값을 SRC 내용으로 나누어 AX에 저장, DX = 나머지 3. EDX와 EAX 레지스터 값을 SRC 내용으로 나눈다. EAX = 몫, EDX = 나머지 |
IDIV ECX BEFORE: EAX(FFFFFFF7), ECX(00000002), EDX(00000000) AFTER: EAX(7FFFFFFB), ECX(00000002), EDX(00000001) |
INC | INC DST | DST = DST + 1 | INC ECX BEFORE: ECX(00000003) AFTER: ECX(00000004) |
DEC | DEC DST | DST = DST - 1 | DEC ECX BEFORE: ECX(00000003) AFTER: ECX(00000002) |
NEG | NEG DST | 부호 반전 DST의 데이터 부호를 바꾼다. (2의 보수) |
NEG ECX BEFORE: ECX(FFFFFFFC) -4 AFTER: ECX(00000004) |
명령어 | 사용법 | 설명 |
AND | AND DST, SRC | DST = DST & SRC |
OR | OR DST, SRC | DST = DST | SRC |
NOT | XOR DST, SRC | DST = DST ^ SRC |
명령어 | 사용법 | 설명 | 예시 |
CMP | CMP 인자1, 인자2 | 인자1 == 인자2: CF=0, ZF=1 CF == 0 && 인자1 != 인자2: CF = 0, ZF = 0 |
CMP EAX, ECX BEFORE: EAX(00000001), ECX(00000001), C(1), Z(0) AFTER: EAX(00000001), ECX(00000001), C(0), Z(1) |
JMP | JMP DST | DST 주소로 이동한다. 복귀 주소 백업 X |
JMP 00401018 |
JE | JE DST | ZF == 1이면 점프 보통 CMP 뒤에 온다. |
JE 00401018 |
JNE | JNE DST | ZF == 0이면 점프 | |
JZ | JZ DST | ZF == 1 또는 앞 연산 결과가 0이면 점프 보통 DEC나 JMP 뒤에 온다. |
|
JNZ | JNZ DST | ZF == 0 또는 앞 연산 결과가 0이 아니면 점프 보통 DEC나 CMP 뒤에 온다. |
|
JA | CMP 인수1, 인수2 JA DST |
CMP 인수1, 인수2 명령어 뒤에 와서 인수1 > 인수2이면 DST로 점프 | |
JB | CMP 인수1, 인수2 JB DST |
CMP 인수1, 인수2 뒤에 와서 인수1 < 인수2 이면 DST로 점프 |
명령어 | 사용법 | 설명 | 예시 |
SHL | SHL DST, 비트 수 | DST에 있는 데이터를 비트 수만큼 왼쪽으로 이동 곱셈과 관련 |
SHL EAX, 2 BEFORE: EAX(00000FFF) AFTER: EAX(000003FFC) |
SHR | SHR DST, 비트 수 | DST에 있는 데이터를 비트 수만큼 오른쪽으로 이동 | SHR EAX, 2 BEFORE: EAX(00000FFF) AFTER: EAX(000003FF) |
명령어 | 사용법 | 설명 |
PUSH | PUSH 데이터 | 스택 맨 위에 데이터를 저장. ESP를 4만큼 감소시킨다. 함수에 인자 전달, 지역변수 위한 공간 할당에 사용 |
POP | POP DST | 스택에서 데이터를 꺼내서 DST에 저장 ESP를 4만큼 증가시킨다. |
PUSHAD | PUSHAD | EAX -> ECX -> EBX -> ESP -> EBP -> ESI -> EDI 레지스터 순서대로 스택에 PUSH한다. ESP 레지스터는 32비트 만큼 감소 |
POPAD | POPAD | 스택에 존재하는 값을 EAX, EBX, ECX, EDX, ESI, EDI, ESP, EBP 레지스터로 POP한다. ESP 레지스터는 32비트 증가 |
명령어 | 사용법 | 설명 |
CALL | CALL DST | RETURN ADDRESS(EIP 레지스터 값)을 스택에 백업한 후, DST 주소에 있는 서브루틴(함수)로 이동한다. |
RETN | RETN RETN 바이트수 |
백업한 RETURN ADDRESS로 이동한다. RETN == POP EIP |
TEST | TEST 인수1, 인수2 | 인수1과 인수2 내용을 AND 연산한 결과가 0이면 ZF = 1 NULL 체크 시 사용 |
CodeEngn Basic RCE L02 (0) | 2021.05.02 |
---|---|
CodeEngn Basic RCE L01 (0) | 2021.05.01 |
asm 분석: 어셈블리 코드에서 소스 코드 변환해보기 (0) | 2021.04.05 |
x86_64 assembly code (0) | 2021.04.04 |
어셈블리 명령어 포맷, 명령어 종류 (Instruction Format, Instructions) (0) | 2021.03.26 |