2
* Copyright (C) 2006 Campanoni Simone
4
* This program is free software; you can redistribute it and/or modify
5
* it under the terms of the GNU General Public License as published by
6
* the Free Software Foundation; either version 2 of the License, or
7
* (at your option) any later version.
9
* This program is distributed in the hope that it will be useful,
10
* but WITHOUT ANY WARRANTY; without even the implied warranty of
11
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
* GNU General Public License for more details.
14
* You should have received a copy of the GNU General Public License
15
* along with this program; if not, write to the Free Software
16
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19
* @file iljit_ecmasoft_decoder.c
30
#include <iljit_ecmasoft_decoder.h>
35
* Return the identificator of the assembly that this plugin can decodes
37
static inline JITINT8 * get_ID_binary (void);
39
char * ecmasoft_getVersion(void);
40
char * ecmasoft_getName(void);
41
char * ecmasoft_getAuthor(void);
45
* Decode the assembly referenced by the binary_info parameter
47
static inline JITBOOLEAN decode_image (t_binary_information *binary_info);
53
static inline JITBOOLEAN decoder_init (t_binary_information *binary_info);
57
* Shutdown the decoder
59
static inline JITBOOLEAN decoder_shutdown (t_binary_information *info);
63
* Decode the MS-DOS Header and stores the information in the binary_info struct
65
static inline JITINT32 load_MSDOS_header (t_binary_information *binary_info);
69
* Decode the MS-DOS Stub and stores the information in the binary_info struct
71
static inline JITINT32 load_MSDOS_stub (t_binary_information *binary_info);
75
* Decode the PE Header and stores the information in the binary_info struct
77
static inline JITINT32 load_PE_header (t_binary_information *binary_info);
81
* Decode the PE Optional Header and stores the information in the binary_info struct
83
static inline JITINT32 load_PEOPTIONAL_header (t_binary_information *binary_info);
87
* Decode the CLI Header and stores the information in the binary_info struct
89
static inline JITINT32 load_CLI_header (t_binary_information *binary_info, JITUINT32 min_address);
93
* Decode al the sections and stores the information in the binary_info struct
95
static inline JITINT32 load_SECTIONS_header_table (t_binary_information *binary_info, JITUINT32 *min_address, JITUINT32 base);
99
* Decode all the metadata and stores the information in the binary_info struct
101
static inline JITINT32 load_metadata (t_binary_information *binary_info);
104
static inline JITINT32 load_assembly_references (t_binary_information *binary_info);
105
static inline void ecmasoft_compilationTime (char *buffer, JITINT32 bufferLength);
106
static inline void ecmasoft_compilationFlags (char *buffer, JITINT32 bufferLength);
108
t_plugin_interface plugin_interface={
113
ecmasoft_getVersion ,
115
ecmasoft_compilationFlags ,
116
ecmasoft_compilationTime
119
static inline JITINT8 * get_ID_binary (void){
120
return (JITINT8 *)BINARY_ID;
123
static inline JITBOOLEAN decode_image (t_binary_information *binary_info){
124
JITUINT32 min_address;
128
assert(binary_info!=NULL);
131
decoder_init(binary_info);
133
/* Load MSDOS Header */
134
if (load_MSDOS_header (binary_info)!=0) {
135
decoder_shutdown(binary_info);
138
base=binary_info->MSDOS_header.base;
140
print_binary_offset(binary_info->binary);
143
/* Load MSDOS Stub */
144
if (load_MSDOS_stub (binary_info)!=0) {
145
decoder_shutdown(binary_info);
149
print_binary_offset(binary_info->binary);
153
if (load_PE_header(binary_info)!=0){
154
decoder_shutdown(binary_info);
158
print_binary_offset(binary_info->binary);
161
/* Load PE Optional Header */
162
if (binary_info->PE_info.optional_header_size!=0){
163
if (load_PEOPTIONAL_header(binary_info)!=0){
164
decoder_shutdown(binary_info);
168
print_binary_offset(binary_info->binary);
172
/* Load all the sections */
173
if (load_SECTIONS_header_table (binary_info, &min_address, base)!=0){
174
decoder_shutdown(binary_info);
178
print_binary_offset(binary_info->binary);
181
/* Load CLI Header */
182
if (load_CLI_header(binary_info, min_address)!=0){
183
decoder_shutdown(binary_info);
187
print_binary_offset(binary_info->binary);
191
if (load_metadata(binary_info)!=0){
192
decoder_shutdown(binary_info);
196
print_binary_offset(binary_info->binary);
199
/* Load assembly references */
200
if (load_assembly_references(binary_info)!=0){
201
print_err("DECODER: ERROR= Cannot load libraries. ", 0);
202
decoder_shutdown(binary_info);
209
static inline JITBOOLEAN decoder_init (t_binary_information *binary_info){
210
if (sections_init(&(binary_info->sections))!=0) return -1;
211
binary_info->binary.offset = 0;
212
binary_info->binary.relative_offset = 0;//FIXME call the file_init
213
//metadata_init(binary_info);
217
static inline JITBOOLEAN decoder_shutdown (t_binary_information *info){
218
PDEBUG("DECODER: Decoder shutting down\n");
220
sections_shutdown(&(info->sections));
221
metadata_shutdown(&(info->metadata));
222
PDEBUG("DECODER: Done\n");
233
/****************************************************************************************************************************
234
SECOND LEVEL FUNCTIONS
235
****************************************************************************************************************************/
236
static inline JITINT32 load_MSDOS_header (t_binary_information *binary_info){
237
JITINT8 buffer[DIM_BUF];
240
assert(binary_info!=NULL);
241
assert(binary_info->binary.file!=NULL);
243
PDEBUG("DECODER: MS-DOS Header\n");
244
if (il_read(buffer, 2, &(binary_info->binary))!=0) {
245
PDEBUG("DECODER: ERROR= Cannot read the binary\n");
246
print_err("ECMASOFT DECODER: load_MSDOS_header: ERROR = Error reading MSDOS header. ", 0);
249
if (buffer[0]!='M' || buffer[1]!='Z') {
250
print_err("DECODER: ERROR= The MS-DOS header is not standard. ", 0);
251
PDEBUG("DECODER: Byte 0=%c\n", buffer[0]);
252
PDEBUG("DECODER: Byte 1=%c\n", buffer[1]);
255
if (il_read(buffer+2, 62, &(binary_info->binary))!=0) {
256
print_err("ECMASOFT DECODER: load_MSDOS_header: ERROR = Error reading MSDOS header. ", 0);
259
binary_info->MSDOS_header.base = (*(JITUINT32 *)(buffer+60));
260
if ((binary_info->MSDOS_header.base) < (binary_info->binary.offset)){
261
print_err("DECODER: ERROR= The offset if grater than the base. ", 0);
265
print_binary_offset(binary_info->binary);
267
PDEBUG("DECODER: base = 0x%X %d\n", (JITUINT32)(binary_info->MSDOS_header.base), binary_info->MSDOS_header.base);
272
static inline JITINT32 load_MSDOS_stub (t_binary_information *binary_info){
273
JITINT8 buffer[DIM_BUF];
276
assert(binary_info!=NULL);
278
PDEBUG("DECODER: MS-DOS Stub\n");
279
if (il_read(buffer, 64, &(binary_info->binary))!=0) {
280
print_err("ECMASOFT DECODER: load_MSDOS_stub: ERROR = Error reading MSDOS stub. ", 0);
286
static inline JITINT32 load_PE_header (t_binary_information *binary_info){
287
JITINT8 buffer[DIM_BUF];
290
assert(binary_info!=NULL);
292
PDEBUG("DECODER: PE File Header\n");
293
if (il_read(buffer, 4, &(binary_info->binary))!=0) {
294
print_err("ECMASOFT DECODER: load_PE_header: ERROR = Error reading PE header. ", 0);
297
if (buffer[0]!='P' || buffer[1]!='E' || buffer[2]!='\0' || buffer[3]!='\0') {
298
PDEBUG("DECODER: ERROR= The binary hasn't the PE header standard\n");
301
if (il_read(buffer, 20, &(binary_info->binary))!=0) {
302
print_err("ECMASOFT DECODER: load_PE_header: ERROR = Error reading PE header. ", 0);
305
binary_info->PE_info.section_cardinality = (*(JITUINT16 *)(buffer+2));
306
binary_info->PE_info.time_stamp = (*(JITUINT32 *)(buffer+4));
307
binary_info->PE_info.optional_header_size = (*(JITUINT16 *)(buffer+16));
308
binary_info->PE_info.characteristic = (*(JITUINT16 *)(buffer+18));
309
binary_info->PE_info.isDLL = ( (*(JITUINT16 *)(buffer+18)) & 0x2000 ) != 0 ? 1 : 0;
310
PDEBUG("DECODER: Section cardinality = 0x%X %d\n", binary_info->PE_info.section_cardinality, binary_info->PE_info.section_cardinality);
311
PDEBUG("DECODER: Time stamp = 0x%X %d\n", binary_info->PE_info.time_stamp, binary_info->PE_info.time_stamp);
312
PDEBUG("DECODER: Optional header size = 0x%X %d\n", binary_info->PE_info.optional_header_size, binary_info->PE_info.optional_header_size);
313
PDEBUG("DECODER: DLL flags = 0x%X %d\n", (JITUINT32)binary_info->PE_info.isDLL, binary_info->PE_info.isDLL);
314
PDEBUG("DECODER: Check header value\n");
315
if ((binary_info->PE_info.section_cardinality==0) || (binary_info->PE_info.optional_header_size!=0 && (binary_info->PE_info.optional_header_size < 216 || binary_info->PE_info.optional_header_size > 1024))){
316
PDEBUG("DECODER: ERROR= The binary is not the CIL image\n");
319
PDEBUG("DECODER: Optional header size OK\n");
323
static inline JITINT32 load_PEOPTIONAL_header (t_binary_information *binary_info){
324
JITINT8 buffer[DIM_BUF];
325
assert(binary_info!=NULL);
327
PDEBUG("DECODER: PE Optional header\n");
328
//////////////////////////////// Standard fields
329
PDEBUG("DECODER: Standard fields\n");
330
if (il_read(buffer, binary_info->PE_info.optional_header_size, &(binary_info->binary))!=0) {
331
print_err("ECMASOFT DECODER: load_PEOPTIONAL_header: ERROR = Error reading PEOPTIONAL header. ", 0);
334
binary_info->PE_optional_header.standard_fields.code_size = (*(unsigned short int *)(buffer+4));
335
binary_info->PE_optional_header.standard_fields.size_initialized_data = (*(unsigned int *)(buffer+8));
336
binary_info->PE_optional_header.standard_fields.size_unitialized_data = (*(unsigned int *)(buffer+12));
337
binary_info->PE_optional_header.standard_fields.entry_point_address = (*(unsigned int *)(buffer+16));
338
binary_info->PE_optional_header.standard_fields.base_of_code = (*(unsigned int *)(buffer+20));
339
binary_info->PE_optional_header.standard_fields.base_of_data = (*(unsigned int *)(buffer+24));
340
PDEBUG("DECODER: Code size = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.code_size, (unsigned long int)binary_info->PE_optional_header.standard_fields.code_size);
341
PDEBUG("DECODER: Size initialized data = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.size_initialized_data, (long int)binary_info->PE_optional_header.standard_fields.size_initialized_data);
342
PDEBUG("DECODER: Size unitialized data = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.size_unitialized_data, (long int)binary_info->PE_optional_header.standard_fields.size_unitialized_data);
343
PDEBUG("DECODER: Entry point RVA = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.entry_point_address, (long int)binary_info->PE_optional_header.standard_fields.entry_point_address);
344
PDEBUG("DECODER: Code base RVA = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.base_of_code, (long int)binary_info->PE_optional_header.standard_fields.base_of_code);
345
PDEBUG("DECODER: Data base RVA = 0x%X %ld\n", binary_info->PE_optional_header.standard_fields.base_of_data, (long int)binary_info->PE_optional_header.standard_fields.base_of_data);
347
//////////////////////////////// Windows NT specific
348
PDEBUG("DECODER: Windows NT specific fields\n");
349
binary_info->PE_optional_header.NT_info.file_alignment = (*(unsigned int *)(buffer+36));
350
binary_info->PE_optional_header.NT_info.image_size = (*(unsigned int *)(buffer+56));
351
binary_info->PE_optional_header.NT_info.header_size = (*(unsigned int *)(buffer+60));
352
binary_info->PE_optional_header.NT_info.subsystem = (*(unsigned short int *)(buffer+68));
353
PDEBUG("DECODER: File alignment = 0x%X %ld\n", binary_info->PE_optional_header.NT_info.file_alignment, (long int)binary_info->PE_optional_header.NT_info.file_alignment);
354
PDEBUG("DECODER: Image size = 0x%X %ld\n", binary_info->PE_optional_header.NT_info.image_size, (long int)binary_info->PE_optional_header.NT_info.image_size);
355
PDEBUG("DECODER: Header size = 0x%X %ld\n", binary_info->PE_optional_header.NT_info.header_size, (long int)binary_info->PE_optional_header.NT_info.header_size);
356
PDEBUG("DECODER: SubSystem = 0x%X %ld\n", binary_info->PE_optional_header.NT_info.subsystem, (long int)binary_info->PE_optional_header.NT_info.subsystem);
357
PDEBUG("DECODER: Check values\n");
358
if (binary_info->PE_optional_header.NT_info.file_alignment!=0x200 && binary_info->PE_optional_header.NT_info.file_alignment!=0x1000){
359
print_err("DECODER: ERROR= The file alignment is not 0x200 or 0x1000 as described in the ECMA 335 spectification. ", 0);
362
PDEBUG("DECODER: File alignment OK\n");
363
PDEBUG("DECODER: Directories cardinality OK\n");
365
/* Data directories */
366
PDEBUG("DECODER: Data directories\n");
367
binary_info->PE_optional_header.data_directories.import_table_RVA = (*(unsigned int *)(buffer + 104));
368
binary_info->PE_optional_header.data_directories.import_table_size = (*(unsigned int *)(buffer + 108));
369
binary_info->PE_optional_header.data_directories.relocation_table_RVA = (*(unsigned int *)(buffer + 136));
370
binary_info->PE_optional_header.data_directories.relocation_table_size = (*(unsigned int *)(buffer + 140));
371
binary_info->PE_optional_header.data_directories.import_address_table = (*(unsigned long int *)(buffer + 192));
372
binary_info->PE_optional_header.data_directories.cli_header_RVA = (*(unsigned int *)(buffer + 208));
373
binary_info->PE_optional_header.data_directories.cli_header_size = (*(unsigned int *)(buffer + 212));
374
PDEBUG("DECODER: Import table RVA = 0x%X %d\n", binary_info->PE_optional_header.data_directories.import_table_RVA, binary_info->PE_optional_header.data_directories.import_table_RVA);
375
PDEBUG("DECODER: Import table size = 0x%X %d\n", binary_info->PE_optional_header.data_directories.import_table_size, binary_info->PE_optional_header.data_directories.import_table_size);
376
PDEBUG("DECODER: Relocation table RVA = 0x%X %d\n", binary_info->PE_optional_header.data_directories.relocation_table_RVA, binary_info->PE_optional_header.data_directories.relocation_table_RVA);
377
PDEBUG("DECODER: Relocation table size = 0x%X %d\n", binary_info->PE_optional_header.data_directories.relocation_table_size, binary_info->PE_optional_header.data_directories.relocation_table_size);
378
PDEBUG("DECODER: Import address table = 0x%X %lld\n", (unsigned int)binary_info->PE_optional_header.data_directories.import_address_table, binary_info->PE_optional_header.data_directories.import_address_table);
379
PDEBUG("DECODER: CLI header RVA = 0x%X %d\n", binary_info->PE_optional_header.data_directories.cli_header_RVA, binary_info->PE_optional_header.data_directories.cli_header_RVA);
380
PDEBUG("DECODER: CLI header size = 0x%X %d\n", binary_info->PE_optional_header.data_directories.cli_header_size, binary_info->PE_optional_header.data_directories.cli_header_size);
386
static inline JITINT32 load_CLI_header (t_binary_information *binary_info, JITUINT32 min_address){
387
JITINT8 buffer[DIM_BUF];
391
assert(binary_info!=NULL);
393
PDEBUG("DECODER: Seeking to the CLI Header\n");
395
// Seek to the beginning of the first section
396
PDEBUG("DECODER: Seek to the begin of the first section\n");
397
if(seek_within_file(&(binary_info->binary), buffer, binary_info->binary.offset, min_address)!=0){
398
print_err("DECODER: ERROR= Cannot seek to the minimum address computed. ", 0);
401
assert(binary_info!=NULL);
402
set_metadata_start_point(&(binary_info->binary), (binary_info->binary).offset);
403
(binary_info->binary).relative_offset=0;
405
print_binary_offset(binary_info->binary);
408
// Delete the delta between the begin of the file and the first section
409
PDEBUG("DECODER: Delete from all sections the delta between the begin of the file and the begin of the first section\n");
410
if (add_offset_to_real_address_for_sections(get_first_section(binary_info->sections), -min_address)!=0){
411
print_err("DECODER: ERROR= Cannot add offset to the real address for all section. ", 0);
415
// Compute the address of the file where is the CLI header from the first section
416
PDEBUG("DECODER: Compute the CLI header address whitin the file from the first section\n");
417
base=convert_virtualaddress_to_realaddress (binary_info->sections, binary_info->PE_optional_header.data_directories.cli_header_RVA);
418
PDEBUG("DECODER: CLI header address from the begin of the file = 0x%X %d\n", base, base);
420
PDEBUG("DECODER: CLI header address from the begin of the first section = 0x%X %d\n", base, base);
422
print_binary_offset(binary_info->binary);
425
// Seek to the CLI header
426
PDEBUG("DECODER: Seek to the CLI header address\n");
427
if(seek_within_file(&(binary_info->binary), buffer, 0, base)!=0){
428
print_err("DECODER: ERROR= Cannot seek to the cli header. ", 0);
432
print_binary_offset(binary_info->binary);
435
if (il_read(buffer, 72, &(binary_info->binary))!=0) {
436
print_err("ECMASOFT DECODER: load_CLI_header: ERROR = Error reading CLI header. ", 0);
439
binary_info->cli_information.cb = (*(JITUINT32 *)(buffer));
440
binary_info->cli_information.mayor_runtime_version = (*(JITUINT16 *)(buffer+4));
441
binary_info->cli_information.minor_runtime_version = (*(JITUINT16 *)(buffer+6));
442
binary_info->cli_information.metadata_RVA = (*(JITUINT32 *)(buffer+8));
443
binary_info->cli_information.metadata_size = (*(JITUINT32 *)(buffer+12));
444
binary_info->cli_information.flags = (*(JITUINT32 *)(buffer+16));
445
binary_info->cli_information.entry_point_token = (*(JITUINT32 *)(buffer+20));
446
binary_info->cli_information.resources_RVA = (*(JITUINT32 *)(buffer+24));
447
binary_info->cli_information.resources_size = (*(JITUINT32 *)(buffer+28));
448
binary_info->cli_information.strong_name_signature = (*(JITUINT32 *)(buffer+32));
449
binary_info->cli_information.vtable_fixups = (*(JITUINT32 *)(buffer+48));
451
PDEBUG("DECODER: CLI Header\n");
452
PDEBUG("DECODER: CB = 0x%X %d\n", binary_info->cli_information.cb, binary_info->cli_information.cb);
453
PDEBUG("DECODER: Mayor runtime version = 0x%X %d\n", (JITUINT32)binary_info->cli_information.mayor_runtime_version, binary_info->cli_information.mayor_runtime_version);
454
PDEBUG("DECODER: Minor runtime version = 0x%X %d\n", (JITUINT32)binary_info->cli_information.minor_runtime_version, binary_info->cli_information.minor_runtime_version);
455
PDEBUG("DECODER: Metadata RVA = 0x%X %d\n", binary_info->cli_information.metadata_RVA, binary_info->cli_information.metadata_RVA);
456
PDEBUG("DECODER: Metadata size = 0x%X %d\n", binary_info->cli_information.metadata_size, binary_info->cli_information.metadata_size);
458
char *temp_buffer=cli_flags_to_string(binary_info->cli_information.flags);
459
PDEBUG("DECODER: Flags = 0x%X %d %s\n", binary_info->cli_information.flags, binary_info->cli_information.flags, temp_buffer);
462
PDEBUG("DECODER: Entry point token = 0x%X %d\n", binary_info->cli_information.entry_point_token, binary_info->cli_information.entry_point_token);
463
PDEBUG("DECODER: Resources RVA = 0x%X %d\n", binary_info->cli_information.resources_RVA, binary_info->cli_information.resources_RVA);
464
PDEBUG("DECODER: Resources size = 0x%X %d\n", binary_info->cli_information.resources_size, binary_info->cli_information.resources_size);
465
PDEBUG("DECODER: Strong name signature = 0x%X %lld\n", (JITUINT32)binary_info->cli_information.strong_name_signature, binary_info->cli_information.strong_name_signature);
466
PDEBUG("DECODER: VTable fixups = 0x%X %lld\n", (JITUINT32)binary_info->cli_information.vtable_fixups, binary_info->cli_information.vtable_fixups);
467
print_binary_offset(binary_info->binary);
473
static inline JITINT32 load_SECTIONS_header_table (t_binary_information *binary_info, JITUINT32 *min_address, JITUINT32 base){
474
JITINT32 num_sections;
476
JITUINT32 max_address;
478
JITUINT32 debug_size;
485
JITINT8 buffer[DIM_BUF];
488
assert(binary_info!=NULL);
490
PDEBUG("DECODER: Section headers table\n");
491
num_sections=binary_info->PE_info.section_cardinality;
493
max_address = MIN_UINT;
494
(*min_address) = (JITUINT32)MAX_UINT;
503
while (num_sections > 0){
504
PDEBUG("DECODER: Section %d\n", num_sections);
505
t_section *current_section;
507
if (il_read(buffer, 40, &(binary_info->binary))!=0) {
508
print_err("DECODER: ERROR during reading from file. ", 0);
511
current_section=add_new_section(binary_info->sections);
512
if (current_section==NULL) {
513
print_err("DECODER: ERROR= current_section is NULL. ", 0);
517
// Read the section values
518
strncpy(current_section->name, (char *)buffer, sizeof(char)*8);
519
current_section->virtual_size = *(JITUINT32 *)(buffer+8);
520
current_section->virtual_address = *(JITUINT32 *)(buffer+12);
521
current_section->real_size = *(JITUINT32 *)(buffer+16);
522
current_section->real_address = *(JITUINT32 *)(buffer+20);
523
current_section->rva_relocation_pointer = *(JITUINT32 *)(buffer+24);
524
current_section->rva_relocation_number = *(JITUINT16 *)(buffer+32);
525
current_section->characteristic = *(JITUINT32 *)(buffer+36);
527
// Print information read
528
PDEBUG("DECODER: Name = %s\n", current_section->name);
529
PDEBUG("DECODER: Virtual size = 0x%X %d\n", current_section->virtual_size, current_section->virtual_size);
530
PDEBUG("DECODER: Virtual address = 0x%X %d\n", current_section->virtual_address, current_section->virtual_address);
531
PDEBUG("DECODER: Real size = 0x%X %d\n", current_section->real_size, current_section->real_size);
532
PDEBUG("DECODER: Real address = 0x%X %d\n", current_section->real_address, current_section->real_address);
533
PDEBUG("DECODER: RVA relocation pointer = 0x%X %d\n", current_section->rva_relocation_pointer, current_section->rva_relocation_pointer);
534
PDEBUG("DECODER: RVA relocation number = 0x%X %d\n", current_section->rva_relocation_number, current_section->rva_relocation_number);
536
char *temp=section_characteristic_to_string(current_section->characteristic);
537
PDEBUG("DECODER: Characteristic = 0x%X %s\n", current_section->characteristic, temp);
540
PDEBUG("DECODER: Max address = 0x%X %d\n", max_address, max_address);
541
PDEBUG("DECODER: Min address = 0x%X %d\n", *min_address, *min_address);
543
print_binary_offset(binary_info->binary);
546
// Check some condition
547
if (current_section->virtual_size > current_section->real_size){
548
PDEBUG("DECODER: Virtual size grater than the real one\n");
549
current_section->virtual_size=current_section->real_size;
552
if (!current_section->virtual_size){
553
PDEBUG("DECODER: Virtual size is zero\n");
554
current_section->virtual_size=current_section->real_size;
555
if (!current_section->virtual_address){
556
PDEBUG("DECODER: Virtual address is zero\n");
557
current_section->virtual_address=current_section->real_address;
563
PDEBUG("DECODER: Check values\n");
564
if (((current_section->virtual_address + current_section->virtual_size) & (JITUINT32)MAX_UINT) < current_section->virtual_address){
565
print_err("DECODER: Virtual size is too big. ", 0);
568
PDEBUG("DECODER: Virtual size OK\n");
569
if (((current_section->real_address + current_section->real_size) & (JITUINT32)MAX_UINT) < current_section->real_address){
570
print_err("DECODER: Real size is too big. ", 0);
573
PDEBUG("DECODER: Real size OK\n");
575
// Classify the current section
576
if (!memcmp(buffer, DOTTEXT_SECTION, 8)){
577
PDEBUG("DECODER: Text section\n");
578
base=current_section->virtual_address;
579
} else if (!memcmp(buffer, CORMETA_SECTION, 8)){
580
PDEBUG("DECODER: Cormeta section\n");
581
base=current_section->virtual_address;
583
} else if (!memcmp(buffer, DEBUG_SECTION, 8)){
584
PDEBUG("DECODER: IL debug section\n");
585
debug_rva=current_section->virtual_address;
586
debug_size=current_section->virtual_size;
587
} else if (!memcmp(buffer, SDATA_SECTION, 8)){
588
PDEBUG("DECODER: SData section\n");
589
data_rva=current_section->virtual_address;
590
data_size=current_section->virtual_size;
591
} else if (!memcmp(buffer, DATA_SECTION, 8)){
592
PDEBUG("DECODER: Data section\n");
593
data_rva=current_section->virtual_address;
594
data_size=current_section->virtual_size;
595
} else if (!memcmp(buffer, TLS_SECTION, 8)){
596
PDEBUG("DECODER: TLS section\n");
597
tls_rva=current_section->virtual_address;
598
tls_size=current_section->virtual_size;
599
} else if (!memcmp(buffer, RSRC_SECTION, 8)){
600
PDEBUG("DECODER: RSRC section\n");
601
rsrc_rva=current_section->virtual_address;
602
rsrc_size=current_section->virtual_size;
603
} else if (!memcmp(buffer, BSS_SECTION, 8)){
604
PDEBUG("DECODER: BSS section\n");
605
if (!(current_section->real_address)){
606
// The section <.cormeta> can have an empty <.bss> section, if it's happens, i ignore it
612
// Check some condition
613
if (current_section->real_size > 0){
614
if (current_section->real_address < (*min_address)) (*min_address)=current_section->real_address;
615
if ((current_section->real_address + current_section->real_size) > max_address) max_address=(current_section->real_address + current_section->real_size);
619
PDEBUG("DECODER: End sections\n");
620
PDEBUG("DECODER: Max address = 0x%X %d\n", max_address, max_address);
621
PDEBUG("DECODER: Min address = 0x%X %d\n", *min_address, *min_address);
622
PDEBUG("DECODER: Checking\n");
624
/* If the maximum address is less than the minimum, then there
625
are no sections in the file, and it cannot possibly be IL */
626
if(max_address <= (*min_address)){
627
print_err("DECODER: ERROR= This binary is not IL because the maximum address is less than the minimum. ", 0);
630
PDEBUG("DECODER: Maximum and minimum address are OK\n");
632
/* If we don't have a runtime header yet, then bail out.
633
This can happen if we are processing an object file that
634
does not have a ".text$il" section within it */
636
print_err("DECODER: ERROR= This IL bitecode hasn't the <.text$il> section. ", 0);
639
PDEBUG("DECODER: <.text$il> section OK\n");
640
assert(binary_info->sections!=NULL);
645
static inline JITINT32 load_metadata (t_binary_information *binary_info){
646
JITUINT32 metadata_real_address;
647
JITINT8 buffer[DIM_BUF];
650
assert(binary_info!=NULL);
652
PDEBUG("DECODER: Read metadata\n");
653
metadata_real_address=convert_virtualaddress_to_realaddress(binary_info->sections, binary_info->cli_information.metadata_RVA);
654
PDEBUG("DECODER: Computed the metadata address = 0x%X %d\n", metadata_real_address, metadata_real_address);
655
PDEBUG("DECODER: Seek to the %d offset\n", metadata_real_address);
656
if(seek_within_file(&(binary_info->binary), buffer, binary_info->binary.offset, metadata_real_address)!=0){
657
print_err("DECODER: ERROR= During seeking the file. ", 0);
660
PDEBUG("DECODER: Call the Metadata manager\n");
661
metadata_init(&(binary_info->metadata));
662
if (read_metadata(&(binary_info->metadata), &(binary_info->binary), binary_info->cli_information.metadata_RVA, binary_info->sections)!=0){
663
print_err("ECMASOFT DECODER: load_metadata: ERROR= Error reading metadata. ", 0);
666
assert(binary_info->sections != NULL);
670
static inline JITINT32 load_assembly_references (t_binary_information *binary_info){
671
//TODO da implementare
675
char * ecmasoft_getVersion(void){
679
char * ecmasoft_getAuthor(void){
680
return "Simone Campanoni";
683
char * ecmasoft_getName(void){
687
static inline void ecmasoft_compilationTime (char *buffer, JITINT32 bufferLength){
690
assert(buffer != NULL);
692
snprintf(buffer, sizeof(char) * bufferLength, "%s %s", __DATE__, __TIME__);
695
static inline void ecmasoft_compilationFlags (char *buffer, JITINT32 bufferLength){
698
assert(buffer != NULL);
700
snprintf(buffer, sizeof(char)*bufferLength, " ");
702
strncat(buffer, "DEBUG ", sizeof(char)*bufferLength);
705
strncat(buffer, "PRINTDEBUG ", sizeof(char)*bufferLength);
708
strncat(buffer, "PROFILE ", sizeof(char)*bufferLength);