| ELF(5) | File Formats Manual | ELF(5) |
نام (NAME)
elf - قالب فایل قابل اجرا و پیوندپذیر (ELF)
خلاصه دستور (SYNOPSIS)
#include <elf.h>
توضیحات (DESCRIPTION)
فایل هدر <elf.h> قالب فایلهای باینری اجرایی ELF را تعریف میکند. از جمله این فایلها میتوان به فایلهای اجرایی معمولی، فایلهای شیء با قابلیت جابجایی (relocatable object files)، فایلهای core، و شیءهای اشتراکی (shared objects) اشاره کرد.
یک فایل اجرایی که از قالب فایل ELF استفاده میکند، شامل یک هدر ELF است که به دنبال آن یک جدول هدر برنامه (program header table) یا یک جدول هدر بخش (section header table)، یا هر دو قرار میگیرند. هدر ELF همیشه در افست صفر از فایل قرار دارد. افست جدول هدر برنامه و جدول هدر بخش در فایل، درون هدر ELF مشخص میشود. این دو جدول سایر ویژگیها و مشخصات فایل را توصیف میکنند.
این فایل هدر، هدرهای یادشده در بالا را به عنوان ساختارهای C توصیف میکند و همچنین شامل ساختارهایی برای بخشهای پویا (dynamic sections)، بخشهای بازمکانیابی (relocation sections) و جداول نماد (symbol tables) است.
انواع پایه (Basic types)
انواع زیر برای معماریهای N-بیتی استفاده میشوند (N=32,64؛ ElfN بیانگر Elf32 یا Elf64، و uintN_t بیانگر uint32_t یا uint64_t است):
ElfN_Addr Unsigned program address, uintN_t ElfN_Off Unsigned file offset, uintN_t ElfN_Section Unsigned section index, uint16_t ElfN_Versym Unsigned version symbol information, uint16_t Elf_Byte unsigned char ElfN_Half uint16_t ElfN_Sword int32_t ElfN_Word uint32_t ElfN_Sxword int64_t ElfN_Xword uint64_t
(توجه: اصطلاحات *BSD کمی متفاوت است. در آنجا، Elf64_Half دو برابر بزرگتر از Elf32_Half است و از Elf64Quarter برای uint16_t استفاده میشود. به منظور جلوگیری از سردرگمی، این انواع در ادامه با انواع صریح جایگزین شدهاند.)
تمام ساختارهای دادهای که قالب فایل تعریف میکند از دستورالعملهای اندازه و تراز «طبیعی» (natural) برای کلاس مربوطه پیروی میکنند. در صورت نیاز، ساختارهای داده شامل پدینگ (padding) صریح هستند تا تراز ۴ بایتی برای اشیاء ۴ بایتی، مضرب ۴ بودن اندازه ساختارها و موارد مشابه تضمین شود.
هدر ELF (Ehdr)
هدر ELF با نوع Elf32_Ehdr یا Elf64_Ehdr توصیف میشود:
#define EI_NIDENT 16
typedef struct {
unsigned char e_ident[EI_NIDENT];
uint16_t e_type;
uint16_t e_machine;
uint32_t e_version;
ElfN_Addr e_entry;
ElfN_Off e_phoff;
ElfN_Off e_shoff;
uint32_t e_flags;
uint16_t e_ehsize;
uint16_t e_phentsize;
uint16_t e_phnum;
uint16_t e_shentsize;
uint16_t e_shnum;
uint16_t e_shstrndx;
} ElfN_Ehdr;
فیلدها معانی زیر را دارند:
- e_ident
- این آرایه از بایتها نحوه تفسیر فایل را، مستقل از پردازنده یا سایر محتویات فایل، مشخص میکند. درون این آرایه همه چیز با ماکروهایی نامگذاری شدهاند که با پیشوند EI_ شروع میشوند و ممکن است مقادیری داشته باشند که با پیشوند ELF شروع میشوند. ماکروهای زیر تعریف شدهاند:
- EI_MAG0
- بایت نخست عدد جادویی (magic number). باید با مقدار ELFMAG0 پر شود. (0: 0x7f)
- EI_MAG1
- بایت دوم عدد جادویی. باید با مقدار ELFMAG1 پر شود. (1: 'E')
- EI_MAG2
- بایت سوم عدد جادویی. باید با مقدار ELFMAG2 پر شود. (2: 'L')
- EI_MAG3
- بایت چهارم عدد جادویی. باید با مقدار ELFMAG3 پر شود. (3: 'F')
- EI_CLASS
- بایت پنجم معماری مربوط به این فایل باینری را مشخص میکند:
- ELFCLASSNONE
- این کلاس نامعتبر است.
- ELFCLASS32
- معماری ۳۲-بیتی را مشخص میکند. از ماشینهایی با فایلها و فضاهای آدرس مجازی تا ۴ گیگابایت پشتیبانی میکند.
- ELFCLASS64
- معماری ۶۴-بیتی را مشخص میکند.
- EI_DATA
- بایت ششم کدگذاری دادههای وابسته به پردازنده را در فایل مشخص میکند. در حال حاضر این کدگذاریها پشتیبانی میشوند:
- ELFDATANONE
- قالب داده ناشناخته.
- ELFDATA2LSB
- مکمل دو، کمارزشترین بایت اول (little-endian).
- ELFDATA2MSB
- مکمل دو، باارزشترین بایت اول (big-endian).
- EI_VERSION
- بایت هفتم شماره نسخه مشخصات ELF است:
- EV_NONE
- نسخه نامعتبر.
- EV_CURRENT
- نسخه کنونی.
- EI_OSABI
- بایت هشتم سیستمعامل و رابط دودویی کاربردی (ABI) هدف شیء را مشخص میکند. برخی از فیلدها در سایر ساختارهای ELF دارای پرچمها و مقادیری هستند که معانی وابسته به پلتفرم دارند؛ تفسیر آن فیلدها با مقدار این بایت تعیین میشود. برای نمونه:
- ELFOSABI_NONE
- مشابه ELFOSABI_SYSV
- ELFOSABI_SYSV
- رابط دودویی کاربردی UNIX System V
- ELFOSABI_HPUX
- رابط دودویی کاربردی HP-UX
- ELFOSABI_NETBSD
- رابط دودویی کاربردی NetBSD
- ELFOSABI_LINUX
- رابط دودویی کاربردی Linux
- ELFOSABI_SOLARIS
- رابط دودویی کاربردی Solaris
- ELFOSABI_IRIX
- رابط دودویی کاربردی IRIX
- ELFOSABI_FREEBSD
- رابط دودویی کاربردی FreeBSD
- ELFOSABI_TRU64
- رابط دودویی کاربردی TRU64 UNIX
- ELFOSABI_ARM
- رابط دودویی کاربردی معماری ARM
- ELFOSABI_STANDALONE
- رابط دودویی کاربردی مستقل (سیستمهای توکار / embedded)
- EI_ABIVERSION
- بایت نهم نسخه ABI هدف شیء را مشخص میکند. این فیلد برای تمایز میان نسخههای ناسازگار یک ABI به کار میرود. تفسیر این شماره نسخه به ABI مشخصشده در فیلد EI_OSABI بستگی دارد. برنامههای سازگار با این مشخصات از مقدار 0 استفاده میکنند.
- EI_PAD
- شروع پدینگ (فاصلهگذاری). این بایتها رزرو شدهاند و با صفر مقداردهی میشوند. برنامههایی که آنها را میخوانند باید نادیدهشان بگیرند. در صورتی که در آینده به بایتهای بلااستفاده کنونی معنایی اختصاص داده شود، مقدار EI_PAD تغییر خواهد کرد.
- EI_NIDENT
- اندازه آرایه e_ident.
- e_type
- این عضو ساختار، نوع فایل شیء را مشخص میکند:
- e_machine
- این عضو معماری مورد نیاز برای یک فایل منفرد را مشخص میکند. برای نمونه:
- EM_NONE
- یک ماشین ناشناخته
- EM_M32
- AT&T WE 32100
- EM_SPARC
- Sun Microsystems SPARC
- EM_386
- Intel 80386
- EM_68K
- Motorola 68000
- EM_88K
- Motorola 88000
- EM_860
- Intel 80860
- EM_MIPS
- MIPS RS3000 (فقط big-endian)
- EM_PARISC
- HP/PA
- EM_SPARC32PLUS
- SPARC با مجموعه دستورالعمل ارتقایافته
- EM_PPC
- PowerPC
- EM_PPC64
- PowerPC ۶۴-بیتی
- EM_S390
- IBM S/390
- EM_ARM
- Advanced RISC Machines
- EM_SH
- Renesas SuperH
- EM_SPARCV9
- SPARC v9 ۶۴-بیتی
- EM_IA_64
- Intel Itanium
- EM_X86_64
- AMD x86-64
- EM_VAX
- DEC Vax
- e_version
- این عضو نسخه فایل را مشخص میکند:
- EV_NONE
- نسخه نامعتبر
- EV_CURRENT
- نسخه کنونی
- e_entry
- این عضو آدرس مجازیای را مشخص میکند که سیستم ابتدا کنترل را به آن منتقل میکند و بدین ترتیب فرآیند آغاز میشود. اگر فایل نقطه ورود مرتبطی نداشته باشد، این عضو مقدار صفر را نگه میدارد.
- e_phoff
- این عضو افست جدول هدر برنامه را در فایل بر حسب بایت نگه میدارد. اگر فایل جدول هدر برنامه نداشته باشد، این عضو مقدار صفر را نگه میدارد.
- e_shoff
- این عضو افست جدول هدر بخش را در فایل بر حسب بایت نگه میدارد. اگر فایل جدول هدر بخش نداشته باشد، این عضو مقدار صفر را نگه میدارد.
- e_flags
- این عضو پرچمهای وابسته به پردازنده را که با فایل مرتبط هستند نگه میدارد. نام پرچمها به صورت EF_`machine_flag' هستند. در حال حاضر هیچ پرچمی تعریف نشده است.
- e_ehsize
- این عضو اندازه هدر ELF را بر حسب بایت نگه میدارد.
- e_phentsize
- این عضو اندازه یک مدخل در جدول هدر برنامه فایل را بر حسب بایت نگه میدارد؛ همه مدخلها اندازه یکسانی دارند.
- e_phnum
- این عضو تعداد مدخلها در جدول هدر برنامه را نگه میدارد. بنابراین حاصلضرب e_phentsize در e_phnum اندازه جدول را بر حسب بایت به دست میدهد. اگر فایلی هدر برنامه نداشته باشد، e_phnum مقدار صفر را نگه میدارد.
- اگر تعداد مدخلها در جدول هدر برنامه بزرگتر یا مساوی PN_XNUM (0xffff) باشد، این عضو مقدار PN_XNUM (0xffff) را نگه میدارد و تعداد واقعی مدخلها در جدول هدر برنامه در عضو sh_info نخستین مدخل در جدول هدر بخش نگهداری میشود. در غیر این صورت، عضو sh_info نخستین مدخل حاوی مقدار صفر است.
- PN_XNUM
- این مقدار برابر 0xffff تعریف شده است که بیشترین مقداری است که e_phnum میتواند داشته باشد، و مشخص میکند که تعداد واقعی هدرهای برنامه در کجا تخصیص یافته است.
- e_shentsize
- این عضو اندازه یک هدر بخش را بر حسب بایت نگه میدارد. یک هدر بخش، یک مدخل در جدول هدر بخش است؛ همه مدخلها اندازه یکسانی دارند.
- e_shnum
- این عضو تعداد مدخلها در جدول هدر بخش را نگه میدارد. بنابراین حاصلضرب e_shentsize در e_shnum اندازه جدول هدر بخش را بر حسب بایت به دست میدهد. اگر فایلی جدول هدر بخش نداشته باشد، e_shnum مقدار صفر را نگه میدارد.
- اگر تعداد مدخلها در جدول هدر بخش بزرگتر یا مساوی SHN_LORESERVE (0xff00) باشد، e_shnum مقدار صفر را نگه میدارد و تعداد واقعی مدخلها در جدول هدر بخش در عضو sh_size نخستین مدخل در جدول هدر بخش نگهداری میشود. در غیر این صورت، عضو sh_size نخستین مدخل در جدول هدر بخش مقدار صفر را نگه میدارد.
- e_shstrndx
- این عضو شاخص (index) مدخل مرتبط با جدول رشته نامهای بخش را در جدول هدر بخش نگه میدارد. اگر فایل فاقد جدول رشته نام بخش باشد، این عضو مقدار SHN_UNDEF را نگه میدارد.
- اگر شاخص بخش جدول رشته نامهای بخش بزرگتر یا مساوی SHN_LORESERVE (0xff00) باشد، این عضو مقدار SHN_XINDEX (0xffff) را نگه میدارد و شاخص واقعی بخش جدول رشته نامهای بخش در عضو sh_link نخستین مدخل در جدول هدر بخش نگهداری میشود. در غیر این صورت، عضو sh_link نخستین مدخل در جدول هدر بخش حاوی مقدار صفر است.
هدر برنامه (Phdr)
جدول هدر برنامه یک فایل اجرایی یا شیء اشتراکی، آرایهای از ساختارها است که هر یک قطعهای (segment) یا اطلاعات دیگری را توصیف میکنند که سیستم برای آمادهسازی برنامه جهت اجرا به آنها نیاز دارد. یک قطعه فایل شیء شامل یک یا چند بخش (section) است. هدرهای برنامه فقط برای فایلهای اجرایی و فایلهای شیء اشتراکی معنادار هستند. یک فایل اندازه هدر برنامه خود را با اعضای e_phentsize و e_phnum در هدر ELF مشخص میکند. هدر برنامه ELF بسته به معماری با نوع Elf32_Phdr یا Elf64_Phdr توصیف میشود:
typedef struct {
uint32_t p_type;
Elf32_Off p_offset;
Elf32_Addr p_vaddr;
Elf32_Addr p_paddr;
uint32_t p_filesz;
uint32_t p_memsz;
uint32_t p_flags;
uint32_t p_align;
} Elf32_Phdr;
typedef struct {
uint32_t p_type;
uint32_t p_flags;
Elf64_Off p_offset;
Elf64_Addr p_vaddr;
Elf64_Addr p_paddr;
uint64_t p_filesz;
uint64_t p_memsz;
uint64_t p_align;
} Elf64_Phdr;
تفاوت اصلی بین هدر برنامه ۳۲-بیتی و ۶۴-بیتی در مکان قرارگیری عضو p_flags در کل ساختار است.
- p_type
- این عضو ساختار نوع قطعهای را که این عنصر آرایه توصیف میکند یا نحوه تفسیر اطلاعات عنصر آرایه را مشخص مینماید.
- PT_NULL
- عنصر آرایه استفاده نشده است و مقادیر سایر اعضا تعریفنشده هستند. این امکان به هدر برنامه اجازه میدهد تا مدخلهای نادیدهگرفتهشده داشته باشد.
- PT_LOAD
- عنصر آرایه یک قطعه قابل بارگذاری را مشخص میکند که با p_filesz و p_memsz توصیف میشود. بایتهای فایل به ابتدای قطعه حافظه نگاشت میشوند. اگر اندازه حافظه قطعه p_memsz بزرگتر از اندازه فایل p_filesz باشد، بایتهای «اضافی» طوری تعریف میشوند که مقدار 0 را نگه دارند و به دنبال ناحیه مقداردهی اولیه قطعه بیایند. اندازه فایل نمیتواند بزرگتر از اندازه حافظه باشد. مدخلهای قطعه قابل بارگذاری در جدول هدر برنامه به ترتیب صعودی، مرتبشده بر اساس عضو p_vaddr ظاهر میشوند.
- PT_DYNAMIC
- عنصر آرایه اطلاعات پیوند پویا (dynamic linking) را مشخص میکند.
- PT_INTERP
- عنصر آرایه مکان و اندازه یک مسیر منتهی به null را برای فراخوانی به عنوان مفسر مشخص میکند. این نوع قطعه فقط برای فایلهای اجرایی معنادار است (هرچند ممکن است برای شیءهای اشتراکی نیز رخ دهد). با این حال ممکن است بیش از یک بار در یک فایل ظاهر نشود. در صورت وجود، باید قبل از هر مدخل قطعه قابل بارگذاری قرار گیرد.
- PT_NOTE
- عنصر آرایه مکان یادداشتها (ElfN_Nhdr) را مشخص میکند.
- PT_SHLIB
- این نوع قطعه رزرو شده است اما معناشناسی نامشخصی دارد. برنامههایی که حاوی یک عنصر آرایه از این نوع باشند با ABI سازگار نیستند.
- PT_PHDR
- عنصر آرایه در صورت وجود، مکان و اندازه خود جدول هدر برنامه را چه در فایل و چه در تصویر حافظه برنامه مشخص میکند. این نوع قطعه ممکن است بیش از یک بار در یک فایل رخ ندهد. علاوه بر این، تنها در صورتی میتواند ظاهر شود که جدول هدر برنامه بخشی از تصویر حافظه برنامه باشد. در صورت وجود، باید قبل از هر مدخل قطعه قابل بارگذاری قرار گیرد.
- PT_LOPROC
- PT_HIPROC
- مقادیر موجود در بازه شامل [PT_LOPROC, PT_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- PT_GNU_STACK
- افزونه گنو (GNU) که توسط هسته لینوکس برای کنترل وضعیت پشته از طریق پرچمهای تنظیمشده در عضو p_flags استفاده میشود.
- p_offset
- این عضو افست از ابتدای فایل را که نخستین بایت قطعه در آن قرار دارد نگه میدارد.
- p_vaddr
- این عضو آدرس مجازیای را که نخستین بایت قطعه در حافظه قرار میگیرد نگه میدارد.
- p_paddr
- در سیستمهایی که آدرسدهی فیزیکی در آنها مطرح است، این عضو برای آدرس فیزیکی قطعه رزرو شده است. در BSD این عضو استفاده نمیشود و باید صفر باشد.
- p_filesz
- این عضو تعداد بایتهای تصویر فایلی قطعه را نگه میدارد. ممکن است صفر باشد.
- p_memsz
- این عضو تعداد بایتهای تصویر حافظهای قطعه را نگه میدارد. ممکن است صفر باشد.
- p_flags
- این عضو یک ماسک بیتی از پرچمهای مرتبط با قطعه را نگه میدارد:
- یک قطعه کد (text segment) معمولاً پرچمهای PF_X و PF_R را دارد. یک قطعه داده (data segment) معمولاً دارای PF_W و PF_R است.
- p_align
- این عضو مقداری را که قطعات بر اساس آن در حافظه و فایل تراز میشوند نگه میدارد. قطعات قابل بارگذاری فرآیند باید مقادیر هماهنگی برای p_vaddr و p_offset، به پیمانه اندازه صفحه (page size) داشته باشند. مقادیر صفر و یک به این معنی است که نیازی به تراز نیست. در غیر این صورت، p_align باید یک توان صحیح و مثبت از دو باشد و p_vaddr باید برابر با p_offset، به پیمانه p_align باشد.
هدر بخش (Shdr)
جدول هدر بخش یک فایل امکان یافتن تمام بخشهای فایل را فراهم میکند. جدول هدر بخش آرایهای از ساختارهای Elf32_Shdr یا Elf64_Shdr است. عضو e_shoff در هدر ELF، افست بایتی از ابتدای فایل تا جدول هدر بخش را مشخص میکند. e_shnum تعداد مدخلهای موجود در جدول هدر بخش را نگه میدارد. e_shentsize اندازه هر مدخل را بر حسب بایت نگه میدارد.
شاخص جدول هدر بخش، زیرنویسی برای این آرایه است. برخی از شاخصهای جدول هدر بخش رزرو شدهاند: مدخل اولیه و شاخصهای بین SHN_LORESERVE و SHN_HIRESERVE. مدخل اولیه در افزونههای ELF برای e_phnum، e_shnum، و e_shstrndx استفاده میشود؛ در سایر موارد، هر فیلد در مدخل اولیه روی صفر تنظیم میشود. یک فایل شیء برای این شاخصهای ویژه بخشی ندارد:
- SHN_UNDEF
- این مقدار نشاندهنده یک ارجاع بخشی تعریفنشده، مفقود، نامربوط، یا فاقد معنا است.
- SHN_LORESERVE
- این مقدار کران پایین بازه شاخصهای رزرو شده را مشخص میکند.
- SHN_LOPROC
- SHN_HIPROC
- مقادیر در بازه شامل [SHN_LOPROC, SHN_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- SHN_ABS
- این مقدار، مقدار مطلق را برای ارجاع متناظر مشخص میکند. به عنوان مثال، نمادی که نسبت به بخش شماره SHN_ABS تعریف شده است دارای مقداری مطلق است و تحت تأثیر بازمکانیابی قرار نمیگیرد.
- SHN_COMMON
- نمادهایی که نسبت به این بخش تعریف شدهاند، نمادهای مشترک هستند، مانند COMMON در فورترن یا متغیرهای خارجی تخصیصنیافته در C.
- SHN_HIRESERVE
- این مقدار کران بالای بازه شاخصهای رزرو شده را مشخص میکند. سیستم شاخصهای بین SHN_LORESERVE و SHN_HIRESERVE، شامل هر دو، را رزرو میکند. جدول هدر بخش شامل مدخلهایی برای شاخصهای رزرو شده نیست.
هدر بخش ساختار زیر را دارد:
typedef struct {
uint32_t sh_name;
uint32_t sh_type;
uint32_t sh_flags;
Elf32_Addr sh_addr;
Elf32_Off sh_offset;
uint32_t sh_size;
uint32_t sh_link;
uint32_t sh_info;
uint32_t sh_addralign;
uint32_t sh_entsize;
} Elf32_Shdr;
typedef struct {
uint32_t sh_name;
uint32_t sh_type;
uint64_t sh_flags;
Elf64_Addr sh_addr;
Elf64_Off sh_offset;
uint64_t sh_size;
uint32_t sh_link;
uint32_t sh_info;
uint64_t sh_addralign;
uint64_t sh_entsize;
} Elf64_Shdr;
هیچ تفاوت واقعی میان هدرهای بخش ۳۲-بیتی و ۶۴-بیتی وجود ندارد.
- sh_name
- این عضو نام بخش را مشخص میکند. مقدار آن یک شاخص در بخش جدول رشته هدر بخش است که مکان یک رشته منتهی به null را نشان میدهد.
- sh_type
- این عضو محتوا و معناشناسی بخش را دستهبندی میکند.
- SHT_NULL
- این مقدار هدر بخش را غیرفعال علامتگذاری میکند. این مدخل بخش مرتبطی ندارد. سایر اعضای هدر بخش مقادیر تعریفنشده دارند.
- SHT_PROGBITS
- این بخش حاوی اطلاعات تعریفشده توسط برنامه است که قالب و معنای آنها صرفاً توسط برنامه تعیین میشود.
- SHT_SYMTAB
- این بخش یک جدول نماد را نگه میدارد. به طور معمول، SHT_SYMTAB نمادها را برای ویرایش پیوند (link editing) فراهم میکند، هرچند ممکن است برای پیوند پویا نیز استفاده شود. به عنوان یک جدول نماد کامل، ممکن است حاوی نمادهای بسیاری باشد که برای پیوند پویا غیرضروری هستند. یک فایل شیء میتواند حاوی یک بخش SHT_DYNSYM نیز باشد.
- SHT_STRTAB
- این بخش یک جدول رشته را نگه میدارد. یک فایل شیء ممکن است چندین بخش جدول رشته داشته باشد.
- SHT_RELA
- این بخش مدخلهای بازمکانیابی با افزودههای صریح (explicit addends) را نگه میدارد، مانند نوع Elf32_Rela برای کلاس ۳۲-بیتی فایلهای شیء. یک شیء ممکن است چندین بخش بازمکانیابی داشته باشد.
- SHT_HASH
- این بخش یک جدول درهمسازی (هش) نماد را نگه میدارد. شیئی که در پیوند پویا شرکت میکند باید حاوی یک جدول هش نماد باشد. یک فایل شیء تنها میتواند یک جدول هش داشته باشد.
- SHT_DYNAMIC
- این بخش اطلاعات پیوند پویا را نگه میدارد. یک فایل شیء تنها میتواند یک بخش پویا داشته باشد.
- SHT_NOTE
- این بخش یادداشتها (ElfN_Nhdr) را نگه میدارد.
- SHT_NOBITS
- بخشی از این نوع هیچ فضایی را در فایل اشغال نمیکند اما در سایر موارد شبیه به SHT_PROGBITS است. اگرچه این بخش حاوی هیچ بایتی نیست، عضو sh_offset حاوی افست مفهومی در فایل است.
- SHT_REL
- این بخش افستهای بازمکانیابی بدون افزودههای صریح را نگه میدارد، مانند نوع Elf32_Rel برای کلاس ۳۲-بیتی فایلهای شیء. یک فایل شیء ممکن است چندین بخش بازمکانیابی داشته باشد.
- SHT_SHLIB
- این بخش رزرو شده است اما معناشناسی نامشخصی دارد.
- SHT_DYNSYM
- این بخش یک مجموعه حداقلی از نمادهای پیوند پویا را نگه میدارد. یک فایل شیء همچنین میتواند شامل یک بخش SHT_SYMTAB باشد.
- SHT_LOPROC
- SHT_HIPROC
- مقادیر در بازه شامل [SHT_LOPROC, SHT_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- SHT_LOUSER
- این مقدار کران پایین بازه شاخصهای رزرو شده برای برنامههای کاربردی را مشخص میکند.
- SHT_HIUSER
- این مقدار کران بالای بازه شاخصهای رزرو شده برای برنامههای کاربردی را مشخص میکند. انواع بخش بین SHT_LOUSER و SHT_HIUSER میتوانند توسط برنامه کاربردی استفاده شوند، بدون آنکه با انواع بخش تعریفشده توسط سیستم کنونی یا آتی تداخل داشته باشند.
- sh_flags
- بخشها از پرچمهای یک-بیتی پشتیبانی میکنند که ویژگیهای متفرقه را توصیف مینمایند. اگر یک بیت پرچم در sh_flags تنظیم شده باشد، آن ویژگی برای بخش «روشن» است. در غیر این صورت، ویژگی «خاموش» است یا اعمال نمیشود. ویژگیهای تعریفنشده روی صفر تنظیم میشوند.
- SHF_WRITE
- این بخش حاوی دادههایی است که در طول اجرای فرآیند باید قابل نوشتن باشند.
- SHF_ALLOC
- این بخش در طول اجرای فرآیند، حافظه اشغال میکند. برخی از بخشهای کنترلی در تصویر حافظه یک فایل شیء قرار نمیگیرند. این ویژگی برای آن بخشها خاموش است.
- SHF_EXECINSTR
- این بخش حاوی دستورالعملهای ماشین قابل اجرا است.
- SHF_MASKPROC
- تمام بیتهای موجود در این ماسک برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- sh_addr
- اگر این بخش در تصویر حافظه یک فرآیند ظاهر شود، این عضو آدرسی را که نخستین بایت بخش باید در آن قرار گیرد نگه میدارد. در غیر این صورت، این عضو حاوی صفر است.
- sh_offset
- مقدار این عضو، افست بایتی از ابتدای فایل تا نخستین بایت در بخش را نگه میدارد. یک نوع بخش، SHT_NOBITS، هیچ فضایی را در فایل اشغال نمیکند و عضو sh_offset آن، مکان مفهومی در فایل را مشخص میکند.
- sh_size
- این عضو اندازه بخش را بر حسب بایت نگه میدارد. مگر اینکه نوع بخش SHT_NOBITS باشد، بخش sh_size بایت را در فایل اشغال میکند. بخشی از نوع SHT_NOBITS ممکن است اندازهای غیرصفر داشته باشد، اما هیچ فضایی را در فایل اشغال نمیکند.
- sh_link
- این عضو پیوند شاخصی در جدول هدر بخش را نگه میدارد که تفسیر آن به نوع بخش بستگی دارد.
- sh_info
- این عضو اطلاعات اضافی را نگه میدارد که تفسیر آن به نوع بخش بستگی دارد.
- sh_addralign
- برخی از بخشها محدودیتهای تراز آدرس دارند. اگر یک بخش یک doubleword را نگه دارد، سیستم باید تراز doubleword را برای کل بخش تضمین کند. یعنی مقدار sh_addr باید همنهشت با صفر به پیمانه مقدار sh_addralign باشد. تنها صفر و توانهای صحیح و مثبت دو مجاز هستند. مقدار 0 یا 1 به این معنی است که بخش هیچ محدودیت ترازی ندارد.
- sh_entsize
- برخی از بخشها جدولی از مدخلهای با اندازه ثابت، مانند جدول نمادها، را نگه میدارند. برای چنین بخشی، این عضو اندازه هر مدخل را بر حسب بایت نشان میدهد. اگر بخش جدولی از مدخلهای با اندازه ثابت را نگه ندارد، این عضو حاوی صفر است.
بخشهای گوناگون اطلاعات برنامه و کنترل را در خود نگه میدارند:
- .bss
- این بخش دادههای مقداردهینشدهای را نگه میدارد که در تصویر حافظه برنامه سهیم هستند. طبق تعریف، هنگام شروع اجرای برنامه، سیستم دادهها را با صفر مقداردهی اولیه میکند. این بخش از نوع SHT_NOBITS است. انواع ویژگیهای آن SHF_ALLOC و SHF_WRITE هستند.
- .comment
- این بخش اطلاعات کنترل نسخه را نگه میدارد. این بخش از نوع SHT_PROGBITS است. هیچ نوع ویژگیای استفاده نشده است.
- .ctors
- این بخش اشارهگرهای مقداردهیشده به توابع سازنده (constructor) در ++C را نگه میدارد. این بخش از نوع SHT_PROGBITS است. انواع ویژگیهای آن SHF_ALLOC و SHF_WRITE هستند.
- .data
- این بخش دادههای مقداردهیشدهای را نگه میدارد که در تصویر حافظه برنامه سهیم هستند. این بخش از نوع SHT_PROGBITS است. انواع ویژگیهای آن SHF_ALLOC و SHF_WRITE هستند.
- .data1
- این بخش دادههای مقداردهیشدهای را نگه میدارد که در تصویر حافظه برنامه سهیم هستند. این بخش از نوع SHT_PROGBITS است. انواع ویژگیهای آن SHF_ALLOC و SHF_WRITE هستند.
- .debug
- این بخش اطلاعاتی را برای اشکالزدایی نمادین (symbolic debugging) نگه میدارد. محتویات آن نامشخص است. این بخش از نوع SHT_PROGBITS است. هیچ نوع ویژگیای استفاده نشده است.
- .dtors
- این بخش اشارهگرهای مقداردهیشده به توابع مخرب (destructor) در ++C را نگه میدارد. این بخش از نوع SHT_PROGBITS است. انواع ویژگیهای آن SHF_ALLOC و SHF_WRITE هستند.
- .dynamic
- این بخش اطلاعات پیوند پویا را نگه میدارد. ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. تنظیم بودن یا نبودن بیت SHF_WRITE وابسته به پردازنده است. این بخش از نوع SHT_DYNAMIC است. ویژگیهای بالا را ببینید.
- .dynstr
- این بخش رشتههای مورد نیاز برای پیوند پویا را نگه میدارد؛ معمولاً رشتههایی که نمایانگر نامهای مرتبط با مدخلهای جدول نماد هستند. این بخش از نوع SHT_STRTAB است. نوع ویژگی استفادهشده SHF_ALLOC است.
- .dynsym
- این بخش جدول نمادهای پیوند پویا را نگه میدارد. این بخش از نوع SHT_DYNSYM است. ویژگی استفادهشده SHF_ALLOC است.
- .fini
- این بخش دستورالعملهای اجرایی را نگه میدارد که در کد خاتمه فرآیند سهیم هستند. هنگامی که یک برنامه به طور عادی خاتمه مییابد، سیستم کد موجود در این بخش را اجرا میکند. این بخش از نوع SHT_PROGBITS است. ویژگیهای استفادهشده SHF_ALLOC و SHF_EXECINSTR هستند.
- .gnu.version
- این بخش جدول نماد نسخه را نگه میدارد که آرایهای از عناصر ElfN_Half است. این بخش از نوع SHT_GNU_versym است. نوع ویژگی استفادهشده SHF_ALLOC است.
- .gnu.version_d
- این بخش تعاریف نماد نسخه را نگه میدارد که جدولی از ساختارهای ElfN_Verdef است. این بخش از نوع SHT_GNU_verdef است. نوع ویژگی استفادهشده SHF_ALLOC است.
- .gnu.version_r
- این بخش عناصر مورد نیاز نماد نسخه را نگه میدارد که جدولی از ساختارهای ElfN_Verneed است. این بخش از نوع SHT_GNU_versym است. نوع ویژگی استفادهشده SHF_ALLOC است.
- .got
- این بخش جدول افست سراسری (global offset table) را نگه میدارد. این بخش از نوع SHT_PROGBITS است. ویژگیها وابسته به پردازنده هستند.
- .hash
- این بخش یک جدول هش نماد را نگه میدارد. این بخش از نوع SHT_HASH است. ویژگی استفادهشده SHF_ALLOC است.
- .init
- این بخش دستورالعملهای اجرایی را نگه میدارد که در کد مقداردهی اولیه فرآیند سهیم هستند. هنگامی که یک برنامه شروع به اجرا میکند، سیستم پیش از فراخوانی نقطه ورود اصلی برنامه، کد این بخش را اجرا مینماید. این بخش از نوع SHT_PROGBITS است. ویژگیهای استفادهشده SHF_ALLOC و SHF_EXECINSTR هستند.
- .interp
- این بخش نام مسیر یک مفسر برنامه را در خود نگه میدارد. اگر فایل دارای یک قطعه قابل بارگذاری باشد که این بخش را شامل شود، ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. در غیر این صورت، آن بیت خاموش خواهد بود. این بخش از نوع SHT_PROGBITS است.
- .line
- این بخش اطلاعات شماره خط را برای اشکالزدایی نمادین نگه میدارد که ارتباط بین منبع برنامه و کد ماشین را توصیف میکند. محتویات نامشخص است. این بخش از نوع SHT_PROGBITS است. هیچ نوع ویژگیای استفاده نشده است.
- .note
- این بخش یادداشتهای مختلف را نگه میدارد. این بخش از نوع SHT_NOTE است. هیچ نوع ویژگیای استفاده نشده است.
- .note.ABI-tag
- این بخش برای اعلام ABI مورد انتظار در زمان اجرای تصویر ELF به کار میرود. ممکن است شامل نام سیستمعامل و نسخههای زمان اجرای آن باشد. این بخش از نوع SHT_NOTE است. تنها ویژگی استفادهشده SHF_ALLOC است.
- .note.gnu.build-id
- این بخش برای نگهداری شناسهای به کار میرود که محتویات تصویر ELF را به طور یکتا مشخص میکند. فایلهای متفاوتی که شناسه ساخت (build ID) یکسانی دارند باید محتوای اجرایی یکسانی داشته باشند. برای جزئیات بیشتر به گزینه --build-id در پیونددهنده گنو (ld (1)) مراجعه کنید. این بخش از نوع SHT_NOTE است. تنها ویژگی استفادهشده SHF_ALLOC است.
- .note.GNU-stack
- این بخش در فایلهای شیء لینوکس برای اعلام ویژگیهای پشته استفاده میشود. این بخش از نوع SHT_PROGBITS است. تنها ویژگی استفادهشده SHF_EXECINSTR است. این ویژگی به پیونددهنده گنو نشان میدهد که فایل شیء نیازمند یک پشته قابل اجرا است.
- .note.openbsd.ident
- فایلهای اجرایی بومی OpenBSD معمولاً حاوی این بخش هستند تا هویت خود را مشخص کنند تا هسته بتواند هنگام بارگذاری فایل، آزمونهای شبیهسازی باینری سازگاری ELF را دور بزند.
- .plt
- این بخش جدول پیوند رویه (procedure linkage table) را نگه میدارد. این بخش از نوع SHT_PROGBITS است. ویژگیها وابسته به پردازنده هستند.
- .relNAME
- این بخش اطلاعات بازمکانیابی را مطابق آنچه در زیر توضیح داده شده است نگه میدارد. اگر فایل دارای یک قطعه قابل بارگذاری باشد که بازمکانیابی را شامل شود، ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. در غیر این صورت، این بیت خاموش خواهد بود. طبق قرارداد، «NAME» توسط بخشی که بازمکانیابیها برای آن اعمال میشوند ارائه میگردد. بنابراین یک بخش بازمکانیابی برای .text معمولاً نام .rel.text را خواهد داشت. این بخش از نوع SHT_REL است.
- .relaNAME
- این بخش اطلاعات بازمکانیابی را مطابق آنچه در زیر توضیح داده شده است نگه میدارد. اگر فایل دارای یک قطعه قابل بارگذاری باشد که بازمکانیابی را شامل شود، ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. در غیر این صورت، این بیت خاموش خواهد بود. طبق قرارداد، «NAME» توسط بخشی که بازمکانیابیها برای آن اعمال میشوند ارائه میگردد. بنابراین یک بخش بازمکانیابی برای .text معمولاً نام .rela.text را خواهد داشت. این بخش از نوع SHT_RELA است.
- .rodata
- این بخش دادههای فقط-خواندنی را نگه میدارد که معمولاً در یک قطعه غیرقابلنوشتن در تصویر فرآیند سهیم هستند. این بخش از نوع SHT_PROGBITS است. ویژگی استفادهشده SHF_ALLOC است.
- .rodata1
- این بخش دادههای فقط-خواندنی را نگه میدارد که معمولاً در یک قطعه غیرقابلنوشتن در تصویر فرآیند سهیم هستند. این بخش از نوع SHT_PROGBITS است. ویژگی استفادهشده SHF_ALLOC است.
- .shstrtab
- این بخش نامهای بخشها را نگه میدارد. این بخش از نوع SHT_STRTAB است. هیچ نوع ویژگیای استفاده نشده است.
- .strtab
- این بخش رشتهها را نگه میدارد، معمولاً رشتههایی که نمایانگر نامهای مرتبط با مدخلهای جدول نماد هستند. اگر فایل دارای یک قطعه قابل بارگذاری باشد که شامل جدول رشته نماد باشد، ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. در غیر این صورت، بیت خاموش خواهد بود. این بخش از نوع SHT_STRTAB است.
- .symtab
- این بخش یک جدول نماد را نگه میدارد. اگر فایل دارای یک قطعه قابل بارگذاری باشد که شامل جدول نماد باشد، ویژگیهای بخش شامل بیت SHF_ALLOC خواهد بود. در غیر این صورت، بیت خاموش خواهد بود. این بخش از نوع SHT_SYMTAB است.
- .text
- این بخش «متن» یا دستورالعملهای اجرایی یک برنامه را نگه میدارد. این بخش از نوع SHT_PROGBITS است. ویژگیهای استفادهشده SHF_ALLOC و SHF_EXECINSTR هستند.
جداول رشته و نماد (String and symbol tables)
بخشهای جدول رشته توالیهایی از نویسههای منتهی به null را نگه میدارند که معمولاً رشته نامیده میشوند. فایل شیء از این رشتهها برای نمایش نامهای نماد و بخش استفاده میکند. برای ارجاع به یک رشته، از شاخص آن در بخش جدول رشته استفاده میشود. بایت نخست، که شاخص صفر است، به گونهای تعریف شده است که یک بایت null ('\0') را نگه دارد. به طور مشابه، آخرین بایت یک جدول رشته برای نگهداری بایت null تعریف شده است تا خاتمه با null برای همه رشتهها تضمین شود.
جدول نماد یک فایل شیء اطلاعات مورد نیاز برای مکانیابی و بازمکانیابی تعاریف و ارجاعات نمادین یک برنامه را نگه میدارد. شاخص جدول نماد، زیرنویسی برای این آرایه است.
typedef struct {
uint32_t st_name;
Elf32_Addr st_value;
uint32_t st_size;
unsigned char st_info;
unsigned char st_other;
uint16_t st_shndx;
} Elf32_Sym;
typedef struct {
uint32_t st_name;
unsigned char st_info;
unsigned char st_other;
uint16_t st_shndx;
Elf64_Addr st_value;
uint64_t st_size;
} Elf64_Sym;
نسخههای ۳۲-بیتی و ۶۴-بیتی دارای اعضای یکسانی هستند، فقط ترتیب آنها متفاوت است.
- st_name
- این عضو یک شاخص در جدول رشته نماد فایل شیء را نگه میدارد که نمایش نویسهای نامهای نماد را در خود دارد. اگر مقدار آن غیرصفر باشد، نشاندهنده شاخص جدول رشته است که نام نماد را به دست میدهد. در غیر این صورت، نماد نامی ندارد.
- st_value
- این عضو مقدار نماد مرتبط را نشان میدهد.
- st_size
- بسیاری از نمادها اندازههای مرتبطی دارند. اگر نماد اندازهای نداشته باشد یا اندازه آن نامشخص باشد، این عضو مقدار صفر را نگه میدارد.
- st_info
- این عضو نوع نماد و ویژگیهای پیوند (binding) آن را مشخص میکند:
- STT_NOTYPE
- نوع نماد تعریف نشده است.
- STT_OBJECT
- نماد با یک شیء دادهای مرتبط است.
- STT_FUNC
- نماد با یک تابع یا کد اجرایی دیگر مرتبط است.
- STT_SECTION
- نماد با یک بخش مرتبط است. مدخلهای جدول نماد از این نوع عمدتاً برای بازمکانیابی وجود دارند و معمولاً دارای پیوندهای STB_LOCAL هستند.
- STT_FILE
- طبق قرارداد، نام نماد نام فایل منبع مرتبط با فایل شیء را نشان میدهد. یک نماد فایل دارای پیوندهای STB_LOCAL است، شاخص بخش آن SHN_ABS است، و در صورت وجود، پیش از سایر نمادهای STB_LOCAL فایل قرار میگیرد.
- STT_LOPROC
- STT_HIPROC
- مقادیر در بازه شامل [STT_LOPROC, STT_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- STB_LOCAL
- نمادهای محلی در خارج از فایل شیء حاوی تعریف آنها قابل مشاهده نیستند. نمادهای محلی همنام میتوانند در چندین فایل بدون تداخل با یکدیگر وجود داشته باشند.
- STB_GLOBAL
- نمادهای سراسری برای تمام فایلهای شیئی که در حال ترکیب هستند قابل مشاهدهاند. تعریف یک نماد سراسری در یک فایل، ارجاع تعریفنشده به همان نماد در فایلی دیگر را برآورده میکند.
- STB_WEAK
- نمادهای ضعیف (weak) شبیه به نمادهای سراسری هستند، اما تعاریف آنها اولویت پایینتری دارند.
- STB_LOPROC
- STB_HIPROC
- مقادیر در بازه شامل [STB_LOPROC, STB_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند.
- ماکروهایی برای بستهبندی و باز کردن فیلدهای پیوند و نوع وجود دارند:
- ELF32_ST_BIND(info)
- ELF64_ST_BIND(info)
- استخراج یک پیوند (binding) از یک مقدار st_info .
- ELF32_ST_TYPE(info)
- ELF64_ST_TYPE(info)
- استخراج یک نوع (type) از یک مقدار st_info .
- ELF32_ST_INFO(bind, type)
- ELF64_ST_INFO(bind, type)
- تبدیل یک پیوند و یک نوع به مقدار st_info .
- st_other
- این عضو قابلیت مشاهده (visibility) نماد را مشخص میکند.
- STV_DEFAULT
- قوانین پیشفرض قابلیت مشاهده نماد. نمادهای سراسری و ضعیف برای سایر ماژولها در دسترس هستند؛ ارجاعات در ماژول محلی میتوانند توسط تعاریف در سایر ماژولها جایگزین (interposed) شوند.
- STV_INTERNAL
- کلاس مخفی وابسته به پردازنده.
- STV_HIDDEN
- نماد برای سایر ماژولها در دسترس نیست؛ ارجاعات در ماژول محلی همیشه به نماد محلی حل میشوند (یعنی نماد نمیتواند توسط تعاریف در سایر ماژولها جایگزین شود).
- STV_PROTECTED
- نماد برای سایر ماژولها در دسترس است، اما ارجاعات در ماژول محلی همیشه به نماد محلی حل میشوند.
ماکروهایی برای استخراج نوع قابلیت مشاهده وجود دارند:
ELF32_ST_VISIBILITY(other) یا ELF64_ST_VISIBILITY(other)
- st_shndx
- هر مدخل جدول نماد نسبت به بخشی «تعریف» میشود. این عضو شاخص جدول هدر بخش مربوطه را نگه میدارد.
مدخلهای بازمکانیابی (Rel & Rela)
بازمکانیابی (Relocation) فرآیند اتصال ارجاعات نمادین به تعاریف نمادین است. فایلهای با قابلیت جابجایی باید اطلاعاتی داشته باشند که نحوه اصلاح محتویات بخشهای آنها را توصیف کند، تا بدین ترتیب فایلهای اجرایی و شیءهای اشتراکی بتوانند اطلاعات مناسب را برای تصویر برنامه یک فرآیند نگه دارند. مدخلهای بازمکانیابی همان دادهها هستند.
ساختارهای بازمکانیابی که نیازی به افزوده (addend) ندارند:
typedef struct {
Elf32_Addr r_offset;
uint32_t r_info;
} Elf32_Rel;
typedef struct {
Elf64_Addr r_offset;
uint64_t r_info;
} Elf64_Rel;
ساختارهای بازمکانیابی که نیازمند افزوده هستند:
typedef struct {
Elf32_Addr r_offset;
uint32_t r_info;
int32_t r_addend;
} Elf32_Rela;
typedef struct {
Elf64_Addr r_offset;
uint64_t r_info;
int64_t r_addend;
} Elf64_Rela;
- r_offset
- این عضو مکانی را که عمل بازمکانیابی باید روی آن اعمال شود مشخص میکند. برای یک فایل با قابلیت جابجایی، این مقدار افست بایتی از ابتدای بخش تا واحد ذخیرهسازی تحت تأثیر بازمکانیابی است. برای یک فایل اجرایی یا شیء اشتراکی، این مقدار آدرس مجازی واحد ذخیرهسازی تحت تأثیر بازمکانیابی است.
- r_info
- این عضو هم شاخص جدول نماد که بازمکانیابی باید نسبت به آن انجام شود و هم نوع بازمکانیابی اعمالشونده را نشان میدهد. انواع بازمکانیابی وابسته به پردازنده هستند. هنگامی که متن به نوع بازمکانیابی یا شاخص جدول نماد یک مدخل بازمکانیابی اشاره میکند، منظور نتیجه اعمال ELF[32|64]_R_TYPE یا ELF[32|64]_R_SYM، به ترتیب، بر روی عضو r_info مدخل است.
- r_addend
- این عضو یک افزوده ثابت را مشخص میکند که برای محاسبه مقدار ذخیرهشونده در فیلد قابل جابجایی استفاده میشود.
تگهای پویا (Dyn)
بخش .dynamic شامل مجموعهای از ساختارها است که اطلاعات مرتبط با پیوند پویا را نگه میدارند. عضو d_tag نحوه تفسیر d_un را کنترل میکند.
typedef struct {
Elf32_Sword d_tag;
union {
Elf32_Word d_val;
Elf32_Addr d_ptr;
} d_un;
} Elf32_Dyn;
extern Elf32_Dyn _DYNAMIC[];
typedef struct {
Elf64_Sxword d_tag;
union {
Elf64_Xword d_val;
Elf64_Addr d_ptr;
} d_un;
} Elf64_Dyn;
extern Elf64_Dyn _DYNAMIC[];
- d_tag
- این عضو میتواند هر یک از مقادیر زیر را داشته باشد:
- DT_NULL
- پایان بخش پویا را مشخص میکند
- DT_NEEDED
- افست در جدول رشته به نام کتابخانه مورد نیاز
- DT_PLTRELSZ
- اندازه مدخلهای بازمکانیابی PLT بر حسب بایت
- DT_PLTGOT
- آدرس PLT و/یا GOT
- DT_HASH
- آدرس جدول هش نماد
- DT_STRTAB
- آدرس جدول رشته
- DT_SYMTAB
- آدرس جدول نماد
- DT_RELA
- آدرس جدول بازمکانیابی Rela
- DT_RELASZ
- اندازه جدول بازمکانیابی Rela بر حسب بایت
- DT_RELAENT
- اندازه یک مدخل از جدول بازمکانیابی Rela بر حسب بایت
- DT_STRSZ
- اندازه جدول رشته بر حسب بایت
- DT_SYMENT
- اندازه یک مدخل جدول نماد بر حسب بایت
- DT_INIT
- آدرس تابع مقداردهی اولیه (initialization function)
- DT_FINI
- آدرس تابع خاتمه (termination function)
- DT_SONAME
- افست در جدول رشته به نام شیء اشتراکی
- DT_RPATH
- افست در جدول رشته به مسیر جستجو برای وابستگیهای مستقیم و غیرمستقیم کتابخانه
- DT_SYMBOLIC
- هشدار به پیونددهنده برای جستجوی نمادها در این شیء اشتراکی پیش از فایل اجرایی
- DT_REL
- آدرس جدول بازمکانیابی Rel
- DT_RELSZ
- اندازه جدول بازمکانیابی Rel بر حسب بایت
- DT_RELENT
- اندازه یک مدخل از جدول Rel بر حسب بایت
- DT_PLTREL
- نوع مدخل بازمکانیابی که PLT به آن ارجاع میدهد (Rela یا Rel)
- DT_DEBUG
- کاربرد تعریفنشده برای اشکالزدایی
- DT_TEXTREL
- نبود این مدخل نشان میدهد که هیچ مدخل بازمکانیابیای نباید روی یک قطعه غیرقابلنوشتن اعمال شود
- DT_JMPREL
- آدرس مدخلهای بازمکانیابی مرتبط صرفاً با PLT
- DT_BIND_NOW
- دستور به پیونددهنده پویا برای پردازش تمام بازمکانیابیها پیش از انتقال کنترل به فایل اجرایی
- DT_RUNPATH
- افست در جدول رشته به مسیر جستجو برای وابستگیهای مستقیم کتابخانه
- DT_LOPROC
- DT_HIPROC
- مقادیر در بازه شامل [DT_LOPROC, DT_HIPROC] برای معناشناسیهای وابسته به پردازنده رزرو شدهاند
- d_val
- این عضو مقادیر صحیح با تفاسیر گوناگون را نشان میدهد.
- d_ptr
- این عضو آدرسهای مجازی برنامه را نشان میدهد. هنگام تفسیر این آدرسها، آدرس واقعی باید بر اساس مقدار اصلی فایل و آدرس پایه حافظه محاسبه شود. فایلها شامل مدخلهای بازمکانیابی برای اصلاح این آدرسها نیستند.
- _DYNAMIC
- آرایهای حاوی تمام ساختارهای پویا در بخش .dynamic. این آرایه به طور خودکار توسط پیونددهنده پر میشود.
یادداشتها (Nhdr)
یادداشتهای ELF امکان پیوست کردن اطلاعات اختیاری را برای استفاده سیستم فراهم میکنند. آنها بیشتر توسط فایلهای core (e_type از ET_CORE) استفاده میشوند، اما پروژههای زیادی مجموعه افزونههای خود را تعریف میکنند. برای نمونه، زنجیره ابزار گنو (GNU) از یادداشتهای ELF برای انتقال اطلاعات از پیونددهنده به کتابخانه C استفاده میکند.
بخشهای یادداشت شامل مجموعهای از یادداشتها هستند (تعاریف struct زیر را ببینید). هر یادداشت با فیلد name (که طول آن در n_namesz مشخص شده) و سپس فیلد descriptor (که طول آن در n_descsz مشخص شده) و آدرس شروع آن دارای تراز ۴ بایتی است، دنبال میشود. هیچکدام از این دو فیلد به دلیل طول اختیاری در ساختار یادداشت تعریف نشدهاند.
یک مثال برای تجزیه دو یادداشت متوالی باید چیدمان آنها را در حافظه مشخص کند:
void *memory, *name, *desc;
Elf64_Nhdr *note, *next_note;
/* The buffer is pointing to the start of the section/segment. */
note = memory;
/* If the name is defined, it follows the note. */
name = note->n_namesz == 0 ? NULL : memory + sizeof(*note);
/* If the descriptor is defined, it follows the name
(with alignment). */
desc = note->n_descsz == 0 ? NULL :
memory + sizeof(*note) + ALIGN_UP(note->n_namesz, 4);
/* The next note follows both (with alignment). */
next_note = memory + sizeof(*note) +
ALIGN_UP(note->n_namesz, 4) +
ALIGN_UP(note->n_descsz, 4);
توجه داشته باشید که تفسیر n_type به فضای نام (namespace) تعریفشده توسط فیلد n_namesz بستگی دارد. اگر فیلد n_namesz تنظیم نشده باشد (مثلاً 0 باشد)، دو مجموعه یادداشت وجود دارد: یکی برای فایلهای core و دیگری برای سایر انواع ELF. اگر فضای نام ناشناخته باشد، ابزارها معمولاً به این مجموعههای یادداشت بازمیگردند.
typedef struct {
Elf32_Word n_namesz;
Elf32_Word n_descsz;
Elf32_Word n_type;
} Elf32_Nhdr;
typedef struct {
Elf64_Word n_namesz;
Elf64_Word n_descsz;
Elf64_Word n_type;
} Elf64_Nhdr;
- n_namesz
- طول فیلد name بر حسب بایت. محتویات بلافاصله پس از این یادداشت در حافظه قرار میگیرد. نام با null خاتمه مییابد. برای نمونه، اگر نام "GNU" باشد، n_namesz برابر با 4 تنظیم میشود.
- n_descsz
- طول فیلد توصیفکننده (descriptor) بر حسب بایت. محتویات بلافاصله پس از فیلد name در حافظه قرار میگیرد.
- n_type
- بسته به مقدار فیلد name، این عضو میتواند هر یک از مقادیر زیر را داشته باشد:
- فایلهای Core (با e_type = ET_CORE)
- یادداشتهای استفادهشده توسط تمام فایلهای core. اینها شدیداً وابسته به سیستمعامل یا معماری هستند و اغلب به هماهنگی نزدیک با هستهها، کتابخانههای C، و اشکالزداها نیاز دارند. این موارد زمانی استفاده میشوند که فضای نام پیشفرض باشد (یعنی n_namesz روی 0 تنظیم شود)، یا به عنوان حالت جایگزین هنگامی که فضای نام ناشناخته است.
- NT_PRSTATUS
- ساختار prstatus
- NT_FPREGSET
- ساختار fpregset
- NT_PRPSINFO
- ساختار prpsinfo
- NT_PRXREG
- ساختار prxregset
- NT_TASKSTRUCT
- ساختار task
- NT_PLATFORM
- رشته از sysinfo(SI_PLATFORM)
- NT_AUXV
- آرایه auxv
- NT_GWINDOWS
- ساختار gwindows
- NT_ASRS
- ساختار asrset
- NT_PSTATUS
- ساختار pstatus
- NT_PSINFO
- ساختار psinfo
- NT_PRCRED
- ساختار prcred
- NT_UTSNAME
- ساختار utsname
- NT_LWPSTATUS
- ساختار lwpstatus
- NT_LWPSINFO
- ساختار lwpinfo
- NT_PRFPXREG
- ساختار fprxregset
- NT_SIGINFO
- siginfo_t (ممکن است اندازه در طول زمان افزایش یابد)
- NT_FILE
- شامل اطلاعات درباره فایلهای نگاشتشده
- NT_PRXFPREG
- user_fxsr_struct
- NT_PPC_VMX
- ثباتهای PowerPC Altivec/VMX
- NT_PPC_SPE
- ثباتهای PowerPC SPE/EVR
- NT_PPC_VSX
- ثباتهای PowerPC VSX
- NT_386_TLS
- اسلاتهای i386 TLS (ساختار user_desc)
- NT_386_IOPERM
- بیتمپ دسترسی ورودی/خروجی x86 (1=رد کردن)
- NT_X86_XSTATE
- وضعیت گسترشیافته x86 با استفاده از xsave
- NT_S390_HIGH_GPRS
- نیمه بالایی ثباتهای s390
- NT_S390_TIMER
- ثبات تایمر s390
- NT_S390_TODCMP
- ثبات مقایسهگر ساعت زمان واقعی (TOD) در s390
- NT_S390_TODPREG
- ثبات قابلبرنامهریزی زمان واقعی (TOD) در s390
- NT_S390_CTRS
- ثباتهای کنترلی s390
- NT_S390_PREFIX
- ثبات پیشوند s390
- NT_S390_LAST_BREAK
- آدرس رویداد شکستن (breaking event) در s390
- NT_S390_SYSTEM_CALL
- دادههای راهاندازی مجدد فراخوانی سیستمی s390
- NT_S390_TDB
- بلوک تشخیصی تراکنش s390
- NT_ARM_VFP
- ثباتهای ARM VFP/NEON
- NT_ARM_TLS
- ثبات ARM TLS
- NT_ARM_HW_BREAK
- ثباتهای نقطه توقف سختافزاری ARM
- NT_ARM_HW_WATCH
- ثباتهای نقطه نظارت سختافزاری ARM
- NT_ARM_SYSTEM_CALL
- شماره فراخوانی سیستمی ARM
- n_name = GNU
- افزونههای استفادهشده توسط زنجیره ابزار گنو (GNU).
- NT_GNU_ABI_TAG
- اطلاعات رابط دودویی کاربردی (ABI) سیستمعامل (OS). فیلد desc برابر با ۴ کلمه خواهد بود:
- [0]
- توصیفکننده سیستمعامل (ELF_NOTE_OS_LINUX، ELF_NOTE_OS_GNU، و غیره)
- [1]
- نسخه اصلی (major) رابط ABI
- [2]
- نسخه فرعی (minor) رابط ABI
- [3]
- نسخه زیرفرعی (subminor) رابط ABI
- NT_GNU_HWCAP
- اطلاعات ترکیبی hwcap. فیلد desc با دو کلمه آغاز میشود:
- [0]
- تعداد مدخلها
- [1]
- ماسک بیتی مدخلهای فعالشده
- سپس مدخلهای با طول متغیر میآیند؛ یک بایت به همراه یک رشته نام hwcap منتهی به null. این بایت شماره بیتی را نشان میدهد که باید بررسی شود فعال است یا نه: (1U << bit) & bit mask.
- NT_GNU_BUILD_ID
- شناسه یکتای ساخت تولیدشده توسط گزینه --build-id در ld(1) گنو. بخش desc از هر تعداد بایت غیرصفر تشکیل میشود.
- NT_GNU_GOLD_VERSION
- بخش desc حاوی نسخه پیونددهنده GNU Gold استفادهشده است.
- فضای نام پیشفرض/ناشناخته (e_type != ET_CORE)
- این موارد زمانی استفاده میشوند که فضای نام پیشفرض باشد (یعنی n_namesz روی 0 تنظیم شود)، یا به عنوان حالت جایگزین هنگامی که فضای نام ناشناخته است.
- NT_VERSION
- یک رشته نسخه از هر نوع.
- NT_ARCH
- اطلاعات معماری.
نکات (NOTES)
قالب ELF نخستین بار در System V ظاهر شد. قالب ELF یک استاندارد پذیرفتهشده است.
افزونههای مربوط به e_phnum، e_shnum، و e_shstrndx به ترتیب افزونههای لینوکس هستند. سیستمهای Sun، BSD، و AMD64 نیز از آنها پشتیبانی میکنند؛ برای اطلاعات بیشتر به بخش «همچنین ببینید» مراجعه کنید.
همچنین ببینید (SEE ALSO)
as(1), elfedit(1), gdb(1), ld(1), nm(1), objcopy(1), objdump(1), patchelf(1), readelf(1), size(1), strings(1), strip(1), execve(2), dl_iterate_phdr(3), core(5), ld.so(8)
Hewlett-Packard, Elf-64 Object File Format.
Santa Cruz Operation, System V Application Binary Interface.
UNIX System Laboratories, "Object Files", Executable and Linking Format (ELF).
Sun Microsystems, Linker and Libraries Guide.
AMD64 ABI Draft, System V Application Binary Interface AMD64 Architecture Processor Supplement.
| 2024-06-15 | Linux man-pages 6.9.1 |