Difference between revisions of "Thread Local Region"

From Nintendo Switch Brew
Jump to navigation Jump to search
m (Hexkyz moved page Thread Local Storage to Thread Local Region)
 
(2 intermediate revisions by 2 users not shown)
Line 1: Line 1:
This is the 0x200-byte TLS (thread local storage). It's base address is loaded via ARM threadid register tpidrro_el0. TLS for multiple threads are stored in the same page, with the first TLS normally located at page+0x200, because the first TLS spot is reserved for usermode exception handling.
+
This is the 0x200-byte thread local region. Its base address is loaded via ARM threadid register tpidrro_el0. TLR for multiple threads are stored in the same page, with the first TLR normally located at page+0x200, because the first TLR spot is reserved for usermode exception handling. In threads created by sdk, tpidr_el0 is assigned to the ThreadPointer object from the thread local region.
  
 
= Structure =
 
= Structure =
 +
This is "nn::svc::ThreadLocalRegion".
 +
 
{| class="wikitable" border="1"
 
{| class="wikitable" border="1"
 
|-
 
|-
 
! Offset
 
! Offset
 
! Size
 
! Size
 +
! Name
 
! Description
 
! Description
! Notes
 
 
|-
 
|-
 
| 0x0
 
| 0x0
 
| 0x100
 
| 0x100
 +
| MessageBuffer
 
| [[IPC_Marshalling|IPC]] command buffer.
 
| [[IPC_Marshalling|IPC]] command buffer.
|
 
 
|-
 
|-
| [8.0.0+] 0x100
+
| 0x100
 
| 0x2
 
| 0x2
| User Disable Count
+
| [8.0.0+] DisableCounter
 
| If userland sets this to non-zero, kernel will pin the thread and disallow calls to almost all SVCs.
 
| If userland sets this to non-zero, kernel will pin the thread and disallow calls to almost all SVCs.
 
|-
 
|-
| [8.0.0+] 0x102
+
| 0x102
 
| 0x2
 
| 0x2
| Interrupt Flag
+
| [8.0.0+] InterruptFlag
 
| If a context switch would have occurred when user disable count was non-zero, kernel will set this to 1. This signifies that the user must call [[SVC#SynchronizePreemptionState|SynchronizePreemptionState]] to unpin itself and regain access other SVCs.
 
| If a context switch would have occurred when user disable count was non-zero, kernel will set this to 1. This signifies that the user must call [[SVC#SynchronizePreemptionState|SynchronizePreemptionState]] to unpin itself and regain access other SVCs.
 
|-
 
|-
 
| 0x104
 
| 0x104
| 0xF4
+
| 0x1
| Unknown.
+
| [14.0.0+] CacheMaintenanceFlag
 +
|
 +
|-
 +
| 0x105
 +
| 0x7B
 +
| Reserved
 +
|
 +
|-
 +
| 0x180
 +
| 0x50
 +
| Tls
 +
|
 +
|-
 +
| 0x1D0
 +
| 0x8
 +
| LocalePtr
 +
|
 +
|-
 +
| 0x1D8
 +
| 0x8
 +
| ErrnoVal
 +
|
 +
|-
 +
| 0x1E0
 +
| 0x8
 +
| ThreadData
 +
|
 +
|-
 +
| 0x1E8
 +
| 0x8
 +
| EhGlobals
 +
|
 +
|-
 +
| 0x1F0
 +
| 0x8
 +
| ThreadPointer
 
|
 
|
 
|-
 
|-
 
| 0x1F8
 
| 0x1F8
 
| 0x8
 
| 0x8
| Pointer to [[Thread_Local_Storage#Thread_context|thread context]].
+
| ThreadType
|
+
| Pointer to [[#ThreadType|thread type]].
 
|}
 
|}
  
 
= Userland context =
 
= Userland context =
== Boot paramter ==
+
== OsResourceManager ==
This is "nn::os::detail::g_OsBootParamter".
+
This is "nn::os::detail::OsResourceManager".
  
 
{| class="wikitable" border="1"
 
{| class="wikitable" border="1"
Line 43: Line 80:
 
! Offset
 
! Offset
 
! Size
 
! Size
 +
! Name
 
! Description
 
! Description
 
|-
 
|-
| 0x00
+
| 0x0
| 0x04
+
| 0x14
| Main thread handle.
+
| [[#RngManager|RngManager]]
 +
|
 +
|-
 +
| 0x14
 +
| 0x4
 +
| Reserved
 +
|
 +
|-
 +
| 0x18
 +
| 0x28
 +
| [[#AslrSpaceManager|AslrSpaceManager]]
 +
|
 +
|-
 +
| 0x40
 +
| 0x28
 +
| [[#StackGuardManager|StackGuardManager]]
 +
|
 +
|-
 +
| 0x68
 +
| 0x1F0
 +
| [[#ThreadManager|ThreadManager]]
 +
|
 +
|-
 +
| 0x258
 +
| 0x110
 +
| [[#TlsManager|TlsManager]]
 +
|
 +
|-
 +
| 0x368
 +
| 0x1
 +
| [[#TickManager|TickManager]]
 +
|  
 
|-
 
|-
| 0x04
+
| 0x369
| 0x04
+
| 0x7
| Always 0.
+
| Reserved
 +
|  
 
|-
 
|-
| 0x08
+
| 0x370
 
| 0x30
 
| 0x30
| Empty.
+
| [[#MemoryHeapManager|MemoryHeapManager]]
 +
|
 +
|-
 +
| 0x3A0
 +
| 0x48
 +
| [[#VammManager|VammManager]]
 +
|
 
|}
 
|}
  
== Resource manager storage ==
+
=== RngManager ===
This is "nn::os::detail::g_OsResourceManagerStorage".
+
This is "nn::os::detail::RngManager".
  
 
{| class="wikitable" border="1"
 
{| class="wikitable" border="1"
Line 65: Line 141:
 
! Offset
 
! Offset
 
! Size
 
! Size
 +
! Name
 
! Description
 
! Description
 
|-
 
|-
| 0x00
+
| 0x0
| 0x04
+
| 0x4
| Always 0.
+
| CriticalSection
 +
|  
 
|-
 
|-
| 0x04
+
| 0x4
 
| 0x10
 
| 0x10
| Process PRNG.
+
| Random
 +
|
 +
|}
 +
 
 +
=== AslrSpaceManager ===
 +
This is "nn::os::detail::AslrSpaceManager".
 +
 
 +
{| class="wikitable" border="1"
 
|-
 
|-
| 0x14
+
! Offset
| 0x04
+
! Size
| Padding.
+
! Name
 +
! Description
 
|-
 
|-
| 0x18
+
| 0x0
| 0x08
+
| 0x20
| Always set to 0.
+
| [[#AddressSpaceAllocator|Allocator]]
 +
|  
 
|-
 
|-
 
| 0x20
 
| 0x20
| 0x08
+
| 0x1
| [[SVC#svcGetInfo|AddressSpaceStart]] right shifted by 0x0C.
+
| Impl
 +
|
 +
|-
 +
| 0x21
 +
| 0x7
 +
| Reserved
 +
|
 +
|}
 +
 
 +
=== StackGuardManager ===
 +
This is "nn::os::detail::StackGuardManager".
 +
 
 +
{| class="wikitable" border="1"
 +
|-
 +
! Offset
 +
! Size
 +
! Name
 +
! Description
 
|-
 
|-
| 0x28
+
| 0x0
| 0x08
+
| 0x20
| AddressSpaceEnd ([[SVC#svcGetInfo|AddressSpaceStart]] + [[SVC#svcGetInfo|AddressSpaceSize]]) right shifted by 0x0C and aligned to AddressSpaceAlign.
+
| [[#AddressSpaceAllocator|Allocator]]
 +
|  
 
|-
 
|-
| 0x30
+
| 0x20
| 0x08
+
| 0x1
| AddressSpaceAlign right shifted by 0x0C.
+
| Impl
 +
|  
 
|-
 
|-
| 0x38
+
| 0x21
| 0x08
+
| 0x7
| Always 0.
+
| Reserved
 +
|
 +
|}
 +
 
 +
=== ThreadManager ===
 +
This is "nn::os::detail::ThreadManager".
 +
 
 +
{| class="wikitable" border="1"
 
|-
 
|-
| 0x40
+
! Offset
| 0x08
+
! Size
| Always set to 0.
+
! Name
 +
! Description
 
|-
 
|-
| 0x48
+
| 0x0
| 0x08
+
| 0x1
| [[SVC#svcGetInfo|MapRegionBased]] right shifted by 0x0C.
+
| Impl
 +
|  
 
|-
 
|-
| 0x50
+
| 0x1
| 0x08
+
| 0x7
| MapRegionEnd ([[SVC#svcGetInfo|MapRegionBased]] + [[SVC#svcGetInfo|MapRegionSize]]) right shifted by 0x0C and aligned to MapRegionAlign.
+
| Reserved
 +
|  
 
|-
 
|-
| 0x58
+
| 0x8
| 0x08
+
| 0x1C0
| MapRegionAlign right shifted by 0x0C.
+
| [[#ThreadType|MainThread]]
 +
|  
 
|-
 
|-
| 0x60
+
| 0x1C8
| 0x08
+
| 0x4
| Always 0.
+
| CriticalSection
 +
|  
 
|-
 
|-
| 0x68
+
| 0x1CC
| 0x08
+
| 0x4
| Always 0.
+
| Reserved
 +
|  
 
|-
 
|-
| 0x70
 
 
| 0x1D0
 
| 0x1D0
| Main [[Thread_Local_Storage#Thread_context|thread context]].
+
| 0x10
 +
| AllThreadsList
 +
|
 +
|-
 +
| 0x1E0
 +
| 0x8
 +
| TotalThreadStackSize
 +
|
 +
|-
 +
| 0x1E8
 +
| 0x4
 +
| NumCreatedThreads
 +
|
 +
|-
 +
| 0x1EC
 +
| 0x4
 +
| Reserved
 +
|
 +
|}
 +
 
 +
=== TlsManager ===
 +
This is "nn::os::detail::TlsManager".
 +
 
 +
{| class="wikitable" border="1"
 +
|-
 +
! Offset
 +
! Size
 +
! Name
 +
! Description
 +
|-
 +
| 0x0
 +
| 0x4
 +
| NumUsedTlsSlots
 +
|
 +
|-
 +
| 0x4
 +
| 0x4
 +
| Reserved
 +
|
 +
|-
 +
| 0x8
 +
| 0x100
 +
| TlsDestructorArray
 +
|
 +
|-
 +
| 0x108
 +
| 0x4
 +
| TlsCriticalSection
 +
|
 +
|-
 +
| 0x10C
 +
| 0x4
 +
| Reserved
 +
|
 +
|}
 +
 
 +
=== TickManager ===
 +
This is "nn::os::detail::TickManager".
 +
 
 +
{| class="wikitable" border="1"
 +
|-
 +
! Offset
 +
! Size
 +
! Name
 +
! Description
 +
|-
 +
| 0x0
 +
| 0x1
 +
| Impl
 +
|
 +
|}
 +
 
 +
=== MemoryHeapManager ===
 +
This is "nn::os::detail::MemoryHeapManager".
 +
 
 +
{| class="wikitable" border="1"
 +
|-
 +
! Offset
 +
! Size
 +
! Name
 +
! Description
 +
|-
 +
| 0x0
 +
| 0x8
 +
| HeapAddress
 +
|
 +
|-
 +
| 0x8
 +
| 0x8
 +
| HeapSize
 +
|
 
|-
 
|-
| 0x240
+
| 0x10
| 0x08
+
| 0x8
| Pointer to main [[Thread_Local_Storage#Thread_context|thread context]].
+
| UsedHeapSize
 +
|
 +
|-
 +
| 0x18
 +
| 0x10
 +
| FreeMemoryList
 +
|  
 
|-
 
|-
| 0x248
+
| 0x28
| 0x08
+
| 0x4
| Unknown.
+
| CriticalSection
 +
|  
 
|-
 
|-
| 0x250
+
| 0x2C
| 0x08
+
| 0x4
| Unknown.
+
| Impl
 +
|
 +
|}
 +
 
 +
=== VammManager ===
 +
This is "nn::os::detail::VammManager".
 +
 
 +
{| class="wikitable" border="1"
 
|-
 
|-
| 0x258
+
! Offset
| 0x130
+
! Size
| Always empty?
+
! Name
 +
! Description
 
|-
 
|-
| 0x388
+
| 0x0
| 0x08
+
| 0x8
| Pointer to [[Thread_Local_Storage#Resource_manager_storage|resource manager storage]] + 0x388.
+
| ReservedRegionAddress
 +
|  
 
|-
 
|-
| 0x390
+
| 0x8
| 0x08
+
| 0x8
| Pointer to [[Thread_Local_Storage#Resource_manager_storage|resource manager storage]] + 0x388.
+
| ReservedRegionSize
 +
|  
 
|-
 
|-
| 0x398
+
| 0x10
| 0x08
+
| 0x30
| Always 0.
+
| ReaderWriterLock
 +
|  
 
|-
 
|-
| 0x3A0
+
| 0x40
| 0x08
+
| 0x8
| Always 0.
+
| RegionManager
 +
|  
 
|}
 
|}
  
== Thread context ==
+
=== AddressSpaceAllocator ===
This structure is used for describing each thread's context. In the main thread's case, this structure comes from the [[Thread_Local_Storage#Resource_manager_storage|resource manager storage]].
+
This is "nn::os::detail::AddressSpaceAllocator".
  
 
{| class="wikitable" border="1"
 
{| class="wikitable" border="1"
Line 167: Line 394:
 
! Offset
 
! Offset
 
! Size
 
! Size
 +
! Name
 
! Description
 
! Description
 
|-
 
|-
| 0x00
+
| 0x0
| 0x08
+
| 0x4
| Pointer to [[Thread_Local_Storage#Thread_context|thread context]] + 0x1C8.
+
| CriticalSection
 +
|
 +
|-
 +
| 0x4
 +
| 0x4
 +
| Reserved
 +
|  
 
|-
 
|-
| 0x08
+
| 0x8
| 0x08
+
| 0x8
| Pointer to [[Thread_Local_Storage#Thread_context|thread context]]
+
| BeginPage
 +
|  
 
|-
 
|-
 
| 0x10
 
| 0x10
| 0x08
+
| 0x8
| Pointer to [[Thread_Local_Storage#Thread_context|thread context]] + 0x10.
+
| EndPage
 +
|  
 
|-
 
|-
 
| 0x18
 
| 0x18
| 0x08
+
| 0x8
| Pointer to [[Thread_Local_Storage#Thread_context|thread context]] + 0x10.
+
| GuardPageCount
 +
|
 +
|}
 +
 
 +
== ThreadType ==
 +
This is "nn::os::ThreadType".
 +
 
 +
{| class="wikitable" border="1"
 +
|-
 +
! Offset
 +
! Size
 +
! Name
 +
! Description
 +
|-
 +
| 0x00
 +
| 0x10
 +
| AllThreadsListNode
 +
|
 +
|-
 +
| 0x10
 +
| 0x10
 +
| MultiWaitObjectList
 +
|
 
|-
 
|-
 
| 0x20
 
| 0x20
 
| 0x20
 
| 0x20
| Empty.
+
| Reserved
 +
|
 
|-
 
|-
 
| 0x40
 
| 0x40
| 0x04
+
| 0x01
 +
| State
 
| Thread status.
 
| Thread status.
 +
|-
 +
| 0x41
 +
| 0x01
 +
| StackIsAliased
 +
|
 +
|-
 +
| 0x42
 +
| 0x01
 +
| AutoRegistered
 +
|
 +
|-
 +
| 0x43
 +
| 0x01
 +
| SuspendCount
 +
|
 
|-
 
|-
 
| 0x44
 
| 0x44
| 0x04
+
| 0x02
 +
| BasePriority
 
| Thread priority minus 0x1C.
 
| Thread priority minus 0x1C.
 +
|-
 +
| 0x46
 +
| 0x02
 +
| Version
 +
|
 
|-
 
|-
 
| 0x48
 
| 0x48
 
| 0x08
 
| 0x08
 +
| OriginalStack
 
| Thread stack base address.
 
| Thread stack base address.
 
|-
 
|-
 
| 0x50
 
| 0x50
 
| 0x08
 
| 0x08
 +
| Stack
 
| Thread stack base address mirror.
 
| Thread stack base address mirror.
 
|-
 
|-
 
| 0x58
 
| 0x58
 
| 0x08
 
| 0x08
 +
| StackSize
 
| Thread stack size.
 
| Thread stack size.
 
|-
 
|-
 
| 0x60
 
| 0x60
 
| 0x08
 
| 0x08
| Thread stub pointer.
+
| Argument
 +
|
 
|-
 
|-
 
| 0x68
 
| 0x68
 
| 0x08
 
| 0x08
| Thread ID.
+
| ThreadFunction
 +
|
 
|-
 
|-
 
| 0x70
 
| 0x70
 
| 0x08
 
| 0x08
| Always 0?
+
| CurrentFiber
 +
|
 
|-
 
|-
 
| 0x78
 
| 0x78
 
| 0x08
 
| 0x08
| Always 0?
+
| InitialFiber
 +
|
 
|-
 
|-
 
| 0x80
 
| 0x80
| 0x08
 
| Always 0?
 
|-
 
| 0x88
 
 
| 0x100
 
| 0x100
 +
| TlsValueArray
 
| TLS slots.
 
| TLS slots.
 
|-
 
|-
| 0x188
+
| 0x180
 
| 0x20
 
| 0x20
 +
| ThreadNameBuffer
 
| Thread name.
 
| Thread name.
 
|-
 
|-
| 0x1A8
+
| 0x1A0
 
| 0x08
 
| 0x08
 +
| NamePointer
 
| Thread name address.
 
| Thread name address.
 
|-
 
|-
| 0x1B0
+
| 0x1A8
 
| 0x04
 
| 0x04
| Critical Section.
+
| CsThread
 +
| Critical Section Storage.
 
|-
 
|-
| 0x1B4
+
| 0x1AC
 
| 0x04
 
| 0x04
| Conditional Variable.
+
| CvThread
 +
| Conditional Variable Storage.
 
|-
 
|-
| 0x1B8
+
| 0x1B0
 
| 0x04
 
| 0x04
 +
| Handle
 
| Thread handle.
 
| Thread handle.
 
|-
 
|-
| 0x1BC
+
| 0x1B4
 
| 0x04
 
| 0x04
| Always 0.
+
| LockHistory
 +
|
 
|-
 
|-
| 0x1C0
+
| 0x1B8
 
| 0x08
 
| 0x08
| Thread global mutex.
+
| ThreadId
|-
+
|
| 0x1C8
 
| 0x08
 
| Unknown.
 
 
|}
 
|}

Latest revision as of 20:23, 5 September 2024

This is the 0x200-byte thread local region. Its base address is loaded via ARM threadid register tpidrro_el0. TLR for multiple threads are stored in the same page, with the first TLR normally located at page+0x200, because the first TLR spot is reserved for usermode exception handling. In threads created by sdk, tpidr_el0 is assigned to the ThreadPointer object from the thread local region.

Structure

This is "nn::svc::ThreadLocalRegion".

Offset Size Name Description
0x0 0x100 MessageBuffer IPC command buffer.
0x100 0x2 [8.0.0+] DisableCounter If userland sets this to non-zero, kernel will pin the thread and disallow calls to almost all SVCs.
0x102 0x2 [8.0.0+] InterruptFlag If a context switch would have occurred when user disable count was non-zero, kernel will set this to 1. This signifies that the user must call SynchronizePreemptionState to unpin itself and regain access other SVCs.
0x104 0x1 [14.0.0+] CacheMaintenanceFlag
0x105 0x7B Reserved
0x180 0x50 Tls
0x1D0 0x8 LocalePtr
0x1D8 0x8 ErrnoVal
0x1E0 0x8 ThreadData
0x1E8 0x8 EhGlobals
0x1F0 0x8 ThreadPointer
0x1F8 0x8 ThreadType Pointer to thread type.

Userland context

OsResourceManager

This is "nn::os::detail::OsResourceManager".

Offset Size Name Description
0x0 0x14 RngManager
0x14 0x4 Reserved
0x18 0x28 AslrSpaceManager
0x40 0x28 StackGuardManager
0x68 0x1F0 ThreadManager
0x258 0x110 TlsManager
0x368 0x1 TickManager
0x369 0x7 Reserved
0x370 0x30 MemoryHeapManager
0x3A0 0x48 VammManager

RngManager

This is "nn::os::detail::RngManager".

Offset Size Name Description
0x0 0x4 CriticalSection
0x4 0x10 Random

AslrSpaceManager

This is "nn::os::detail::AslrSpaceManager".

Offset Size Name Description
0x0 0x20 Allocator
0x20 0x1 Impl
0x21 0x7 Reserved

StackGuardManager

This is "nn::os::detail::StackGuardManager".

Offset Size Name Description
0x0 0x20 Allocator
0x20 0x1 Impl
0x21 0x7 Reserved

ThreadManager

This is "nn::os::detail::ThreadManager".

Offset Size Name Description
0x0 0x1 Impl
0x1 0x7 Reserved
0x8 0x1C0 MainThread
0x1C8 0x4 CriticalSection
0x1CC 0x4 Reserved
0x1D0 0x10 AllThreadsList
0x1E0 0x8 TotalThreadStackSize
0x1E8 0x4 NumCreatedThreads
0x1EC 0x4 Reserved

TlsManager

This is "nn::os::detail::TlsManager".

Offset Size Name Description
0x0 0x4 NumUsedTlsSlots
0x4 0x4 Reserved
0x8 0x100 TlsDestructorArray
0x108 0x4 TlsCriticalSection
0x10C 0x4 Reserved

TickManager

This is "nn::os::detail::TickManager".

Offset Size Name Description
0x0 0x1 Impl

MemoryHeapManager

This is "nn::os::detail::MemoryHeapManager".

Offset Size Name Description
0x0 0x8 HeapAddress
0x8 0x8 HeapSize
0x10 0x8 UsedHeapSize
0x18 0x10 FreeMemoryList
0x28 0x4 CriticalSection
0x2C 0x4 Impl

VammManager

This is "nn::os::detail::VammManager".

Offset Size Name Description
0x0 0x8 ReservedRegionAddress
0x8 0x8 ReservedRegionSize
0x10 0x30 ReaderWriterLock
0x40 0x8 RegionManager

AddressSpaceAllocator

This is "nn::os::detail::AddressSpaceAllocator".

Offset Size Name Description
0x0 0x4 CriticalSection
0x4 0x4 Reserved
0x8 0x8 BeginPage
0x10 0x8 EndPage
0x18 0x8 GuardPageCount

ThreadType

This is "nn::os::ThreadType".

Offset Size Name Description
0x00 0x10 AllThreadsListNode
0x10 0x10 MultiWaitObjectList
0x20 0x20 Reserved
0x40 0x01 State Thread status.
0x41 0x01 StackIsAliased
0x42 0x01 AutoRegistered
0x43 0x01 SuspendCount
0x44 0x02 BasePriority Thread priority minus 0x1C.
0x46 0x02 Version
0x48 0x08 OriginalStack Thread stack base address.
0x50 0x08 Stack Thread stack base address mirror.
0x58 0x08 StackSize Thread stack size.
0x60 0x08 Argument
0x68 0x08 ThreadFunction
0x70 0x08 CurrentFiber
0x78 0x08 InitialFiber
0x80 0x100 TlsValueArray TLS slots.
0x180 0x20 ThreadNameBuffer Thread name.
0x1A0 0x08 NamePointer Thread name address.
0x1A8 0x04 CsThread Critical Section Storage.
0x1AC 0x04 CvThread Conditional Variable Storage.
0x1B0 0x04 Handle Thread handle.
0x1B4 0x04 LockHistory
0x1B8 0x08 ThreadId