NSO is the main executable format.
It starts with the "NSO" header and mainly describes .text, .rodata, and .data segments (like a short-form of ELF program headers):
Offset
|
Size
|
Description
|
0x0
|
4
|
file offset of data
|
0x4
|
4
|
memory offset loaded to
|
0x8
|
4
|
size of data copied to memory offset (i.e. size after decompression)
|
0xC
|
4
|
alignment used on memory size / size of .bss in the case of .data segment
|
.rodata-relative extent
Offset
|
Size
|
Description
|
0x0
|
4
|
offset (relative to .rodata)
|
0x4
|
4
|
size of region
|
Offset
|
Size
|
Description
|
0x0
|
4
|
Magic "NSO0"
|
0x4
|
4
|
|
0x8
|
4
|
|
0xC
|
4
|
|
0x10
|
0x10 * 3
|
SegmentHeader for each segment
|
0x40
|
0x14
|
Value of "build id" from ELF's GNU .note section
|
0x54
|
0xC
|
Padding
|
0x60
|
0x4 * 3
|
file size of each segment (i.e. LZ4-compressed size)
|
0x6c
|
0x24
|
Padding
|
0x90
|
8
|
.rodata-relative extents of .dynstr
|
0x98
|
8
|
.rodata-relative extents of .dynsym
|
0xA0
|
0x20 * 3
|
SHA256 hashes over the decompressed sections using the above byte-sizes: .text, .rodata, and .data.
|
0x100
|
|
Compressed sections
|