X-Git-Url: https://jxself.org/git/?a=blobdiff_plain;f=src%2Flinker.c;h=2da3249b39b119954e4d732dd47f573b2e034378;hb=8e63120c630c94c598d4e2d6ba823dac59bce8fa;hp=6ee0418e0a6aca0390f3ff89ec4e3c0ead4c5b03;hpb=d11f2f726ed7feea617476d99cf7505ddd9a27ce;p=inform.git diff --git a/src/linker.c b/src/linker.c index 6ee0418..2da3249 100644 --- a/src/linker.c +++ b/src/linker.c @@ -1,8 +1,8 @@ /* ------------------------------------------------------------------------- */ /* "linker" : For compiling and linking modules */ /* */ -/* Part of Inform 6.35 */ -/* copyright (c) Graham Nelson 1993 - 2021 */ +/* Part of Inform 6.40 */ +/* copyright (c) Graham Nelson 1993 - 2022 */ /* */ /* Inform is free software: you can redistribute it and/or modify */ /* it under the terms of the GNU General Public License as published by */ @@ -15,18 +15,21 @@ /* GNU General Public License for more details. */ /* */ /* You should have received a copy of the GNU General Public License */ -/* along with Inform. If not, see https://gnu.org/licenses/ * +/* along with Inform. If not, see https://gnu.org/licenses/ */ /* */ /* ------------------------------------------------------------------------- */ #include "header.h" -memory_block link_data_area; -uchar *link_data_holding_area, *link_data_top; +uchar *link_data_holding_area; /* Allocated to link_data_ha_size */ +static memory_list link_data_holding_area_memlist; +int32 link_data_ha_size; + +uchar *link_data_area; +static memory_list link_data_area_memlist; /* Start, current top, size of */ int32 link_data_size; /* link data table being written */ /* (holding import/export names) */ -extern int32 *action_symbol; /* ------------------------------------------------------------------------- */ /* Marker values */ @@ -220,28 +223,28 @@ static void accept_export(void) xref_table[IE.symbol_number] = index; - if (!(sflags[index] & UNKNOWN_SFLAG)) + if (!(symbols[index].flags & UNKNOWN_SFLAG)) { if (IE.module_value == EXPORTAC_MV) - { if ((!(sflags[index] & ACTION_SFLAG)) - && (stypes[index] != FAKE_ACTION_T)) + { if ((!(symbols[index].flags & ACTION_SFLAG)) + && (symbols[index].type != FAKE_ACTION_T)) link_error_named( "action name clash with", IE.symbol_name); } else - if (stypes[index] == IE.symbol_type) + if (symbols[index].type == IE.symbol_type) { switch(IE.symbol_type) { case CONSTANT_T: - if ((!(svals[index] == IE.symbol_value)) + if ((!(symbols[index].value == IE.symbol_value)) || (IE.backpatch != 0)) link_error_named( "program and module give differing values of", IE.symbol_name); break; case INDIVIDUAL_PROPERTY_T: - property_identifier_map[IE.symbol_value] = svals[index]; + property_identifier_map[IE.symbol_value] = symbols[index].value; break; case ROUTINE_T: if ((IE.module_value == EXPORTSF_MV) - && (sflags[index] & REPLACE_SFLAG)) + && (symbols[index].flags & REPLACE_SFLAG)) break; default: sprintf(link_errorm, @@ -254,7 +257,7 @@ static void accept_export(void) else { sprintf(link_errorm, "'%s' has type %s in program but type %s in module", - IE.symbol_name, typename(stypes[index]), + IE.symbol_name, typename(symbols[index].type), typename(IE.symbol_type)); link_error(link_errorm); } @@ -262,15 +265,18 @@ static void accept_export(void) else { if (IE.module_value == EXPORTAC_MV) { IE.symbol_value = no_actions; - action_symbol[no_actions++] = index; + ensure_memory_list_available(&actions_memlist, no_actions+1); + actions[no_actions].symbol = index; + actions[no_actions].byte_offset = 0; /* fill in later */ + no_actions++; if (linker_trace_level >= 4) - printf("Creating action ##%s\n", (char *) symbs[index]); + printf("Creating action ##%s\n", symbols[index].name); } else switch(IE.symbol_type) { case ROUTINE_T: if ((IE.module_value == EXPORTSF_MV) - && (sflags[index] & REPLACE_SFLAG)) + && (symbols[index].flags & REPLACE_SFLAG)) { routine_replace[no_rr] = IE.symbol_value; routine_replace_with[no_rr++] = index; return; @@ -282,7 +288,7 @@ static void accept_export(void) IE.symbol_value += no_objects; break; case ARRAY_T: - IE.symbol_value += dynamic_array_area_size - (MAX_GLOBAL_VARIABLES*2); + IE.symbol_value += dynamic_array_area_size - (MAX_ZCODE_GLOBAL_VARS*2); break; case GLOBAL_VARIABLE_T: if (no_globals==233) @@ -310,21 +316,21 @@ static void accept_export(void) break; } - assign_symbol(index, IE.backpatch*0x10000 + IE.symbol_value, + assign_marked_symbol(index, IE.backpatch, IE.symbol_value, IE.symbol_type); - if (IE.backpatch != 0) sflags[index] |= CHANGE_SFLAG; - sflags[index] |= EXPORT_SFLAG; + if (IE.backpatch != 0) symbols[index].flags |= CHANGE_SFLAG; + symbols[index].flags |= EXPORT_SFLAG; if (IE.module_value == EXPORTSF_MV) - sflags[index] |= INSF_SFLAG; + symbols[index].flags |= INSF_SFLAG; if (IE.module_value == EXPORTAC_MV) - sflags[index] |= ACTION_SFLAG; + symbols[index].flags |= ACTION_SFLAG; } if (IE.module_value == EXPORTAC_MV) { if (linker_trace_level >= 4) printf("Map %d '%s' to %d\n", - IE.symbol_value, (char *) (symbs[index]), svals[index]); - actions_map[map_to] = svals[index]; + IE.symbol_value, (symbols[index].name), symbols[index].value); + actions_map[map_to] = symbols[index].value; } } @@ -332,22 +338,22 @@ static void accept_import(void) { int32 index; index = symbol_index(IE.symbol_name, -1); - sflags[index] |= USED_SFLAG; + symbols[index].flags |= USED_SFLAG; xref_table[IE.symbol_number] = index; - if (!(sflags[index] & UNKNOWN_SFLAG)) + if (!(symbols[index].flags & UNKNOWN_SFLAG)) { switch (IE.symbol_type) { case GLOBAL_VARIABLE_T: - if (stypes[index] != GLOBAL_VARIABLE_T) + if (symbols[index].type != GLOBAL_VARIABLE_T) link_error_named( "module (wrongly) declared this a variable:", IE.symbol_name); - variables_map[IE.symbol_value] = svals[index]; + variables_map[IE.symbol_value] = symbols[index].value; if (IE.symbol_value < lowest_imported_global_no) lowest_imported_global_no = IE.symbol_value; break; default: - switch(stypes[index]) + switch(symbols[index].type) { case ATTRIBUTE_T: link_error_named( "this attribute is undeclared within module:", IE.symbol_name);; break; @@ -374,7 +380,7 @@ static void accept_import(void) { switch (IE.symbol_type) { case GLOBAL_VARIABLE_T: - if (stypes[index] != GLOBAL_VARIABLE_T) + if (symbols[index].type != GLOBAL_VARIABLE_T) link_error_named( "Module tried to import a Global variable not defined here:", IE.symbol_name); @@ -463,11 +469,11 @@ static int32 backpatch_backpatch(int32 v) break; case ARRAY_MV: - if (v < (MAX_GLOBAL_VARIABLES*2)) + if (v < (MAX_ZCODE_GLOBAL_VARS*2)) { v = 2*(variables_map[v/2 + 16] - 16); } else - { v += dynamic_array_area_size - (MAX_GLOBAL_VARIABLES*2); + { v += dynamic_array_area_size - (MAX_ZCODE_GLOBAL_VARS*2); } break; @@ -512,12 +518,12 @@ static void backpatch_module_image(uchar *p, /* The main routine: linking in a module with the given filename. */ /* ------------------------------------------------------------------------- */ -char current_module_filename[128]; +char current_module_filename[PATHLEN]; void link_module(char *given_filename) { FILE *fin; int record_type; - char filename[128]; + char filename[PATHLEN]; uchar *p, p0[64]; int32 last, i, j, k, l, m, vn, len, size, link_offset, module_size, map, max_property_identifier, symbols_base = no_symbols; @@ -638,7 +644,7 @@ of the Inform 6 compiler knows about: it may not link in correctly", filename); no_rr = 0; if ((linker_trace_level>=1) || transcript_switch) - { char link_banner[128]; + { char link_banner[PATHLEN+128]; sprintf(link_banner, "[Linking release %d.%c%c%c%c%c%c of module '%s' (size %dK)]", p[2]*256 + p[3], p[18], p[19], p[20], p[21], p[22], p[23], @@ -681,7 +687,7 @@ of the Inform 6 compiler knows about: it may not link in correctly", filename); if (((record_type == EXPORT_MV) || (record_type == EXPORTSF_MV)) && (IE.symbol_type == INDIVIDUAL_PROPERTY_T)) { int32 si = symbol_index(IE.symbol_name, -1); - property_identifier_map[IE.symbol_value] = svals[si]; + property_identifier_map[IE.symbol_value] = symbols[si].value; } switch(record_type) { case EXPORT_MV: @@ -706,7 +712,7 @@ of the Inform 6 compiler knows about: it may not link in correctly", filename); for (i=0; i story file '%s'\n", i, - (char *) symbs[xref_table[i]]); + symbols[xref_table[i]].name); } } @@ -728,14 +734,14 @@ of the Inform 6 compiler knows about: it may not link in correctly", filename); /* (6) Backpatch the backpatch markers attached to exported symbols */ for (i=symbols_base; i= MAX_STATIC_DATA) - memoryerror("MAX_STATIC_DATA", MAX_STATIC_DATA); + i = m_static_offset - m_vars_offset - MAX_ZCODE_GLOBAL_VARS*2; + ensure_memory_list_available(&dynamic_array_area_memlist, dynamic_array_area_size + i); if (linker_trace_level >= 2) printf("Inserting dynamic array area, %04x to %04x, at %04x\n", - m_vars_offset + MAX_GLOBAL_VARIABLES*2, m_static_offset, + m_vars_offset + MAX_ZCODE_GLOBAL_VARS*2, m_static_offset, variables_offset + dynamic_array_area_size); for (k=0;km_props_offset) - { i = m_static_offset - m_vars_offset - MAX_GLOBAL_VARIABLES*2; - if (dynamic_array_area_size + i >= MAX_STATIC_DATA) - memoryerror("MAX_STATIC_DATA", MAX_STATIC_DATA); + { i = m_static_offset - m_vars_offset - MAX_ZCODE_GLOBAL_VARS*2; if (linker_trace_level >= 2) printf("Inserting object properties area, %04x to %04x, at +%04x\n", m_props_offset, last, properties_table_size); + ensure_memory_list_available(&properties_table_memlist, properties_table_size+last-m_props_offset); for (k=0;k= MAX_INDIV_PROP_TABLE_SIZE) - memoryerror("MAX_INDIV_PROP_TABLE_SIZE", - MAX_INDIV_PROP_TABLE_SIZE); + ensure_memory_list_available(&individuals_table_memlist, individuals_length + i); if (linker_trace_level >= 2) printf("Inserting individual prop tables area, %04x to %04x, at +%04x\n", @@ -987,23 +985,19 @@ at strings offset %04x (+%04x)\n", /* ------------------------------------------------------------------------- */ static void write_link_byte(int x) -{ *link_data_top=(unsigned char) x; link_data_top++; link_data_size++; - if (subtract_pointers(link_data_top,link_data_holding_area) - >= MAX_LINK_DATA_SIZE) - { memoryerror("MAX_LINK_DATA_SIZE",MAX_LINK_DATA_SIZE); - } +{ + ensure_memory_list_available(&link_data_holding_area_memlist, link_data_ha_size+1); + link_data_holding_area[link_data_ha_size] = (unsigned char) x; + link_data_ha_size++; link_data_size++; } extern void flush_link_data(void) { int32 i, j; - j = subtract_pointers(link_data_top, link_data_holding_area); - if (temporary_files_switch) - for (i=0;i= 1) { IE.module_value = EXPORT_MV; IE.symbol_number = symbol_number; - IE.symbol_type = stypes[symbol_number]; - IE.symbol_value = svals[symbol_number]; - IE.symbol_name = (char *) (symbs[symbol_number]); + IE.symbol_type = symbols[symbol_number].type; + IE.symbol_value = symbols[symbol_number].value; + IE.symbol_name = (symbols[symbol_number].name); describe_importexport(&IE); } - if (sflags[symbol_number] & ACTION_SFLAG) + if (symbols[symbol_number].flags & ACTION_SFLAG) write_link_byte(EXPORTAC_MV); else - if (sflags[symbol_number] & INSF_SFLAG) + if (symbols[symbol_number].flags & INSF_SFLAG) write_link_byte(EXPORTSF_MV); else write_link_byte(EXPORT_MV); write_link_word(symbol_number); - write_link_byte(stypes[symbol_number]); - if (sflags[symbol_number] & CHANGE_SFLAG) - write_link_byte(svals[symbol_number] / 0x10000); + write_link_byte(symbols[symbol_number].type); + if (symbols[symbol_number].flags & CHANGE_SFLAG) + write_link_byte(symbols[symbol_number].marker); else write_link_byte(0); - write_link_word(svals[symbol_number] % 0x10000); - write_link_string((char *) (symbs[symbol_number])); + write_link_word(symbols[symbol_number].value % 0x10000); + write_link_string((symbols[symbol_number].name)); flush_link_data(); } @@ -1086,17 +1080,17 @@ static void export_symbols(void) { if (linker_trace_level >= 1) { IE.module_value = IMPORT_MV; IE.symbol_number = symbol_number; - IE.symbol_type = stypes[symbol_number]; - IE.symbol_value = svals[symbol_number]; - IE.symbol_name = (char *) (symbs[symbol_number]); + IE.symbol_type = symbols[symbol_number].type; + IE.symbol_value = symbols[symbol_number].value; + IE.symbol_name = (symbols[symbol_number].name); describe_importexport(&IE); } write_link_byte(IMPORT_MV); write_link_word(symbol_number); - write_link_byte(stypes[symbol_number]); - write_link_word(svals[symbol_number]); - write_link_string((char *) (symbs[symbol_number])); + write_link_byte(symbols[symbol_number].type); + write_link_word(symbols[symbol_number].value); + write_link_string((symbols[symbol_number].name)); flush_link_data(); } } @@ -1109,10 +1103,10 @@ static void export_symbols(void) int mv_vref=LOWEST_SYSTEM_VAR_NUMBER-1; void import_symbol(int32 symbol_number) -{ sflags[symbol_number] |= IMPORT_SFLAG; - switch(stypes[symbol_number]) +{ symbols[symbol_number].flags |= IMPORT_SFLAG; + switch(symbols[symbol_number].type) { case GLOBAL_VARIABLE_T: - assign_symbol(symbol_number, mv_vref--, stypes[symbol_number]); + assign_symbol(symbol_number, mv_vref--, symbols[symbol_number].type); break; } } @@ -1123,11 +1117,13 @@ void import_symbol(int32 symbol_number) extern void init_linker_vars(void) { link_data_size = 0; - initialise_memory_block(&link_data_area); + link_data_area = NULL; + link_data_ha_size = 0; + link_data_holding_area = NULL; } extern void linker_begin_pass(void) -{ link_data_top = link_data_holding_area; +{ link_data_ha_size = 0; } extern void linker_endpass(void) @@ -1137,17 +1133,20 @@ extern void linker_endpass(void) } extern void linker_allocate_arrays(void) -{ if (!module_switch) - link_data_holding_area - = my_malloc(64, "link data holding area"); - else - link_data_holding_area - = my_malloc(MAX_LINK_DATA_SIZE, "link data holding area"); +{ + int initlinksize = (module_switch ? 2000 : 0); + initialise_memory_list(&link_data_holding_area_memlist, + sizeof(uchar), initlinksize, (void**)&link_data_holding_area, + "link data holding area"); + initialise_memory_list(&link_data_area_memlist, + sizeof(uchar), 128, (void**)&link_data_area, + "link data area"); } extern void linker_free_arrays(void) -{ my_free(&link_data_holding_area, "link data holding area"); - deallocate_memory_block(&link_data_area); +{ + deallocate_memory_list(&link_data_holding_area_memlist); + deallocate_memory_list(&link_data_area_memlist); } /* ========================================================================= */