Skip to content
Claudiu Zissulescu edited this page Nov 2, 2020 · 6 revisions

ARC64 status

Supported addressing modes

Addressing Type Example
Direct LD/ST ld Ra,[@Symbol/32-bit known address]
Indirect LD/ST ld Ra,[Rb]
Index/Offset LD/ST ld Ra,[Rb+s9]
Scalled Offset LD/ST ld.as Ra,[Rb+s9]
Index/Register LD ld Ra,[Rb + Ri]
Scalled Register LD ld.as Ra,[Rb + Ri]
Pre-modify LD/ST ld.a Ra,[Rb + s9]
Post-modify LD/ST ld.ab Ra,[Rb + s9]

Memory models and call instructions

Model Predicated call Binds locally Symbol Ref Register Ref
small bl/b jl/j bl/b bl/b jl/j
medium only via reg bl/b bl/b jl/j
large only via reg bl/b via jl/j jl/j

Memory models and addresses types

Type Small Medium Large
non-pic LO32 LO32 HI/LO
non-pic (weak) LO32 LO32 HI/LO
pic N.A. GOT32 TBD
pic (local) N.A. pc-rel pc-rel

PIC addressing

For a small/medium memory model (fpic), we use the signed 32-bit PC-rel offset to the symbol in GOT table.

ld  reg,[pcl, @symb@gotpc] R_ARC_GOTPC32

where R_ARC_GOTPC32 is ME (GOT + G + A - P)

For a large memory model (fPIC), we have two proposals:

  1. Using _GLOBAL_OFFSET_TABLE_ symbol as an anchor (upper 32bit), and an offset (lower 35bit) in GOT table to the symbol of interest.
  2. Using an anchor (upper 32bit) to the symbol in GOT table, and the offset (lower 32bit) from the symbol anchor to the GOT entry.

Using _GLOBAL_OFFSET_TABLE_

The idea is to use the upper 32bit of the PC-relative offset to the address of the GOT table. Hence, this upper 32-bit offset it acts like a 4G page address. To have the full addressing within a page, we need another offest from the start of GOT page to the desired symbol.

    PAGE (_GLOBAL_OFFSET_TABLE_)
    +------------------------------------+
    | hi 32bit address | 000000000000000 |
    +------------------+-----------------+
                       |
		       |    symbol @foo
		       + -> +------------------+
		            |   35bit offset   |
			    +------------------+

Example:

addhl_s  gp,pcl,_GLOBAL_OFFSET_TABLE_@hi32gotpc # R_ARC_HI32_GOTPC
ldl.as    reg,[gp,@foo@gotoff] # R_ARC_SCALLED_GOTOFF

where:

  • R_ARC_HI32_GOTPC is ME(((GOT_BEGIN & ~0xffffffff) - (P & ~0xffffffff)) >> 32)
  • R_ARC_SCALLED_GOTOFF is ME(UNSIGNED32((S + A - GOT + (GOT_BEGIN & 0xffffffff)) >> 3)

Using GOT symbol page address

This techinque is symilar with the above one, but the anchor is not anylonger the GOT_BEGIN address, but the symbol itself, and a displacement to where the symbol is. The displacement is guaranteed to fit within 32bit offset.

Example:

addhl_s  gp,pcl,@foo@hi32gotpc # R_ARC_HI32_GOTPC
ldl      reg,[gp,@foo@gotoff]  # R_ARC_GOTDISP

where:

  • R_ARC_HI32_GOTPC is ME(((GOT + G + A) & ~0xffffffff - (P & ~0xffffffff)) >> 32)
  • R_ARC_GOTDISP is ME(UNSIGNED32(S + A - GOT + ((GOT + G + A) & 0xffffffff)))

Discussion

Using as an anchor _GLOBAL_OFFSET_TABLE_ has an advantage when speaking about code-size, as once the page symbol is loaded, any other GOT symbol will be addressed using only the lower part. For example:

addhl_s  gp,pcl,_GLOBAL_OFFSET_TABLE_@hi32gotpc # R_ARC_HI32_GOTPC
ldl.as   reg,[gp,@foo@gotoff] # R_ARC_SCALLED_GOTOFF
ldl.as   reg,[gp,@bar@gotoff] # R_ARC_SCALLED_GOTOFF

Hower this tehnique only partailly address the entire 64bit data space. As oposite to the second one which has no such limitation. However, for any GOT address we need to have two instructions one which loads the symbol page address and the other one the displacement. For example:

addhl_s  gp,pcl,@foo@hi32gotpc # R_ARC_HI32_GOTPC
ldl      reg,[gp,@foo@gotoff]  # R_ARC_GOTDISP
addhl_s  gp,pcl,@bar@hi32gotpc # R_ARC_HI32_GOTPC
ldl      reg,[gp,@bar@gotoff]  # R_ARC_GOTDISP

Conditional execution

Conditional execution is supported for all the instructions marked so in the ARC64 instruction support table. The predicated return instructions (i.e.jcc [blink]) are generated only with a ifcvt.c mainline patch.

Compare with zero.

Most of ARC64 instructions accept .f flag which implements (mostly) a compare with zero of the resulted operations. These patterns are supported by the compiler via combiner pass.

Overview of ARC64 instructions support

Mnemonic Type short predicated normal
abs ARITH 1 N.A. 1
absl ARITH N.A. 1
adc ARITH Not used
adcl ARITH N.A. 1
add ARITH 1 1 1
add1 ARITH 1 1
add1l ARITH N.A. 1
add2 ARITH 1 1
add2l ARITH N.A. 1
add3 ARITH 1 1
add3l ARITH N.A. 1
addhl ARITH 1 1
addl ARITH N.A. 1 1
aex CORE_CTRL N.A. N.A. builtin
aexl CORE_CTRL N.A. N.A. builtin
and LOGIC 1 1
andl LOGIC N.A. 1 1
asl LOGIC 1 1
asll LOGIC 1 1
asr LOGIC 1 1
asr16 LOGIC
asr8 LOGIC
asrl LOGIC 1 1
b JUMP 1 1 1
bbit0 JUMP
bbit1 JUMP
bclr LOGIC
bclrl LOGIC
bi JUMP
bic LOGIC 1 1
bicl LOGIC N.A. 1
bih JUMP
bl JUMP Linker 1 1
bmsk LOGIC
bmskl LOGIC N.A.
bmskn LOGIC
bmsknl LOGIC N.A.
breq JUMP 0 0
breql JUMP N.A. 0 0
brge JUMP 0 0
brgel JUMP N.A. 0 0
brhs JUMP 0 0
brhsl JUMP N.A. 0 0
brk CORE_CTRL N.A. N.A. builtin
brlo JUMP 0 0
brlol JUMP N.A. 0 0
brlt JUMP 0 0
brltl JUMP N.A. 0 1
brne JUMP 0 0
brnel JUMP N.A. 0 0
bset LOGIC N.A. 1
bsetl LOGIC N.A. 1
btst COMPARE 1 Ignore 1
btstl COMPARE N.A. Ignore 1
bxor LOGIC N.A. 1
bxorl LOGIC N.A. 1
clri CORE_CTRL N.A. N.A.
cmp COMPARE 1 0 1
cmpl COMPARE N.A. 1
dbnz JUMP N.A. N.A. 1
div ARITH N.A. 1
divl ARITH N.A. 1
divu ARITH N.A. 1
divul ARITH N.A. 1
dmb CORE_CTRL N.A.
dsync CORE_CTRL N.A.
ex CORE_CTRL N.A.
exl CORE_CTRL N.A.
extb MOVE N.A. 1 1
exth MOVE N.A. 1 1
ffs LOGIC N.A. N.A.
ffsl LOGIC N.A. N.A.
flag CORE_CTRL N.A. N.A.
fls LOGIC N.A. N.A.
flsl LOGIC N.A. N.A.
j JUMP 1 1 1
jl JUMP 1 1 1
kflag CORE_CTRL N.A. N.A.
ld MOVE N.A. 1
llock ATOMIC N.A. N.A. 1
llockl ATOMIC N.A. N.A. 1
lr CORE_CTRL N.A. N.A. 1
lrl CORE_CTRL N.A. N.A.
lsl16 LOGIC
lsl8 LOGIC
lsr LOGIC 1 1
lsr16 LOGIC
lsr8 LOGIC
lsrl LOGIC N.A. 1 1
lstl LOGIC N.A.
max ARITH N.A. 1 1
maxl ARITH N.A. 1 1
min ARITH N.A. 1 1
minl ARITH N.A. 1 1
mov MOVE 1 1 1
movhl MOVE 1 1
movl MOVE 1 1 1
mpy ARITH 1 1 1
mpyl ARITH N.A. 1 1
mpymul ARITH N.A. 1
mpym ARITH N.A. 1
mpyml ARITH N.A. 1
mpymsul ARITH N.A. 1
mpymu ARITH N.A. 1
mpyu ARITH 1 1
mpyuw ARITH 1 1 1
mpyw ARITH 1 1 1
mpywhfl ARITH
mpywhflr ARITH
mpywhfm ARITH
mpywhfmr ARITH
mpywhkl ARITH
mpywhkul ARITH
mpywhl ARITH
mpywhul ARITH
neg ARITH N.A. 1
nop CORE_CTRL 1 N.A. N.A.
norm LOGIC
normh LOGIC
norml LOGIC
not LOGIC 1 1
notl LOGIC N.A. 1
or LOGIC 1 1 1
orl LOGIC N.A. 1 1
rcmp COMPARE N.A. Ignore 1
rcmpl COMPARE N.A. Ignore 1
rem ARITH N.A. 1
reml ARITH N.A. 1
remu ARITH N.A. 1
remul ARITH N.A. 1
rlc LOGIC
rol LOGIC N.A. 1
rol8 LOGIC N.A. 1
ror LOGIC N.A. 1 1
ror8 LOGIC N.A. 1
rrc LOGIC
rsub ARITH N.A. 1
rtie CORE_CTRL
sbc ARITH
sbcl ARITH N.A. 1
scond ATOMIC N.A. N.A. 1
scondl ATOMIC N.A. N.A. 1
seteq COMPARE N.A. 1 1
seteql COMPARE N.A. 1 1
setge COMPARE N.A. 1 1
setgel COMPARE N.A. 1 1
setgt COMPARE N.A. 1 1
setgtl COMPARE N.A. 1 1
seths COMPARE N.A. 1 1
sethsl COMPARE N.A. 1 1
seti CORE_CTRL
setle COMPARE N.A. 1 1
setlel COMPARE N.A. 1 1
setlo COMPARE N.A. 1 1
setlol COMPARE N.A. 1 1
setlt COMPARE N.A. 1 1
setltl COMPARE N.A. 1 1
setne COMPARE N.A. 1 1
setnel COMPARE N.A. 1 1
sexb MOVE 1 1 1
sexbl MOVE N.A. 1
sexh MOVE 1 1 1
sexhl MOVE N.A. 1
sexwl MOVE N.A. 1
sleep CORE_CTRL
sqrt ARITH
sr CORE_CTRL N.A. N.A. 1
srl CORE_CTRL N.A. N.A.
st MOVE N.A. 1
sub ARITH 1 1
sub1 ARITH N.A. 1
sub1l ARITH N.A. 1
sub2 ARITH N.A. 1
sub2l ARITH N.A. 1
sub3 ARITH N.A. 1
sub3l ARITH N.A. 1
subl ARITH 1 1
swap LOGIC
swape LOGIC
swapel LOGIC
swapl LOGIC
swi CORE_CTRL
sync CORE_CTRL
tst COMPARE 1 N.A. 1
tstl COMPARE N.A. N.A. 1
umaxl ARITH N.A.
uminl ARITH N.A.
wevt ATOMIC
wlfc ATOMIC
xbfu LOGIC N.A. 1
xbful LOGIC N.A. 1
xor LOGIC 1 1 1
xorl LOGIC N.A. 1 1