Decreasing size of data ( size 가 줄어드는 data )
mov ax, 0034h mov cl, al |
ㆍ큰 size 에서 작은 size 에 넣으면 data 의 상위 byte는 잘려 나간다.
Increasing size of data
mov ah, 0 |
ㆍah의 양수 공간 확장
movzx eax, ax |
ㆍeax 는 4byte ax는 2byte 임으로 movzx 로 size를 맞춘다.
ㆍzx : 는 양수일때의 공간 확장을 할경우 mov앞에 사용된다.
ㆍ비쥬어 스튜디오 에서 디버그 모드에 진입후 단축키alt + 8 을 눌리면 디스어셈블리 창이 보인다.
[ C 소스코드 ]
[ 위 C소스 코드의 어셈블리 ]
ㆍmov 앞의 숫자는 기계어 주소이다.
※ 보수관계에 의해 signed, unsigned 타입은 어셈블리에서 다음과 같이 나타낸다.
ㆍ양수를 확장시켜 mov 시키면 movzx 가 된다.
ㆍ음수를 확장시켜 mov 시키면 movsx 가 된다.
Type | 속도 |
mov | 클럭 빠름 |
movzx | 클럭 중간 |
movsx | 클럭 느림 |
※ Intel cpu 는 어큐뮬레이터(accumulators 가 존재하는데 eax레지스터등이 있다.
어큐뮬레이터는 속도가 틀별히 빠른 레지스터이다.
◈ 함수 호출 규약 (Calling Conventions)
ㆍ함수를 호출하는 과정에서 인자를 전달하기 위해 스택 프레임이라는 구조를 사용합니다.
피라미터를 위해 확보한 스택 공간안에 인자를 어떠한 순서로 넣을 것인가? 누가 해지해줄 것인가?
하는 부분에 대한 정의예요. 종류로는 여러가지 있는데 대표적으로 cdecl , stdcall , fastcall 이 있습니다.
함수 호출 방식(cdecl, stdcall, pascal) 1. 인수를 스택에 저장하는 순서를 왼쪽에서 오른쪽으로 한다. pascal : 인수를 스택에 저장하는 순서를 왼쪽에서 오른쪽으로 한다. cdecl : 인수를 스택에 저장하는 순서를 오른쪽에서 왼쪽으로 한다. stdcall : 인수를 스택에 저장하는 순서를 오른쪽에서 왼쪽으로 한다.
2. 스택에 인수를 pop 하는 주체에 따라서 다음과 같이 나뉘고. pascal : 호출을 당하는 쪽이 스택공간을 삭제한다. stdcall : 호출을 당하는 쪽이 스택광간을 삭제한다. cdcl : 호출을 하는 쪽이 스택공간을 삭제한다. 이렇게 stdcall 은 pascal 방식과 cdedl 방식을 혼합한 형태를 띄운다. |
MASM :: ml 컴파일
ㆍml 컴파일 설치는 첨부파일에 있다.
Ex) io.h 헤더파일
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 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 | ; IO.H -- header file for I/O macros ; 32-bit version for flat memory model ; R. Detmer last revised 8/2000 .NOLIST ; turn off listing .386 EXTRN itoaproc:near32, atoiproc:near32 EXTRN dtoaproc:near32, atodproc:near32 EXTRN inproc:near32, outproc:near32 itoa MACRO dest,source,xtra ;; convert integer to ASCII string IFB <source> .ERR <missing operand(s) in ITOA> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in ITOA> EXITM ENDIF push ebx ;; save EBX mov bx, source push bx ;; source parameter lea ebx,dest ;; destination address push ebx ;; destination parameter call itoaproc ;; call itoaproc(source,dest) pop ebx ;; restore EBX ENDM atoi MACRO source,xtra ;; convert ASCII string to integer in AX ;; offset of terminating character in ESI IFB <source> .ERR <missing operand in ATOI> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in ATOI> EXITM ENDIF push ebx ;; save EBX lea ebx,source ;; source address to EBX push ebx ;; source parameter on stack call atoiproc ;; call atoiproc(source) pop ebx ;; parameter removed by ret ENDM dtoa MACRO dest,source,xtra ;; convert double to ASCII string IFB <source> .ERR <missing operand(s) in DTOA> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in DTOA> EXITM ENDIF push ebx ;; save EBX mov ebx, source push ebx ;; source parameter lea ebx,dest ;; destination address push ebx ;; destination parameter call dtoaproc ;; call dtoaproc(source,dest) pop ebx ;; restore EBX ENDM atod MACRO source,xtra ;; convert ASCII string to integer in EAX ;; offset of terminating character in ESI IFB <source> .ERR <missing operand in ATOD> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in ATOD> EXITM ENDIF lea eax,source ;; source address to EAX push eax ;; source parameter on stack call atodproc ;; call atodproc(source) ;; parameter removed by ret ENDM output MACRO string,xtra ;; display string IFB <string> .ERR <missing operand in OUTPUT> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in OUTPUT> EXITM ENDIF push eax ;; save EAX lea eax,string ;; string address push eax ;; string parameter on stack call outproc ;; call outproc(string) pop eax ;; restore EAX ENDM input MACRO dest,length,xtra ;; read string from keyboard IFB <length> .ERR <missing operand(s) in INPUT> EXITM ENDIF IFNB <xtra> .ERR <extra operand(s) in INPUT> EXITM ENDIF push ebx ;; save EBX lea ebx,dest ;; destination address push ebx ;; dest parameter on stack mov ebx,length ;; length of buffer push ebx ;; length parameter on stack call inproc ;; call inproc(dest,length) pop ebx ;; restore EBX ENDM .NOLISTMACRO ; suppress macro expansion listings .LIST ; begin listing | cs |
Ex) first.asm 파일
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 | .386 .MODEL FLAT ExitProcess PROTO NEAR32 stdcall, dwExitCode:DWORD INCLUDE io.h cr EQU 0Dh Lf EQU 0Ah .STACK 4096 .DATA number1 DWORD ? number2 DWORD ? prompt1 BYTE "Enter First Number : ", 0 prompt2 BYTE "Enter Second Number : ", 0 string BYTE 40 DUP (?) label1 BYTE cr, Lf, "The Sum is " sum BYTE 11 DUP (?) BYTE cr, Lf, 0 .CODE _start: output prompt1 input string, 40 atod string mov number1, eax output prompt2 input string, 40 atod string mov number2, eax mov eax, number1 add eax, number2 dtoa sum, eax output label1 INVOKE ExitProcess, 0 PUBLIC _start END | cs |
아래 두 파일이 필요함
ㆍml 컴파일을 setup 하면 소프트웨어 파일 내부에 있다.
first.asm 컴파일 명령
link 를 걸어 main.exe를 만드는 명령어
main.exe 실행 결과 :
ㆍ숫자 두개를 입력받아 덧셈 해준다.
위 first.asm 코드의 해석 :
ml 디버그
ㆍ소프트 웨어 파일에서 아래 파일을 복사하여 소스파일 위치로 이동
ㆍml 컴파일
ㆍ디버그를 위한 명령어는 다음과 같다.
ㆍ위 두개의 파일이 생성된다.
ㆍwindbg.exe 를 실행시켜 main.exe파일을 열어 단축키 F11 을 두번 눌러준다.
ㆍ다음과 같이 디버그가 시작된다.
ㆍentry 를 start 로 설정되어 디버깅도 start 함수부분에 entry포인트로 설정되었다.
※ 시스템 환경변수의 path 에 소프트웨어 경로를 등록하면 어떤 폴더에서든 파일만 복사해서 넣어주면 디버그와 컴파일이 가능하다.
디버깅 메뉴
ㆍ위 경로로 Registers 창을열어 레지스트를 확인할 수 있다.
ㆍView 에서 Memory 창을열어 &붙여 다음과 같이 입력하면 해당 변수의 메모리를 볼수 있다.
ㆍ다음과 같이 진행 단축키F11로 레지스터와 메모리를 확인한다.
Assembly(Assembly 기초/C소스 어셈블리로 코딩하기) (0) | 2017.07.25 |
---|---|
ASSEMBLY 기초/문법 (0) | 2017.07.18 |
어셈블리 기초 (0) | 2017.07.18 |