쾌락없는 책임 (공부)/시스템프로그래밍

시스템프로그래밍 03 - 어셈블리어 조금 더 맛뵈기01

허스크 2021. 4. 19. 13:58
반응형

본 포스트는 강동완 교수님의 '시스템프로그래밍' 강의를 듣고

이해한 것들을 정리한 포스트입니다.

- 강의자료는 올리지 않습니다


<어셈블리어에서 데이터>

 어셈블리어에서 데이터는 다른 언어와는 다르게 '크기'만 중요합니다. 음수도 two's complement로 되어있고 CPU는 애초에 기계어만 알아들으니 크기를 이용해 offset값 등을 알아내는게 중요합니다.

(변수명)  Directives  초기화 (, 초기화)     ; Directives는 WORD같은 크기들

 위 문법을 예시로 하나 만들어보면 A DWORD 0 같은 식으로 만들 수 있다. (, 초기화)는 한번에 여러번 선언이 가능하다는 이야기인데 이 구조가 굉장히 특이하다

변수명 메모리 주소
arr 10 0000
  20 0001
  30 0002

 arr BYTE 10, 20, 30  과 같은 방식으로 한번에 여러번 데이터를 메모리에 만들 수 있습니다. 그런데 변수명인 arr은 '10'만을 가리키고 있으며 다른 20과 30의 경우 주소값을 통해서 접근할 수 있습니다.

( 이런 경우 여러 진수를 섞어서 사용할 수 있습니다. 어차피 컴퓨터는 2진수로 다 바꾸니깐)

 

* 컴퓨터에서 메모리+메모리 연산은 안되니 무조건 레지스터를 통해서 연산을 해야 합니다.

 

 

관련 데이터 타입들

1. 크기

 - BYTE : 1바이트

 - WORD : 2바이트 (16비트)

 - DWORD : 4바이트 (32비트)

 - QWORD : 8바이트 (64비트)

 - REAL4, REAL8, REAL10 : 실수를 저장하기 위한 타입으로 각각 4, 8, 10바이트입니다.

 

앞에 S 가 붙은 SWORD같은 형태는 부호가 있다는 뜻이다.


2. 문자열

 어셈블리어에서 문자열의 경우 작은/큰 따옴표 안에 표현하면 됩니다. 대신 character의 set으로 저장됩니다.

 - 문자열 끝에는 0을 붙여줘야 합니다.    ex) BigString  BYTE  "Hello World", 0

 - 개행의 경우 0dh, 0ah입니다. 16진수의 d, a라는 뜻


3. DUP

 Duplicate의 약자로 한번 선언으로 복수 선언이 가능합니다.

BYTE  10 DUP(7)      ; 10의 값을 메모리에 7번 연속으로 선언, 주소값은 이어서


4. 초기화가 안된 데이터

 ? 를 사용해서 표기하게 됩니다

.data?
arr WORD 100 DUP(?)		; 비어있는 공간 200바이트 생성

 이런식으로 하면 메모리를 쓰지 않는 비어 있는 공간이 할당되게 됩니다(할당도 이상하네). 이런 괴상한(?) 문법이 있는 이유는 이전 '시스템프로그래밍 02'에서 말한 메모리 버스의 용량때문입니다. 


5. Symbolic Constants

 C 에서 #define같은 문법입니다.

 

5-1. = 으로 이용하는 심볼

v = 10

 위에같은 방식으로 v 를 선언하면 어셈블리어가 코드 실행 전 v 를 전부 10으로 변경해 줍니다. 따라서 이 문법은 저장공간을 차지하지 않고, 런타임에 영향을 주지 않습니다. C++에서 #define으로 각종 변수들을 만들걸 생각하면 됩니다.

 

5-2. $

 현재 주소를 의미하는 심볼입니다. 할당시 크기에 주의해야 하며 앞으로 많이 사용하게 됩니다.  (고수준 언어의 인덱스 같은 역할로 계속 구르게 됩니다). 만약 WORD로 되어있다면 ($- ~~)/2를 하는 등 크기에 신경써줘야 합니다.

me DWORD $

 배열을 선언했을 때 사용하는 방법으로는 아래와 같습니다.

arr BYTE 10, 20, 30, ....
arrSize = ($ - arr)

 

5-3. 키보드 코드 정의 가능

 유니티의 KeyCode처럼 키보드의 값도 지정이 가능합니다. 대신 역시 숫자로 입력해야 하며 위에 Symbolic Constants와 결합해서 사용하면 가독성 좋게 처리할 수 있습니다.

 

5-4. EQU

 위에 있는 =은 숫자만 가능(+문자열)하지만 얘는 숫자나 임의의 텍스트도 가능합니다. 하는 일은 = 와 역시 같습니다. 대신 =에서 가능한 재정의가 불가합니다. 

- 이름 EQU ~~~           ; ~~~를 바로 인식하게 됩니다.

- 이름 EQU <~~~>       ; <> 안의 ~~~를 텍스트로 인식합니다.

hi EQU <"Hello World..!", 0>
prompt BYTE hi

+ TEXTEQU : EQU의 텍스트 전용으로 재정의가 가능합니다.

 

 

Little Edian

리틀 엔디안과 빅 엔디안이 있습니다. 만약 4바이트의 16진수 수인 12345678h를 저장한다고 하면 리틀 엔디안과 빅 엔디안의 결과는 아래 표와 같습니다.

방식 리틀 엔디안 빅 엔디안
메모리 주소 0 78 12
메모리 주소 1 56 34
메모리 주소 2 34 56
메모리 주소 3 12 78

 빅 엔디안의 경우 일반적으로 사람이 생각하는 방식으로 데이터의 왼쪽부터 저장하게 됩니다. 하지만 리틀엔디안의 경우 데이터의 오른쪽부터 저장을 하며 저장되는 방식이 위와 같습니다. 대부분의 인텔,윈도우 기반은 리틀 엔디안을 사용하고 있고 이 방식이 빅 엔디안에 비해서 연산이나 메모리 관리가 효율적이라고 합니다.

 간혹 데이터 전송 분야같은 다른 곳에서는 빅 엔디안을 사용하는 경우가 있습니다!

 

 

반응형