13
13
14
14
int elf_symbol_index ;
15
15
16
- void elf_write_str (strbuf_t * elf_array , char * vals )
16
+ void elf_write_str (strbuf_t * elf_array , const char * vals )
17
17
{
18
18
/*
19
19
* Note that strbuf_puts() does not push the null character.
@@ -64,8 +64,7 @@ void elf_generate_header(void)
64
64
}
65
65
66
66
elf32_hdr_t hdr ;
67
- /*
68
- * The following table explains the meaning of each field in the
67
+ /* The following table explains the meaning of each field in the
69
68
* ELF32 file header.
70
69
*
71
70
* Notice that the following values are hexadecimal.
@@ -134,26 +133,34 @@ void elf_generate_header(void)
134
133
hdr .e_version = 1 ; /* ELF version */
135
134
hdr .e_entry = ELF_START + elf_header_len ; /* entry point */
136
135
hdr .e_phoff = 0x34 ; /* program header offset */
137
- hdr .e_shoff = elf_header_len + elf_code -> size + elf_data -> size + 39 +
138
- elf_symtab -> size +
139
- elf_strtab -> size ; /* section header offset */
140
- hdr .e_flags = ELF_FLAGS ; /* flags */
141
- hdr .e_ehsize [0 ] = (char ) 0x34 ; /* header size */
136
+ /* Section header offset: The section headers come after symtab, strtab, and
137
+ * shstrtab which are all written as part of elf_section buffer.
138
+ * shstrtab size = 1 (null) + 10 (.shstrtab\0) + 6 (.text\0) + 6 (.data\0) +
139
+ * 8 (.rodata\0) + 5 (.bss\0) + 8 (.symtab\0) + 8
140
+ * (.strtab\0) + 1 (padding) = 53
141
+ */
142
+ const int shstrtab_size = 53 ; /* section header string table with padding */
143
+ hdr .e_shoff = elf_header_len + elf_code -> size + elf_data -> size +
144
+ elf_rodata -> size + elf_symtab -> size + elf_strtab -> size +
145
+ shstrtab_size ;
146
+ hdr .e_flags = ELF_FLAGS ; /* flags */
147
+ hdr .e_ehsize [0 ] = (char ) 0x34 ; /* header size */
142
148
hdr .e_ehsize [1 ] = 0 ;
143
149
hdr .e_phentsize [0 ] = (char ) 0x20 ; /* program header size */
144
150
hdr .e_phentsize [1 ] = 0 ;
145
151
hdr .e_phnum [0 ] = 1 ; /* number of program headers */
146
152
hdr .e_phnum [1 ] = 0 ;
147
153
hdr .e_shentsize [0 ] = (char ) 0x28 ; /* section header size */
148
154
hdr .e_shentsize [1 ] = 0 ;
149
- hdr .e_shnum [0 ] = 6 ; /* number of section headers */
155
+ /* number of section headers: .rodata and .bss included */
156
+ hdr .e_shnum [0 ] = 8 ;
150
157
hdr .e_shnum [1 ] = 0 ;
151
- hdr .e_shstrndx [0 ] = 5 ; /* section index with names */
158
+ /* section index with names: updated for new sections */
159
+ hdr .e_shstrndx [0 ] = 7 ;
152
160
hdr .e_shstrndx [1 ] = 0 ;
153
161
elf_write_blk (elf_header , & hdr , sizeof (elf32_hdr_t ));
154
162
155
- /*
156
- * Explain the meaning of each field in the ELF32 program header.
163
+ /* Explain the meaning of each field in the ELF32 program header.
157
164
*
158
165
* | Program | |
159
166
* & | Header bytes | Explanation |
@@ -176,14 +183,16 @@ void elf_generate_header(void)
176
183
*/
177
184
/* program header - code and data combined */
178
185
elf32_phdr_t phdr ;
179
- phdr .p_type = 1 ; /* PT_LOAD */
180
- phdr .p_offset = elf_header_len ; /* offset of segment */
181
- phdr .p_vaddr = ELF_START + elf_header_len ; /* virtual address */
182
- phdr .p_paddr = ELF_START + elf_header_len ; /* physical address */
183
- phdr .p_filesz = elf_code -> size + elf_data -> size ; /* size in file */
184
- phdr .p_memsz = elf_code -> size + elf_data -> size ; /* size in memory */
185
- phdr .p_flags = 7 ; /* flags */
186
- phdr .p_align = 4 ; /* alignment */
186
+ phdr .p_type = 1 ; /* PT_LOAD */
187
+ phdr .p_offset = elf_header_len ; /* offset of segment */
188
+ phdr .p_vaddr = ELF_START + elf_header_len ; /* virtual address */
189
+ phdr .p_paddr = ELF_START + elf_header_len ; /* physical address */
190
+ phdr .p_filesz = elf_code -> size + elf_data -> size +
191
+ elf_rodata -> size ; /* size in file - includes .rodata */
192
+ phdr .p_memsz = elf_code -> size + elf_data -> size + elf_rodata -> size +
193
+ elf_bss_size ; /* size in memory - includes .bss */
194
+ phdr .p_flags = 7 ; /* flags */
195
+ phdr .p_align = 4 ; /* alignment */
187
196
elf_write_blk (elf_header , & phdr , sizeof (elf32_phdr_t ));
188
197
}
189
198
@@ -195,26 +204,39 @@ void elf_generate_sections(void)
195
204
return ;
196
205
}
197
206
207
+ int section_data_size = 0 ;
208
+ int shstrtab_start = 0 ; /* Track start of shstrtab */
209
+
198
210
/* symtab section */
199
211
for (int b = 0 ; b < elf_symtab -> size ; b ++ )
200
212
elf_write_byte (elf_section , elf_symtab -> elements [b ]);
213
+ section_data_size += elf_symtab -> size ;
201
214
202
215
/* strtab section */
203
216
for (int b = 0 ; b < elf_strtab -> size ; b ++ )
204
217
elf_write_byte (elf_section , elf_strtab -> elements [b ]);
218
+ section_data_size += elf_strtab -> size ;
205
219
206
- /* shstr section; len = 39 */
220
+ /* shstr section - compute size dynamically */
221
+ shstrtab_start = elf_section -> size ;
207
222
elf_write_byte (elf_section , 0 );
208
223
elf_write_str (elf_section , ".shstrtab" );
209
224
elf_write_byte (elf_section , 0 );
210
225
elf_write_str (elf_section , ".text" );
211
226
elf_write_byte (elf_section , 0 );
212
227
elf_write_str (elf_section , ".data" );
213
228
elf_write_byte (elf_section , 0 );
229
+ elf_write_str (elf_section , ".rodata" );
230
+ elf_write_byte (elf_section , 0 );
231
+ elf_write_str (elf_section , ".bss" );
232
+ elf_write_byte (elf_section , 0 );
214
233
elf_write_str (elf_section , ".symtab" );
215
234
elf_write_byte (elf_section , 0 );
216
235
elf_write_str (elf_section , ".strtab" );
217
236
elf_write_byte (elf_section , 0 );
237
+ /* Add padding byte for alignment - some tools expect this */
238
+ elf_write_byte (elf_section , 0 );
239
+ int shstrtab_size = elf_section -> size - shstrtab_start ;
218
240
219
241
/* section header table */
220
242
elf32_shdr_t shdr ;
@@ -288,22 +310,51 @@ void elf_generate_sections(void)
288
310
elf_write_blk (elf_section , & shdr , sizeof (elf32_shdr_t ));
289
311
ofs += elf_data -> size ;
290
312
313
+ /* .rodata */
314
+ shdr .sh_name = 0x17 ; /* Offset in shstrtab for ".rodata" */
315
+ shdr .sh_type = 1 ; /* SHT_PROGBITS */
316
+ shdr .sh_flags = 2 ; /* SHF_ALLOC only (read-only) */
317
+ shdr .sh_addr = elf_code_start + elf_code -> size + elf_data -> size ;
318
+ shdr .sh_offset = ofs ;
319
+ shdr .sh_size = elf_rodata -> size ;
320
+ shdr .sh_link = 0 ;
321
+ shdr .sh_info = 0 ;
322
+ shdr .sh_addralign = 4 ;
323
+ shdr .sh_entsize = 0 ;
324
+ elf_write_blk (elf_section , & shdr , sizeof (elf32_shdr_t ));
325
+ ofs += elf_rodata -> size ;
326
+
327
+ /* .bss */
328
+ shdr .sh_name = 0x1f ; /* Offset in shstrtab for ".bss" */
329
+ shdr .sh_type = 8 ; /* SHT_NOBITS */
330
+ shdr .sh_flags = 3 ; /* SHF_ALLOC | SHF_WRITE */
331
+ shdr .sh_addr =
332
+ elf_code_start + elf_code -> size + elf_data -> size + elf_rodata -> size ;
333
+ shdr .sh_offset = ofs ; /* File offset (not actually used for NOBITS) */
334
+ shdr .sh_size = elf_bss_size ;
335
+ shdr .sh_link = 0 ;
336
+ shdr .sh_info = 0 ;
337
+ shdr .sh_addralign = 4 ;
338
+ shdr .sh_entsize = 0 ;
339
+ elf_write_blk (elf_section , & shdr , sizeof (elf32_shdr_t ));
340
+ /* Note: .bss is not written to file (SHT_NOBITS) */
341
+
291
342
/* .symtab */
292
- shdr .sh_name = 0x17 ;
343
+ shdr .sh_name = 0x24 ; /* Updated offset for ".symtab" */
293
344
shdr .sh_type = 2 ;
294
345
shdr .sh_flags = 0 ;
295
346
shdr .sh_addr = 0 ;
296
347
shdr .sh_offset = ofs ;
297
348
shdr .sh_size = elf_symtab -> size ;
298
- shdr .sh_link = 4 ;
349
+ shdr .sh_link = 6 ; /* Link to .strtab (section 6) */
299
350
shdr .sh_info = elf_symbol_index ;
300
351
shdr .sh_addralign = 4 ;
301
352
shdr .sh_entsize = 16 ;
302
353
elf_write_blk (elf_section , & shdr , sizeof (elf32_shdr_t ));
303
354
ofs += elf_symtab -> size ;
304
355
305
356
/* .strtab */
306
- shdr .sh_name = 0x1f ;
357
+ shdr .sh_name = 0x2c ; /* Updated offset for ".strtab" */
307
358
shdr .sh_type = 3 ;
308
359
shdr .sh_flags = 0 ;
309
360
shdr .sh_addr = 0 ;
@@ -322,7 +373,7 @@ void elf_generate_sections(void)
322
373
shdr .sh_flags = 0 ;
323
374
shdr .sh_addr = 0 ;
324
375
shdr .sh_offset = ofs ;
325
- shdr .sh_size = 39 ;
376
+ shdr .sh_size = shstrtab_size ; /* Computed dynamically */
326
377
shdr .sh_link = 0 ;
327
378
shdr .sh_info = 0 ;
328
379
shdr .sh_addralign = 1 ;
@@ -333,22 +384,25 @@ void elf_generate_sections(void)
333
384
void elf_align (void )
334
385
{
335
386
/* Check for null pointers to prevent crashes */
336
- if (!elf_data || !elf_symtab || !elf_strtab ) {
387
+ if (!elf_data || !elf_rodata || ! elf_symtab || !elf_strtab ) {
337
388
error ("ELF buffers not initialized for alignment" );
338
389
return ;
339
390
}
340
391
341
392
while (elf_data -> size & 3 )
342
393
elf_write_byte (elf_data , 0 );
343
394
395
+ while (elf_rodata -> size & 3 )
396
+ elf_write_byte (elf_rodata , 0 );
397
+
344
398
while (elf_symtab -> size & 3 )
345
399
elf_write_byte (elf_symtab , 0 );
346
400
347
401
while (elf_strtab -> size & 3 )
348
402
elf_write_byte (elf_strtab , 0 );
349
403
}
350
404
351
- void elf_add_symbol (char * symbol , int pc )
405
+ void elf_add_symbol (const char * symbol , int pc )
352
406
{
353
407
/* Check for null pointers to prevent crashes */
354
408
if (!symbol || !elf_symtab || !elf_strtab ) {
@@ -366,7 +420,7 @@ void elf_add_symbol(char *symbol, int pc)
366
420
elf_symbol_index ++ ;
367
421
}
368
422
369
- void elf_generate (char * outfile )
423
+ void elf_generate (const char * outfile )
370
424
{
371
425
elf_align ();
372
426
elf_generate_header ();
@@ -387,6 +441,9 @@ void elf_generate(char *outfile)
387
441
fputc (elf_code -> elements [i ], fp );
388
442
for (int i = 0 ; i < elf_data -> size ; i ++ )
389
443
fputc (elf_data -> elements [i ], fp );
444
+ for (int i = 0 ; i < elf_rodata -> size ; i ++ )
445
+ fputc (elf_rodata -> elements [i ], fp );
446
+ /* Note: .bss is not written to file (SHT_NOBITS) */
390
447
for (int i = 0 ; i < elf_section -> size ; i ++ )
391
448
fputc (elf_section -> elements [i ], fp );
392
449
fclose (fp );
0 commit comments