vector_offset* process_offsets(const vector_offset* first_offsets, const vector_offset* second_offsets) { // We don't known the size of the two file. // We calculate possible value int global_shift_first = global_shift_from_modified_offsets(first_offsets); int global_shift_second = global_shift_from_modified_offsets(second_offsets); int last_pos_mentionned_file0 = (first_offsets->nbelems > 0) ? first_offsets->tab[first_offsets->nbelems-1].old_end : 0; int last_pos_mentionned_file1a = (first_offsets->nbelems > 0) ? first_offsets->tab[first_offsets->nbelems-1].new_end : 0; int last_pos_mentionned_file1b = (second_offsets->nbelems > 0) ? second_offsets->tab[second_offsets->nbelems-1].old_end : 0; int last_pos_mentionned_file2 = (second_offsets->nbelems > 0) ? second_offsets->tab[second_offsets->nbelems-1].new_end : 0; int size_possible_file_1a = offset_max(last_pos_mentionned_file0 + global_shift_first, last_pos_mentionned_file1a); int size_possible_file_1b = offset_max(last_pos_mentionned_file2 - global_shift_second, last_pos_mentionned_file1b); int size_possible_file_1 = offset_max(size_possible_file_1a, size_possible_file_1b); int size_possible_file_0 = size_possible_file_1 - global_shift_first; int size_possible_file_2 = size_possible_file_1 + global_shift_second; // if we add the same positive integer to size_possible_file_0, size_possible_file_1, size_possible_file_2 // the merged_modified result will be the same vector_offset* first_offset_common = modified_offsets_to_common(first_offsets, size_possible_file_0, size_possible_file_1); vector_offset* second_offset_common = modified_offsets_to_common(second_offsets, size_possible_file_1, size_possible_file_2); vector_offset* merged_common = process_common_offsets(first_offset_common, second_offset_common); vector_offset* merged_modified = common_offsets_to_modified(merged_common, size_possible_file_0, size_possible_file_2); free_vector_offset(first_offset_common); free_vector_offset(second_offset_common); free_vector_offset(merged_common); return merged_modified; }
/* 5.6: block statement (compile_body) */ void compile_body(Node decls_node, Node stmts_node, Node handler_node, int is_block_statement) /*;compile_body*/ { int save_last_offset; /* stack frame offset for local variables */ /* will overlap for blocks at the same nesting level */ int save_tasks_declared; Symbol start_handler, end_handler; CURRENT_LEVEL += 1; save_last_offset = LAST_OFFSET; save_tasks_declared = TASKS_DECLARED; TASKS_DECLARED = FALSE; gen(I_ENTER_BLOCK); compile(decls_node); if (handler_node != OPT_NODE) { start_handler = new_unique_name("handler"); gen_s(I_INSTALL_HANDLER, start_handler); } if (TASKS_DECLARED) { gen(I_ACTIVATE); } compile(stmts_node); if (handler_node != OPT_NODE) { if (is_block_statement) { /* use label allocated if return in accept else allocate * a label for end of block (cf. comments in gen_accept) */ if (symbol_accept_return != (Symbol)0) { end_handler = symbol_accept_return; } else { end_handler = new_unique_name("end_handler"); } gen_s(I_JUMP, end_handler); gen_s(I_LABEL, start_handler); compile(handler_node); gen_s(I_LABEL, end_handler); } else { gen_s(I_LABEL, start_handler); compile(handler_node); } } /*MAX_OFFSET max= abs LAST_OFFSET;*/ MAX_OFFSET = offset_max(MAX_OFFSET, LAST_OFFSET); LAST_OFFSET = save_last_offset; TASKS_DECLARED = save_tasks_declared; CURRENT_LEVEL -= 1; }
/** * translate a set of offset * ofs is an array of nb_translations items of type offset_translation * Before calling the function, you must fill: * (ofs + #)->position_to_translate with a position (offset) to translate * (ofs + #)->sort_order=# (because array will be sorted on position_to_translate, then back to sort_order */ void translate_offset(offset_translation* ofs, int nb_translations, const vector_offset* offsets, int revert) { if (offsets == NULL) { return; } if ((nb_translations == 0) || (ofs == NULL)) { return; } int i; int sorted_by_position = 1; for (i = 1;i < nb_translations;i++) if (((ofs + i)->position_to_translate) < ((ofs + i - 1)->position_to_translate)) { sorted_by_position = 0; break; } if (!sorted_by_position) { qsort(ofs,nb_translations,sizeof(offset_translation), compare_offset_translation_by_position); } int last_position_in_offsets = revert ? (offsets->tab[offsets->nbelems - 1].new_start + offsets->tab[offsets->nbelems-1].new_end) : (offsets->tab[offsets->nbelems - 1].old_start + offsets->tab[offsets->nbelems-1].old_end); int last_position_to_translate = (ofs + nb_translations - 1)->position_to_translate; int minimal_filesize = offset_max(last_position_in_offsets, last_position_to_translate); vector_offset* common_offsets = modified_offsets_to_common(offsets, -1, minimal_filesize); int pos_common_offsets = 0; for (i = 0; i < nb_translations; i++) { int pos_to_translate = (ofs + i)->position_to_translate; for (;;) { if (pos_common_offsets == common_offsets->nbelems) break; int end_current_common = revert ? (common_offsets->tab[pos_common_offsets].new_end) : (common_offsets->tab[pos_common_offsets].old_end); if (end_current_common > pos_to_translate) break; pos_common_offsets++; } int current_common_start = -1; int current_common_end = -1; if (pos_common_offsets < common_offsets->nbelems) { current_common_start = revert ? (common_offsets->tab[pos_common_offsets].new_start) : (common_offsets->tab[pos_common_offsets].old_start); current_common_end = revert ? (common_offsets->tab[pos_common_offsets].new_end) : (common_offsets->tab[pos_common_offsets].old_end); int translate_common_start = revert ? (common_offsets->tab[pos_common_offsets].old_start) : (common_offsets->tab[pos_common_offsets].new_start); if ((pos_to_translate >= current_common_start) && (pos_to_translate < current_common_end)) { (ofs + i)->translated_position = translate_common_start + (pos_to_translate - current_common_start); (ofs + i)->translation_pos_in_common = 1; } else { (ofs + i)->translated_position = translate_common_start + (current_common_end - current_common_start); (ofs + i)->translation_pos_in_common = -1; } } else { int last_pos_translated = 0; if (common_offsets->nbelems > 0) last_pos_translated = revert ? ((common_offsets->tab[common_offsets->nbelems-1].old_start) -1) : ((common_offsets->tab[common_offsets->nbelems-1].new_start) -1); if (last_pos_translated == -1) last_pos_translated = 0; (ofs + i)->translated_position = last_pos_translated; (ofs + i)->translation_pos_in_common = -1; } } free_vector_offset(common_offsets); int sorted_by_sort_order = 1; for (i = 1;i < nb_translations;i++) if (((ofs + i)->sort_order) < ((ofs + i - 1)->sort_order)) { sorted_by_sort_order = 0; break; } if (!sorted_by_sort_order) { qsort(ofs, nb_translations, sizeof(offset_translation), compare_offset_translation_by_sort_order); } }