- What's Assembly Language
CPU는 전기 신호를 받아들이는 '회로' 이다.
따라서 CPU로 명령을 전달할 때는 전기 신호로 전달하는데, 이 신호를 전압에 따라 0과 1로 표현할 수 있다.
이 0과 1로 구성된 신호를 '기계어' 라고 한다.
프로그램은 CPU에게 일련의 명령을 내리는데, 사람이 CPU에게 내릴 명령을 작성할 때 0과 1로 구성된 기계어로 명령을 작성하는 것은 매우 어렵다.
따라서 프로그램을 작성하는 사람의 편의를 위해 만들어진 High Level Language 가 C, Python 같은 언어이다.
물론 High Level Language 는 CPU 같은 회로가 이해할 수 있는 형태가 아니기에 이를 변환하는 과정이 필요하고,
이를 '컴파일' 이라고 한다.
컴파일의 과정은 각 언어에 따른 '컴파일러' 가 수행한다.
(파이썬 같은 언어는 인터프리터가 수행한다.)
어셈블리 언어 관점에서 '컴파일' 은 High Level Language 를 Assembly Langulage 로 변환하는 과정이다.
기계어로의 변환은 어셈블러가 담당한다.
예전에는 프로그래밍을 하다가 로우레벨에서 문제가 생겼을 때 디버깅을 해야하는 상황이 있었다고 한다.
그럴 때 기계어를 직접 보는 것이 너무 불편하기 때문에 만들어진 언어가 '어셈블리 언어' 이다.
즉, 기계어를 사람이 볼 수 있는 형태로 변환한 것이 어셈블리 언어이다.
그렇기 때문에 기계에 매우 가까운 언어이다.
'CPU가 이해할 수 있는 기계어' 의 형태는 표준이 없어 CPU 회사마다, 제조사마다 다르다.
그래서 같은 ARM 계열이라도 안드로이드, 애플, AMD 의 프로세서가 이해하는 기계어가 모두 다르다.
이때 'CPU가 이해할 수 있는 기계어' 의 정해진 형태를 '명령어 (Instruction)' 라고 하며 명령어는 CPU가 처리해야할 작업이 무엇인지를 알려준다. (Instruct)
명령어는 일종의 '데이터' 이기도 하다.
폰 노이만의 컴퓨터에서는 이 명령어들을 메모리에 넣고 순차적으로 실행하기 때문에, 명령어도 하나의 데이터인 셈이다.
각 제조사마다 CPU 회사마다 이 명령어의 형태가 모두 다르다고 볼 수 있다.
명령어의 길이(사이즈), 명령어 내에서 각 부분이 의미하는 것들 구분되어 있는 포맷이 서로 다르다.
(예로 32bit CPU는 32bit 사이즈의 명령어를 처리한다.)
명령어 내에서 어떤 부분은 처리해야할 데이터를 의미하고, 어떤 부분은 그 데이터를 가지고 할 작업을 의미하는 등, 구성이 다르다.
하지만 이걸 숫자로 보는게 어려우니 어셈블리 언어의 형태로 보는 것
어셈블리 언어는 flexible 하지 않다. a + b + c 를 한번에 연산하지 못한다.
(가능한 경우가 있긴하나, 32bit 라는 한정된 사이즈에서는 3개의 피연산자를 다 저장할 수 없기 때문에)
=> 그럼 64비트에서는 가능하려나? x86은 32bit 임에도 이 제한을 극복했지만 명령어 종류가 많아서 복잡하다고 한다.
- Why We Learn Assembly Language
1. 더 빠른 프로그램을 만들 수 있다
컴파일러가 표준화 되어있기 때문에 모든 상황에 대응하기 위해서 컴파일 과정에서 비효율적인 어셈블리 코드도 생성하기 때문에 아주 틀린 말은 아니다.
-> 그러나 요즘은 하드웨어 성능이 올라가서 별 차이가 없다.
2. 하드웨어를 원하는대로 직접 컨트롤 할 수 있다.
그래픽카드, 디스플레이 같은 IO 를 컨트롤 할 때 일종의 API를 쓰는데, 이를 사용하는 것보다 어셈블리어로 조작할 때 더 많은 조작이 가능하다.
그러나 정말 low 레벨이라서 보기 간단하지는 않아 실제로는 API를 쓰는게 낫다.
3. 컴퓨터가 동작하는 방식을 이해할 수 있다.
어셈블리 언어로 코드를 짜다보면 CPU가 실제로 어떻게 동작하는지를 이해하는데 도움이 된다.
- ISA
CPU마다 다룰 수 있는 명령어 종류가 다른데, 이 명령어 셋을 ISA (Instructions Set Architecture) 라고 한다.
레지스터 타입과 메모리 모델도 ISA 마다 정해져 있다.
따라서 ISA는 CPU하고 세트다.
그냥 CPU 제조사에서 이 CPU를 다룰 땐 이런 명령어들로 다루세요~ 하고 주는 메뉴얼과 같은 존재라고 보면 된다.
그래서 특정 프로세서를 대상으로 작성된 프로그램은 다른 프로세서 위에서 돌아가지 않는다
유명한 ISA : x86(PC), ARM(Mobile), SPARC (Server) 등
=> 그러면 Windows 프로그램이 AMD CPU 하고 Intel CPU 모두에서 돌아갈 수 있는 이유는 무엇인가?
Why can an executable run on both Intel and AMD processors?
How is it that an executable can work on both AMD and Intel systems? Aren't AMD's and Intel's instruction sets different? How does the executable work on both? How exactly do they compile the files...
stackoverflow.com
역시 스택 오버플로우에 답이 있었다.
AMD 와 Intel CPU 는 32bit 라면 x86, 64bit 라면 x64 라는 공통의 ISA 를 가지고 있으나 이 ISA 의 Instructions 를 어떻게 구현하는지에 차이가 있다고 한다.
즉, 명령어를 어떻게 실행시킬지 칩의 구조의 차이만 있을 뿐, ISA는 같기 때문에 x64 위에서 돌아가는 프로그램은 Intel 이든 AMD 든 상관없이 돌아갈 수 있다는 얘기
'CS > 어셈블리' 카테고리의 다른 글
[SPARC] 6. Pipelining Hazard (2) | 2023.09.21 |
---|---|
[SPARC] 5. Pipelining Analogy & SPARC Pipeline Stage Example (1) | 2023.09.19 |
[SPARC] 4. Stack Machine, Single Register Machine, Multiple Register Machine (0) | 2023.09.14 |
[SPARC] 3. Computer System Organization (CPU Machine Type) (0) | 2023.09.13 |
[SPARC] 2. Computer System Organization (2) | 2023.09.08 |