※ 용어 정의 Rd: Destination Register / Rn: Operand1 Register / Rm: Operand2 Register
<cond>: Execution Condition code
<S>: S-Suffix - Status Update Suffix - SPSR의 값을 CPSR로 불러와서 Status를 Update
<!> : ! - Suffix - Writeback Suffix - [,]내의 선처리 연산 수행 후 값을 갱신
<Operand2>: Operand2가 가질 수 있는 형식
ㄱ. #Immediate: 32bit 명령에서 Immediate값은 8-bit pattern의 짝수 shift 값 만을 허용
ㄴ. Rm{, shift연산 #immediate}: Register(Rm)값에 #immediate 값으로 Shift 연산
1. 데이터 처리 명령(General Data Processing Instruction)
<ARM Instructioin Set>
① opcode<cond><S> Rd, Rn, #Immediate
② opcode<cond><S> Rd, Rn, Rm OP #Imm
③ opcode<cond><S> Rd, Rn, Rm OP Rs
- cmp, cmn 명령에서는 Rd는 무조건 '0' 값을 넣어줘야 함.(SBZ(Should Be Zero))
④ opcode<cond> Rd, Rn, #Immediate
⑤ opcode<cond> Rd, Rn, Rm OP #Imm
⑥ opcode<cond> Rd, <address>
⑦ opcode<cond><addrmode> Rm, Register_List^
⑧ opcode<cond><addrmode> Rm<!>, Register_List
⑨ opcode<cond><addrmode> Rm<!>, Register_List^
- P='1' Pre, P='0' Post / U='1' Increment, U='0' Decrement / B='1' Byte load, B='0' Word load /
W='1' Write-back(Auto-Index) W='0' / L='1' opcode는 ldr, L= '0' str /
I='1' Addr_mode가 모두 Offset field I='0' 앞에 Addr_mode는 '0' 뒤에 Addr_mode는 Rm /
S='1' Signed, S='0' Unsigned / H='1' Half Word, H='0' Word or Byte
⑩ b<cond> #Target Address(24bit Offset) - L의 값이 '1'이면 bl 명령
⑪ SWI #SWI Number
⑫ mrs<cond><S> Rd, PSR
⑬ msr<cond><S> PSR_<Field_Mask>, Rm
⑭ msr<cond><S> PSR_f, #Immediate
- S의 값이 '1'이면 SPSR에서, '0'이면 CPSR.
- SBO(Should Be One) 영역은 '1'로, SBZ(Should Be Zero) 영역은 '0'의 값을 넣어줘야 함
<cond>: Execution Condition code
<S>: S-Suffix - Status Update Suffix - SPSR의 값을 CPSR로 불러와서 Status를 Update
<!> : ! - Suffix - Writeback Suffix - [,]내의 선처리 연산 수행 후 값을 갱신
<Operand2>: Operand2가 가질 수 있는 형식
ㄱ. #Immediate: 32bit 명령에서 Immediate값은 8-bit pattern의 짝수 shift 값 만을 허용
ㄴ. Rm{, shift연산 #immediate}: Register(Rm)값에 #immediate 값으로 Shift 연산
§ Shift 연산의 종류
- asr(Arithmetic Shift Right): Immediate의 값 만큼 right shift, 앞에 bit는 Sign Extension
- lsr(Logical Shift Right): Immediate의 값 만큼 right shift, 앞에 bit는 0으로 채움
- lsl(Logical Shift Left): Immediate의 값 만큼 left shift, 뒤에 bit는 0으로 채움
- ror(ROtate Right): Immediate의 값 만큼 rotate right, rotate후 bit 0값은 carry에 저장
- rrx(Rotate Right eXtend): rrx는 1bit 씩 rotate right, bit 0값은 carry에 저장
- asr(Arithmetic Shift Right): Immediate의 값 만큼 right shift, 앞에 bit는 Sign Extension
- lsr(Logical Shift Right): Immediate의 값 만큼 right shift, 앞에 bit는 0으로 채움
- lsl(Logical Shift Left): Immediate의 값 만큼 left shift, 뒤에 bit는 0으로 채움
- ror(ROtate Right): Immediate의 값 만큼 rotate right, rotate후 bit 0값은 carry에 저장
- rrx(Rotate Right eXtend): rrx는 1bit 씩 rotate right, bit 0값은 carry에 저장
1. 데이터 처리 명령(General Data Processing Instruction)
1.1 산술 연산
add: Rd := Rn + <Operand2>
sub: Rd := Rn - <Operand2>
adc(ADd with Carry), sbc(SuBtract with Carry): Carry를 포함한 add, sub 연산
rsb(Reverse SuBtract): Rd := <Operand2> - Rn
rsc(Reverse Subract with Carry): Carry를 포함한 역 sub 연산
1.2 논리 연산
and: Rd := Rn & <Operand2>
orr: Rd := Rn | <Operand2>
eor: Rd := Rn ^ <Operand2>
bic: Rd := Rn & !<Operand2>
Syntax: add<cond><S> Rd, Rn, <Operand2>
add: Rd := Rn + <Operand2>
sub: Rd := Rn - <Operand2>
adc(ADd with Carry), sbc(SuBtract with Carry): Carry를 포함한 add, sub 연산
rsb(Reverse SuBtract): Rd := <Operand2> - Rn
rsc(Reverse Subract with Carry): Carry를 포함한 역 sub 연산
1.2 논리 연산
Syntax: and<cond><S> Rd, Rn, <Operand2>
and: Rd := Rn & <Operand2>
orr: Rd := Rn | <Operand2>
eor: Rd := Rn ^ <Operand2>
bic: Rd := Rn & !<Operand2>
1.3 Register 값 저장
mov: Rd := <Operand2>
mvn: Rd := !<Operand2>
1.4 비교
cmp: Rn값에서 Opeand2값을 빼서 그 결과를 Status flag에 반영, SUBS와 동일한 명령
cmn: Rn값에서 Operand2값을 더해서 그 결과를 Status flag에 반영, ADDS와 동일한 명령
tst: Rn과 Opearand2를 bit and 연산을 수행해서 그 결과를 Status flag에 반영, ANDS와 동일한 명령
teq: Rn과 Operand2를 bit xor 연산을 수행해서 그 결과를 Status flag에 반영, EORS와 동일한 명령
2. 메모리 접근 명령(Memory Accesss Instruction)
Syntax: ldr<cond><B> Rd, label
ldr<cond><B><T> Rd, [Rn]
ldr<cond><B> Rd, [Rn, FlexOffset]<!> ;Pre-Indexed<Auto-Indexing>
ldr<cond><B><T> Rd, [Rn], FlexOffset ;Post-Indexed
<B>: B Suffix가 있을 경우 8-bit Unsigned byte 단위로 Access, 없을 경우 32-bit word로 Access
<T>: T suffix가 있을 경우 Processor가 User mode에서 memory access 처리
FlexOffset:
ㄱ.#Immediate: -4095 부터 -4096사이의 상수 값
ㄴ.{-}Rm{, shift연산}: Rm은 음의 부호를 가질 수 있으며, Rm의 Shift 연산도 가능함
2.1 Load 또는 Store 명령 예제
ldr r0, [r1]: r1에 저장된 주소를 이용해서 메모리로부터 r0로 값을 불러옴
str r0, [r1], #4: r0의 값을 메모리의 r1의 주소에 저장하고 r1을 +4함.
참고) 부호가 있는 Halfword, Byte로 읽을 때는 SH(Signed Halfword), SB(Signed Byte) <--(ldr only)
Unsigned Halfword로 읽거나 저장할 때는 H를 사용.
Doubleword의 경우 D 를 사용, 이 때의 Offset은 {-}Rm 만 허용함.
2.2 Multiple Load 또는 Store 명령
<addrmode>: address mode에는 총 8가지가 있으며, 4가지는 address의 연상 방식에 따른
구분이며 4가지는 stack의 특성에 따른 구분이다.
- IA(Increment Address after each transfer), - IB(Increment Address after each transfer)
- DA(Decrement Address after each transfer), - DB(Decrement Address after each transfer)
- FD(Full descending stack): stack의 주소에 data가 저장이 된 상태이고, 주소가 감소하면서 저장
- ED(Emtpy descending stack): stack의 주소에 data가 없는 상태이고, 주소가 감소하면서 저장
- FA(Full ascending stack): stack의 주소에 data가 저장이 된 상태이고, 주소가 증가하면서 저장
- EA(Emtpy ascending stack): stack의 주소에 data가 없는 상태이고, 주소가 증가하면서 저장
<!>: ! - Suffix가 있을 경우 마지막 주소(최종으로 이동한 주소)를 Rn에 저장함
<^>: SPSR의 값을 CPSR에 넣어줌, S-Suffix와 동일한 기능을 수행함.
ldm: Rn으로 부터 reglist에 지정한 register 수 만큼 값을 불러옴
stm: reglist에 있는 register의 값들을 Rn에 저장함.
[주의] Reglist에 지정한 Register의 순서와 상관없이 Register의 번호가 낮은 값이
메모리의 낮은 주소에 저장 또는 읽어진다. reglist는 'r1,r2,r3' 또는 'r1-r3'으로 표현
[자주 사용되는 형식] STMFD sp!, {r4-r7,lr} / LDMFD sp!, {r4-r7,pc}
3. 분기 명령(Branch Instruction)
Syntax: b<cond> label
b: label이 있는 주소로 branch(PC값에 label의 주소를 입력)
bl: 다음 명령의 주소를 lr에 저장하고, b와 같이 label의 주소로 branch
4. 기타 명령어
4.1 Software Interrupt
swi: 지정한 번호를 갖는 Software Interrupt를 발생시킴, 해당 번호에 맞는 SWI vector로 branch
(Software Interrupt가 걸리면 프로세서의 모드는 Supervisor로 변경됨)
4.2 PSR Access
psr에 지정한 값(cpsr 또는 spsr)로 부터 값을 불러와서 Rd에 저장 (Register <- PSR)
Syntax: mov<cond><S> Rd, <Operand2>
mov: Rd := <Operand2>
mvn: Rd := !<Operand2>
1.4 비교
Syntax: cmp<cond><S> Rn, <Operand2>
cmp: Rn값에서 Opeand2값을 빼서 그 결과를 Status flag에 반영, SUBS와 동일한 명령
cmn: Rn값에서 Operand2값을 더해서 그 결과를 Status flag에 반영, ADDS와 동일한 명령
tst: Rn과 Opearand2를 bit and 연산을 수행해서 그 결과를 Status flag에 반영, ANDS와 동일한 명령
teq: Rn과 Operand2를 bit xor 연산을 수행해서 그 결과를 Status flag에 반영, EORS와 동일한 명령
2. 메모리 접근 명령(Memory Accesss Instruction)
Syntax: ldr<cond><B> Rd, label
ldr<cond><B><T> Rd, [Rn]
ldr<cond><B> Rd, [Rn, FlexOffset]<!> ;Pre-Indexed<Auto-Indexing>
ldr<cond><B><T> Rd, [Rn], FlexOffset ;Post-Indexed
<B>: B Suffix가 있을 경우 8-bit Unsigned byte 단위로 Access, 없을 경우 32-bit word로 Access
<T>: T suffix가 있을 경우 Processor가 User mode에서 memory access 처리
FlexOffset:
ㄱ.#Immediate: -4095 부터 -4096사이의 상수 값
ㄴ.{-}Rm{, shift연산}: Rm은 음의 부호를 가질 수 있으며, Rm의 Shift 연산도 가능함
2.1 Load 또는 Store 명령 예제
ldr r0, [r1]: r1에 저장된 주소를 이용해서 메모리로부터 r0로 값을 불러옴
str r0, [r1], #4: r0의 값을 메모리의 r1의 주소에 저장하고 r1을 +4함.
참고) 부호가 있는 Halfword, Byte로 읽을 때는 SH(Signed Halfword), SB(Signed Byte) <--(ldr only)
Unsigned Halfword로 읽거나 저장할 때는 H를 사용.
Doubleword의 경우 D 를 사용, 이 때의 Offset은 {-}Rm 만 허용함.
2.2 Multiple Load 또는 Store 명령
Syntax: ldm<cond><addrmode> Rn<!>, {reglist}<^>
<addrmode>: address mode에는 총 8가지가 있으며, 4가지는 address의 연상 방식에 따른
구분이며 4가지는 stack의 특성에 따른 구분이다.
- IA(Increment Address after each transfer), - IB(Increment Address after each transfer)
- DA(Decrement Address after each transfer), - DB(Decrement Address after each transfer)
- FD(Full descending stack): stack의 주소에 data가 저장이 된 상태이고, 주소가 감소하면서 저장
- ED(Emtpy descending stack): stack의 주소에 data가 없는 상태이고, 주소가 감소하면서 저장
- FA(Full ascending stack): stack의 주소에 data가 저장이 된 상태이고, 주소가 증가하면서 저장
- EA(Emtpy ascending stack): stack의 주소에 data가 없는 상태이고, 주소가 증가하면서 저장
<!>: ! - Suffix가 있을 경우 마지막 주소(최종으로 이동한 주소)를 Rn에 저장함
<^>: SPSR의 값을 CPSR에 넣어줌, S-Suffix와 동일한 기능을 수행함.
ldm: Rn으로 부터 reglist에 지정한 register 수 만큼 값을 불러옴
stm: reglist에 있는 register의 값들을 Rn에 저장함.
[주의] Reglist에 지정한 Register의 순서와 상관없이 Register의 번호가 낮은 값이
메모리의 낮은 주소에 저장 또는 읽어진다. reglist는 'r1,r2,r3' 또는 'r1-r3'으로 표현
[자주 사용되는 형식] STMFD sp!, {r4-r7,lr} / LDMFD sp!, {r4-r7,pc}
3. 분기 명령(Branch Instruction)
Syntax: b<cond> label
b: label이 있는 주소로 branch(PC값에 label의 주소를 입력)
bl: 다음 명령의 주소를 lr에 저장하고, b와 같이 label의 주소로 branch
4. 기타 명령어
4.1 Software Interrupt
Syntax: swi<cond> Immediate_24bit
swi: 지정한 번호를 갖는 Software Interrupt를 발생시킴, 해당 번호에 맞는 SWI vector로 branch
(Software Interrupt가 걸리면 프로세서의 모드는 Supervisor로 변경됨)
4.2 PSR Access
Syntax: mrs<cond> Rd, psr
psr에 지정한 값(cpsr 또는 spsr)로 부터 값을 불러와서 Rd에 저장 (Register <- PSR)
Syntax: msr<cond> psr_(field), #Immediate_8bit
msr<cond> psr_fields, Rm
Register(Rm)의 값 또는 8bit Immediate값을 psr(cpsr 또는 spsr)에 저장 (Register -> PSR)
(field): f, s, x, c 값이 선택적으로 올 수 있음. 지정한 field 영역에만 값을 저장함.
msr<cond> psr_fields, Rm
Register(Rm)의 값 또는 8bit Immediate값을 psr(cpsr 또는 spsr)에 저장 (Register -> PSR)
(field): f, s, x, c 값이 선택적으로 올 수 있음. 지정한 field 영역에만 값을 저장함.
[주의] 프로세서가 User 또는 System mode일 때는 SPSR에 엑세스 하지 말아야 한다.
[자주 사용되는 형식] msr CPSR_c,r0
[자주 사용되는 형식] msr CPSR_c,r0
5. 상태 플래그와 실행 조건 코드(Status Flags & Execution Condition Codes) N: 연산 결과가 음의 값을 가질 때 Set '1'
Z: 연산 결과가 영일 때 Set '1'
C: 연산 결과가 캐리(Carry)를 가질 때 Set '1'
V: 연산 결과 오버플로우(Overflow)를 발생시킬 때 Se
Z: 연산 결과가 영일 때 Set '1'
C: 연산 결과가 캐리(Carry)를 가질 때 Set '1'
V: 연산 결과 오버플로우(Overflow)를 발생시킬 때 Se
<ARM Instructioin Set>
① opcode<cond><S> Rd, Rn, #Immediate
② opcode<cond><S> Rd, Rn, Rm OP #Imm
③ opcode<cond><S> Rd, Rn, Rm OP Rs
- cmp, cmn 명령에서는 Rd는 무조건 '0' 값을 넣어줘야 함.(SBZ(Should Be Zero))
④ opcode<cond> Rd, Rn, #Immediate
⑤ opcode<cond> Rd, Rn, Rm OP #Imm
⑥ opcode<cond> Rd, <address>
⑦ opcode<cond><addrmode> Rm, Register_List^
⑧ opcode<cond><addrmode> Rm<!>, Register_List
⑨ opcode<cond><addrmode> Rm<!>, Register_List^
- P='1' Pre, P='0' Post / U='1' Increment, U='0' Decrement / B='1' Byte load, B='0' Word load /
W='1' Write-back(Auto-Index) W='0' / L='1' opcode는 ldr, L= '0' str /
I='1' Addr_mode가 모두 Offset field I='0' 앞에 Addr_mode는 '0' 뒤에 Addr_mode는 Rm /
S='1' Signed, S='0' Unsigned / H='1' Half Word, H='0' Word or Byte
⑩ b<cond> #Target Address(24bit Offset) - L의 값이 '1'이면 bl 명령
⑪ SWI #SWI Number
⑫ mrs<cond><S> Rd, PSR
⑬ msr<cond><S> PSR_<Field_Mask>, Rm
⑭ msr<cond><S> PSR_f, #Immediate
- S의 값이 '1'이면 SPSR에서, '0'이면 CPSR.
- SBO(Should Be One) 영역은 '1'로, SBZ(Should Be Zero) 영역은 '0'의 값을 넣어줘야 함
댓글
댓글 쓰기