Long Calls

Normally, the compilers generate a single-instruction call sequence using the BL instruction. The compilers can be forced to generate a long call sequence when the module is so large that the BL is not guaranteed to reach the beginning of the subspace. In the latter case, the linker can insert a stub. The existing long call sequence is three instructions, using an absolute target address:

LDIL L'target,%r1

BLE R'target(%sr4,%r1)

COPY %r1,%rp

When the PIC option is in effect, the compilers must generate the following instruction sequence, which is PC-relative:

BL

.+8,%rp

; get pc into rp

 

ADDIL

L'target - $L0 + 4, %rp

; add pc-rel offset to rp

 

LDO

R'target - $L1 + 8(%r1), %r1

$L0:

LDSID

(%r1), %r31

 

 

$L1:

MTSP

%r31, %sr0

 

 

 

BLE

0(%sr0,%r1)

 

 

 

COPY

%r31,%rp

 

 

Long Branches and Switch Tables

Long branches are similar to long calls, but are only two instructions because the return pointer is not needed:

LDIL L'target,%r1

BE R'target(%sr4,%r1)

For PIC, these two instructions must be transformed into four instructions, similar to the long call sequence:

BL

.+8,%r1

; get pc into r1

 

ADDIL

L'target-L,%r1

; add

pc-relative offset

L:

LDO

R'target-L,%r1

;

add

pc-relative offset

 

BV,N

0(%r1)

 

;

and

branch

The only problem with this sequence occurs when the long branch is in a switch table, where each switch table entry is restricted to two words. A long branch within a switch table must allocate a linkage table entry and make an indirect branch:

LDW

T'target(%r19),%r1

; load LT entry

 

BV,N

0(%r1)

; branch indirect

Here, the T' operator indicates a new fixup request supported by the linker for linkage table entries.

Assigned GOTO Statements

ASSIGN statements in FORTRAN must be converted to a PC-relative form. The existing sequence forms the absolute address in a register before storing it in the variable:

LDIL L'target,tmp

LDO R'target(tmp),tmp

This must be transformed into the following four-instruction sequence:

BL

.+8,tmp

; get rp into tmp

 

DEPI

0,31,2,tmp

;

zero out low-order 2 bits

L:

ADDIL

L'target-L,tmp ;

get pc-rel offset

 

LDO

R'target-L(%r1),tmp

Literal References

References to literals in the text space are handled exactly like ASSIGN statements (shown above). The LDO instruction can be replaced with LDW as appropriate.

188 Writing and Generating Position-Independent Code