Skip Navigation Links | |
Exit Print View | |
SPARC Assembly Language Reference Manual Oracle Solaris 11.1 Information Library |
2. Executable and Linking Format
3. Directives and Pseudo-Operations
5.3 Global Object Table (GOT) Code Models
5.4 Thread Local Storage (TLS) Code Models
5.4.1 Local Executable Code Model
5.4.2 Initial Executable Code Model
6. Writing Functions -- The SPARC ABI
7. Assembler Inline Functions and __asm Code
A. Using the Assembler Command Line
The local executable code model uses the fastest code sequence, but it can only be used for code within an executable accessing a variable within that executable.
The initial executable code model allows code in the executable to access TLS variables in the shared objects to which the executable has been statically linked. The IE code is somewhat slower than the LE code.
The local dynamic code model allows code in a shared object to access TLS variables of its own. The LD code is usually somewhat slower than the IE code.
The general dynamic code model allows code from anywhere to access TLS variables anywhere. So, the executable could access a TLS variable in a dynamically linked shared object, for example. The GD code is the slowest.
Note that on Solaris, the %g7 register is used by the OS to point to thread data, and the TLS variables are sometimes accessed through this register. The program should not modify %g7 or unpredicatable results will happen.
An example of the code for the local executable TLS code model is shown below:
add: sethi %tle_hix22(sum),%o3 xor %o3,%tle_lox10(sum),%o2 ld [%g7+%o2],%o1 add %o1,%o0,%g4 retl st %g4,[%g7+%o2]
It takes two instructions to form the address of sum. The operators act as follows:
|
An example of the code for the initial executable TLS code model is shown below:
add: rd %pc,%o1 sethi %pc22(_GLOBAL_OFFSET_TABLE_-(.L900000106-.)),%g1 add %g1,%pc10(_GLOBAL_OFFSET_TABLE_-(.L900000106-.)),%g1 add %g1,%o1,%o1 sethi %tie_hi22(sum),%o3 add %o3,%tie_lo10(sum),%o2 ldx [%o1+%o2],%g5,%tie_ldx(sum) add %g7,%g5,%g3,%tie_add(sum) ld [%g3],%g4 add %g4,%o0,%g2 retl st %g2,[%g3]
Here it takes four instructions to form a pointer to the GOT into register %o1, followed by two instruction to form the offset of the address of sum in the GOT.
The operators act as follows:
|
An example of the local dynamic TLS code model is shown below:
add: save %sp,-176,%sp .L900000107: rd %pc,%i3 sethi %pc22(_GLOBAL_OFFSET_TABLE_-(.L900000107-.)),%g1 add %g1,%pc10(_GLOBAL_OFFSET_TABLE_-(.L900000107-.)),%g1 add %g1,%i3,%i3 sethi %tldm_hi22(sum),%i2 add %i2,%tldm_lo10(sum),%i1 add %i3,%i1,%o0,%tldm_add(sum) call __tls_get_addr,%tldm_call(sum) nop sethi %tldo_hix22(sum),%l7 xor %l7,%tldo_lox10(sum),%l6 add %o0,%l6,%l4,%tldo_add(sum) ld [%l4],%l5 add %l5,%i0,%l3 st %l3,[%l4] ret restore %g0,%g0,%g0
Notice that we could nothave a leaf routine because of the call instruction.
There are four instructions to form a pointer to the GOT into register %i3. Then it takes two more instructions to form the offset of the address of sum in the GOT, and another instruction to add those to the address of the GOT to form the address of the GOT slot for sum. This address is passed to function __tls_get_addr that returns the address for local module's TLS data in register %o0. Three more instructions form the offset of sum in the module data and to add that to the module data address. Note that the module data address can be reused to access multiple TLS variables.
The operators act as follows:
|
An example of the general dynamic TLS code model is shown below:
add: save %sp,-176,%sp .L900000107: rd %pc,%i3 sethi %pc22(_GLOBAL_OFFSET_TABLE_-(.L900000107-.)),%g1 add %g1,%pc10(_GLOBAL_OFFSET_TABLE_-(.L900000107-.)),%g1 add %g1,%i3,%i3 sethi %tgd_hi22(sum),%i2 add %i2,%tgd_lo10(sum),%i1 add %i3,%i1,%o0,%tgd_add(sum) call __tls_get_addr,%tgd_call(sum) nop ld [%o0],%l7 add %l7,%i0,%l6 st %l6,[%o0] ret restore %g0,%g0,%g0
Notice that we could not have a leaf routine because of the call instruction.
There are four instructions to form a pointer to the GOT into register %i3, followed by two more instruction to form the offset of the address of sum in the GOT, and another instruction to add those to the address of the GOT to form the address of the GOT slot for sum. This address is passed to function __tls_get_addr that returns the address for sum in register %o0.
The operators act as follows:
|