final.c (107604) | final.c (117404) |
---|---|
1/* Convert RTL to assembler code and output it, for GNU compiler. 2 Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 3 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc. 4 5This file is part of GCC. 6 7GCC is free software; you can redistribute it and/or modify it under 8the terms of the GNU General Public License as published by the Free --- 54 unchanged lines hidden (view full) --- 63#include "function.h" 64#include "toplev.h" 65#include "reload.h" 66#include "intl.h" 67#include "basic-block.h" 68#include "target.h" 69#include "debug.h" 70#include "expr.h" | 1/* Convert RTL to assembler code and output it, for GNU compiler. 2 Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 3 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc. 4 5This file is part of GCC. 6 7GCC is free software; you can redistribute it and/or modify it under 8the terms of the GNU General Public License as published by the Free --- 54 unchanged lines hidden (view full) --- 63#include "function.h" 64#include "toplev.h" 65#include "reload.h" 66#include "intl.h" 67#include "basic-block.h" 68#include "target.h" 69#include "debug.h" 70#include "expr.h" |
71#include "profile.h" 72#include "cfglayout.h" |
|
71 72#ifdef XCOFF_DEBUGGING_INFO 73#include "xcoffout.h" /* Needed for external data 74 declarations for e.g. AIX 4.x. */ 75#endif 76 77#if defined (DWARF2_UNWIND_INFO) || defined (DWARF2_DEBUGGING_INFO) 78#include "dwarf2out.h" --- 14 unchanged lines hidden (view full) --- 93#ifndef IS_ASM_LOGICAL_LINE_SEPARATOR 94#define IS_ASM_LOGICAL_LINE_SEPARATOR(C) ((C) == ';') 95#endif 96 97#ifndef JUMP_TABLES_IN_TEXT_SECTION 98#define JUMP_TABLES_IN_TEXT_SECTION 0 99#endif 100 | 73 74#ifdef XCOFF_DEBUGGING_INFO 75#include "xcoffout.h" /* Needed for external data 76 declarations for e.g. AIX 4.x. */ 77#endif 78 79#if defined (DWARF2_UNWIND_INFO) || defined (DWARF2_DEBUGGING_INFO) 80#include "dwarf2out.h" --- 14 unchanged lines hidden (view full) --- 95#ifndef IS_ASM_LOGICAL_LINE_SEPARATOR 96#define IS_ASM_LOGICAL_LINE_SEPARATOR(C) ((C) == ';') 97#endif 98 99#ifndef JUMP_TABLES_IN_TEXT_SECTION 100#define JUMP_TABLES_IN_TEXT_SECTION 0 101#endif 102 |
103#if defined(READONLY_DATA_SECTION) || defined(READONLY_DATA_SECTION_ASM_OP) 104#define HAVE_READONLY_DATA_SECTION 1 105#else 106#define HAVE_READONLY_DATA_SECTION 0 107#endif 108 |
|
101/* Last insn processed by final_scan_insn. */ 102static rtx debug_insn; 103rtx current_output_insn; 104 105/* Line number of last NOTE. */ 106static int last_linenum; 107 108/* Highest line number in current block. */ 109static int high_block_linenum; 110 111/* Likewise for function. */ 112static int high_function_linenum; 113 114/* Filename of last NOTE. */ 115static const char *last_filename; 116 | 109/* Last insn processed by final_scan_insn. */ 110static rtx debug_insn; 111rtx current_output_insn; 112 113/* Line number of last NOTE. */ 114static int last_linenum; 115 116/* Highest line number in current block. */ 117static int high_block_linenum; 118 119/* Likewise for function. */ 120static int high_function_linenum; 121 122/* Filename of last NOTE. */ 123static const char *last_filename; 124 |
117/* Number of instrumented arcs when profile_arc_flag is set. */ 118extern int count_instrumented_edges; 119 | |
120extern int length_unit_log; /* This is defined in insn-attrtab.c. */ 121 122/* Nonzero while outputting an `asm' with operands. 123 This means that inconsistencies are the user's fault, so don't abort. 124 The precise value is the insn being output, to pass to error_for_asm. */ | 125extern int length_unit_log; /* This is defined in insn-attrtab.c. */ 126 127/* Nonzero while outputting an `asm' with operands. 128 This means that inconsistencies are the user's fault, so don't abort. 129 The precise value is the insn being output, to pass to error_for_asm. */ |
125static rtx this_is_asm_operands; | 130rtx this_is_asm_operands; |
126 127/* Number of operands of this insn, for an `asm' with operands. */ 128static unsigned int insn_noperands; 129 130/* Compare optimization flag. */ 131 132static rtx last_ignored_compare = 0; 133 --- 59 unchanged lines hidden (view full) --- 193 194static char *line_note_exists; 195 196#ifdef HAVE_conditional_execution 197/* Nonnull if the insn currently being emitted was a COND_EXEC pattern. */ 198rtx current_insn_predicate; 199#endif 200 | 131 132/* Number of operands of this insn, for an `asm' with operands. */ 133static unsigned int insn_noperands; 134 135/* Compare optimization flag. */ 136 137static rtx last_ignored_compare = 0; 138 --- 59 unchanged lines hidden (view full) --- 198 199static char *line_note_exists; 200 201#ifdef HAVE_conditional_execution 202/* Nonnull if the insn currently being emitted was a COND_EXEC pattern. */ 203rtx current_insn_predicate; 204#endif 205 |
206struct function_list 207{ 208 struct function_list *next; /* next function */ 209 const char *name; /* function name */ 210 long cfg_checksum; /* function checksum */ 211 long count_edges; /* number of intrumented edges in this function */ 212}; 213 214static struct function_list *functions_head = 0; 215static struct function_list **functions_tail = &functions_head; 216 |
|
201#ifdef HAVE_ATTR_length 202static int asm_insn_count PARAMS ((rtx)); 203#endif 204static void profile_function PARAMS ((FILE *)); 205static void profile_after_prologue PARAMS ((FILE *)); 206static void notice_source_line PARAMS ((rtx)); 207static rtx walk_alter_subreg PARAMS ((rtx *)); 208static void output_asm_name PARAMS ((void)); | 217#ifdef HAVE_ATTR_length 218static int asm_insn_count PARAMS ((rtx)); 219#endif 220static void profile_function PARAMS ((FILE *)); 221static void profile_after_prologue PARAMS ((FILE *)); 222static void notice_source_line PARAMS ((rtx)); 223static rtx walk_alter_subreg PARAMS ((rtx *)); 224static void output_asm_name PARAMS ((void)); |
225static void output_alternate_entry_point PARAMS ((FILE *, rtx)); |
|
209static tree get_mem_expr_from_op PARAMS ((rtx, int *)); 210static void output_asm_operand_names PARAMS ((rtx *, int *, int)); 211static void output_operand PARAMS ((rtx, int)); 212#ifdef LEAF_REGISTERS 213static void leaf_renumber_regs PARAMS ((rtx)); 214#endif 215#ifdef HAVE_cc0 216static int alter_cond PARAMS ((rtx)); --- 15 unchanged lines hidden (view full) --- 232 final_sequence = 0; 233 234#ifdef ASSEMBLER_DIALECT 235 dialect_number = ASSEMBLER_DIALECT; 236#endif 237} 238 239/* Called at end of source file, | 226static tree get_mem_expr_from_op PARAMS ((rtx, int *)); 227static void output_asm_operand_names PARAMS ((rtx *, int *, int)); 228static void output_operand PARAMS ((rtx, int)); 229#ifdef LEAF_REGISTERS 230static void leaf_renumber_regs PARAMS ((rtx)); 231#endif 232#ifdef HAVE_cc0 233static int alter_cond PARAMS ((rtx)); --- 15 unchanged lines hidden (view full) --- 249 final_sequence = 0; 250 251#ifdef ASSEMBLER_DIALECT 252 dialect_number = ASSEMBLER_DIALECT; 253#endif 254} 255 256/* Called at end of source file, |
240 to output the block-profiling table for this entire compilation. */ | 257 to output the arc-profiling table for this entire compilation. */ |
241 242void 243end_final (filename) 244 const char *filename; 245{ | 258 259void 260end_final (filename) 261 const char *filename; 262{ |
246 if (profile_arc_flag) | 263 if (profile_arc_flag && profile_info.count_instrumented_edges) |
247 { 248 char name[20]; | 264 { 265 char name[20]; |
249 int align = exact_log2 (BIGGEST_ALIGNMENT / BITS_PER_UNIT); 250 int size, rounded; 251 int long_bytes = LONG_TYPE_SIZE / BITS_PER_UNIT; 252 int gcov_type_bytes = GCOV_TYPE_SIZE / BITS_PER_UNIT; 253 int pointer_bytes = POINTER_SIZE / BITS_PER_UNIT; 254 unsigned int align2 = LONG_TYPE_SIZE; | 266 tree string_type, string_cst; 267 tree structure_decl, structure_value, structure_pointer_type; 268 tree field_decl, decl_chain, value_chain; 269 tree sizeof_field_value, domain_type; |
255 | 270 |
256 size = gcov_type_bytes * count_instrumented_edges; 257 rounded = size; | 271 /* Build types. */ 272 string_type = build_pointer_type (char_type_node); |
258 | 273 |
259 rounded += (BIGGEST_ALIGNMENT / BITS_PER_UNIT) - 1; 260 rounded = (rounded / (BIGGEST_ALIGNMENT / BITS_PER_UNIT) 261 * (BIGGEST_ALIGNMENT / BITS_PER_UNIT)); | 274 /* Libgcc2 bb structure. */ 275 structure_decl = make_node (RECORD_TYPE); 276 structure_pointer_type = build_pointer_type (structure_decl); |
262 | 277 |
263 /* ??? This _really_ ought to be done with a structure layout 264 and with assemble_constructor. If long_bytes != pointer_bytes 265 we'll be emitting unaligned data at some point. */ 266 if (long_bytes != pointer_bytes) 267 abort (); | 278 /* Output the main header, of 7 words: 279 0: 1 if this file is initialized, else 0. 280 1: address of file name (LPBX1). 281 2: address of table of counts (LPBX2). 282 3: number of counts in the table. 283 4: always 0, libgcc2 uses this as a pointer to next ``struct bb'' |
268 | 284 |
269 data_section (); | 285 The following are GNU extensions: |
270 | 286 |
271 /* Output the main header, of 11 words: 272 0: 1 if this file is initialized, else 0. 273 1: address of file name (LPBX1). 274 2: address of table of counts (LPBX2). 275 3: number of counts in the table. 276 4: always 0, for compatibility with Sun. | 287 5: Number of bytes in this header. 288 6: address of table of function checksums (LPBX7). */ |
277 | 289 |
278 The following are GNU extensions: | 290 /* The zero word. */ 291 decl_chain = 292 build_decl (FIELD_DECL, get_identifier ("zero_word"), 293 long_integer_type_node); 294 value_chain = build_tree_list (decl_chain, 295 convert (long_integer_type_node, 296 integer_zero_node)); |
279 | 297 |
280 5: address of table of start addrs of basic blocks (LPBX3). 281 6: Number of bytes in this header. 282 7: address of table of function names (LPBX4). 283 8: address of table of line numbers (LPBX5) or 0. 284 9: address of table of file names (LPBX6) or 0. 285 10: space reserved for basic block profiling. */ | 298 /* Address of filename. */ 299 { 300 char *cwd, *da_filename; 301 int da_filename_len; |
286 | 302 |
287 ASM_OUTPUT_ALIGN (asm_out_file, align); | 303 field_decl = 304 build_decl (FIELD_DECL, get_identifier ("filename"), string_type); 305 TREE_CHAIN (field_decl) = decl_chain; 306 decl_chain = field_decl; |
288 | 307 |
289 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 0); | 308 cwd = getpwd (); 309 da_filename_len = strlen (filename) + strlen (cwd) + 4 + 1; 310 da_filename = (char *) alloca (da_filename_len); 311 strcpy (da_filename, cwd); 312 strcat (da_filename, "/"); 313 strcat (da_filename, filename); 314 strcat (da_filename, ".da"); 315 da_filename_len = strlen (da_filename); 316 string_cst = build_string (da_filename_len + 1, da_filename); 317 domain_type = build_index_type (build_int_2 (da_filename_len, 0)); 318 TREE_TYPE (string_cst) 319 = build_array_type (char_type_node, domain_type); 320 value_chain = tree_cons (field_decl, 321 build1 (ADDR_EXPR, string_type, string_cst), 322 value_chain); 323 } |
290 | 324 |
291 /* Zero word. */ 292 assemble_integer (const0_rtx, long_bytes, align2, 1); | 325 /* Table of counts. */ 326 { 327 tree gcov_type_type = make_unsigned_type (GCOV_TYPE_SIZE); 328 tree gcov_type_pointer_type = build_pointer_type (gcov_type_type); 329 tree domain_tree 330 = build_index_type (build_int_2 (profile_info. 331 count_instrumented_edges - 1, 0)); 332 tree gcov_type_array_type 333 = build_array_type (gcov_type_type, domain_tree); 334 tree gcov_type_array_pointer_type 335 = build_pointer_type (gcov_type_array_type); 336 tree counts_table; |
293 | 337 |
294 /* Address of filename. */ 295 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 1); 296 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name), pointer_bytes, 297 align2, 1); | 338 field_decl = 339 build_decl (FIELD_DECL, get_identifier ("counts"), 340 gcov_type_pointer_type); 341 TREE_CHAIN (field_decl) = decl_chain; 342 decl_chain = field_decl; |
298 | 343 |
299 /* Address of count table. */ 300 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2); 301 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name), pointer_bytes, 302 align2, 1); | 344 /* No values. */ 345 counts_table 346 = build (VAR_DECL, gcov_type_array_type, NULL_TREE, NULL_TREE); 347 TREE_STATIC (counts_table) = 1; 348 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2); 349 DECL_NAME (counts_table) = get_identifier (name); 350 assemble_variable (counts_table, 0, 0, 0); |
303 | 351 |
352 value_chain = tree_cons (field_decl, 353 build1 (ADDR_EXPR, 354 gcov_type_array_pointer_type, 355 counts_table), value_chain); 356 } 357 |
|
304 /* Count of the # of instrumented arcs. */ | 358 /* Count of the # of instrumented arcs. */ |
305 assemble_integer (GEN_INT (count_instrumented_edges), 306 long_bytes, align2, 1); | 359 field_decl 360 = build_decl (FIELD_DECL, get_identifier ("ncounts"), 361 long_integer_type_node); 362 TREE_CHAIN (field_decl) = decl_chain; 363 decl_chain = field_decl; |
307 | 364 |
308 /* Zero word (link field). */ 309 assemble_integer (const0_rtx, pointer_bytes, align2, 1); | 365 value_chain = tree_cons (field_decl, 366 convert (long_integer_type_node, 367 build_int_2 (profile_info. 368 count_instrumented_edges, 369 0)), value_chain); 370 /* Pointer to the next bb. */ 371 field_decl 372 = build_decl (FIELD_DECL, get_identifier ("next"), 373 structure_pointer_type); 374 TREE_CHAIN (field_decl) = decl_chain; 375 decl_chain = field_decl; |
310 | 376 |
311 assemble_integer (const0_rtx, pointer_bytes, align2, 1); | 377 value_chain = tree_cons (field_decl, null_pointer_node, value_chain); |
312 | 378 |
313 /* Byte count for extended structure. */ 314 assemble_integer (GEN_INT (11 * UNITS_PER_WORD), long_bytes, align2, 1); | 379 /* sizeof(struct bb). We'll set this after entire structure 380 is laid out. */ 381 field_decl 382 = build_decl (FIELD_DECL, get_identifier ("sizeof_bb"), 383 long_integer_type_node); 384 TREE_CHAIN (field_decl) = decl_chain; 385 decl_chain = field_decl; |
315 | 386 |
316 /* Address of function name table. */ 317 assemble_integer (const0_rtx, pointer_bytes, align2, 1); | 387 sizeof_field_value = tree_cons (field_decl, NULL, value_chain); 388 value_chain = sizeof_field_value; |
318 | 389 |
319 /* Address of line number and filename tables if debugging. */ 320 assemble_integer (const0_rtx, pointer_bytes, align2, 1); 321 assemble_integer (const0_rtx, pointer_bytes, align2, 1); | 390 /* struct bb_function []. */ 391 { 392 struct function_list *item; 393 int num_nodes; 394 tree checksum_field, arc_count_field, name_field; 395 tree domain; 396 tree array_value_chain = NULL_TREE; 397 tree bb_fn_struct_type; 398 tree bb_fn_struct_array_type; 399 tree bb_fn_struct_array_pointer_type; 400 tree bb_fn_struct_pointer_type; 401 tree field_value, field_value_chain; |
322 | 402 |
323 /* Space for extension ptr (link field). */ 324 assemble_integer (const0_rtx, UNITS_PER_WORD, align2, 1); | 403 bb_fn_struct_type = make_node (RECORD_TYPE); |
325 | 404 |
326 /* Output the file name changing the suffix to .d for 327 Sun tcov compatibility. */ 328 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 1); 329 { 330 char *cwd = getpwd (); 331 int len = strlen (filename) + strlen (cwd) + 1; 332 char *data_file = (char *) alloca (len + 4); | 405 checksum_field = build_decl (FIELD_DECL, get_identifier ("checksum"), 406 long_integer_type_node); |
333 | 407 |
334 strcpy (data_file, cwd); 335 strcat (data_file, "/"); 336 strcat (data_file, filename); 337 strip_off_ending (data_file, len); 338 strcat (data_file, ".da"); 339 assemble_string (data_file, strlen (data_file) + 1); | 408 arc_count_field 409 = build_decl (FIELD_DECL, get_identifier ("arc_count"), 410 integer_type_node); 411 TREE_CHAIN (checksum_field) = arc_count_field; 412 413 name_field 414 = build_decl (FIELD_DECL, get_identifier ("name"), string_type); 415 TREE_CHAIN (arc_count_field) = name_field; 416 417 TYPE_FIELDS (bb_fn_struct_type) = checksum_field; 418 419 num_nodes = 0; 420 421 for (item = functions_head; item != 0; item = item->next) 422 num_nodes++; 423 424 /* Note that the array contains a terminator, hence no - 1. */ 425 domain = build_index_type (build_int_2 (num_nodes, 0)); 426 427 bb_fn_struct_pointer_type = build_pointer_type (bb_fn_struct_type); 428 bb_fn_struct_array_type 429 = build_array_type (bb_fn_struct_type, domain); 430 bb_fn_struct_array_pointer_type 431 = build_pointer_type (bb_fn_struct_array_type); 432 433 layout_type (bb_fn_struct_type); 434 layout_type (bb_fn_struct_pointer_type); 435 layout_type (bb_fn_struct_array_type); 436 layout_type (bb_fn_struct_array_pointer_type); 437 438 for (item = functions_head; item != 0; item = item->next) 439 { 440 size_t name_len; 441 442 /* create constructor for structure. */ 443 field_value_chain 444 = build_tree_list (checksum_field, 445 convert (long_integer_type_node, 446 build_int_2 (item->cfg_checksum, 0))); 447 field_value_chain 448 = tree_cons (arc_count_field, 449 convert (integer_type_node, 450 build_int_2 (item->count_edges, 0)), 451 field_value_chain); 452 453 name_len = strlen (item->name); 454 string_cst = build_string (name_len + 1, item->name); 455 domain_type = build_index_type (build_int_2 (name_len, 0)); 456 TREE_TYPE (string_cst) 457 = build_array_type (char_type_node, domain_type); 458 field_value_chain = tree_cons (name_field, 459 build1 (ADDR_EXPR, string_type, 460 string_cst), 461 field_value_chain); 462 463 /* Add to chain. */ 464 array_value_chain 465 = tree_cons (NULL_TREE, build (CONSTRUCTOR, 466 bb_fn_struct_type, NULL_TREE, 467 nreverse (field_value_chain)), 468 array_value_chain); 469 } 470 471 /* Add terminator. */ 472 field_value = build_tree_list (arc_count_field, 473 convert (integer_type_node, 474 build_int_2 (-1, 0))); 475 476 array_value_chain = tree_cons (NULL_TREE, 477 build (CONSTRUCTOR, bb_fn_struct_type, 478 NULL_TREE, field_value), 479 array_value_chain); 480 481 482 /* Create constructor for array. */ 483 field_decl 484 = build_decl (FIELD_DECL, get_identifier ("function_infos"), 485 bb_fn_struct_pointer_type); 486 value_chain = tree_cons (field_decl, 487 build1 (ADDR_EXPR, 488 bb_fn_struct_array_pointer_type, 489 build (CONSTRUCTOR, 490 bb_fn_struct_array_type, 491 NULL_TREE, 492 nreverse 493 (array_value_chain))), 494 value_chain); 495 TREE_CHAIN (field_decl) = decl_chain; 496 decl_chain = field_decl; |
340 } 341 | 497 } 498 |
342 /* Make space for the table of counts. */ 343 if (size == 0) 344 { 345 /* Realign data section. */ 346 ASM_OUTPUT_ALIGN (asm_out_file, align); 347 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 2); 348 if (size != 0) 349 assemble_zeros (size); 350 } 351 else 352 { 353 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2); 354#ifdef ASM_OUTPUT_SHARED_LOCAL 355 if (flag_shared_data) 356 ASM_OUTPUT_SHARED_LOCAL (asm_out_file, name, size, rounded); 357 else 358#endif 359#ifdef ASM_OUTPUT_ALIGNED_DECL_LOCAL 360 ASM_OUTPUT_ALIGNED_DECL_LOCAL (asm_out_file, NULL_TREE, name, 361 size, BIGGEST_ALIGNMENT); 362#else 363#ifdef ASM_OUTPUT_ALIGNED_LOCAL 364 ASM_OUTPUT_ALIGNED_LOCAL (asm_out_file, name, size, 365 BIGGEST_ALIGNMENT); 366#else 367 ASM_OUTPUT_LOCAL (asm_out_file, name, size, rounded); 368#endif 369#endif 370 } | 499 /* Finish structure. */ 500 TYPE_FIELDS (structure_decl) = nreverse (decl_chain); 501 layout_type (structure_decl); 502 503 structure_value 504 = build (VAR_DECL, structure_decl, NULL_TREE, NULL_TREE); 505 DECL_INITIAL (structure_value) 506 = build (CONSTRUCTOR, structure_decl, NULL_TREE, 507 nreverse (value_chain)); 508 TREE_STATIC (structure_value) = 1; 509 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 0); 510 DECL_NAME (structure_value) = get_identifier (name); 511 512 /* Size of this structure. */ 513 TREE_VALUE (sizeof_field_value) 514 = convert (long_integer_type_node, 515 build_int_2 (int_size_in_bytes (structure_decl), 0)); 516 517 /* Build structure. */ 518 assemble_variable (structure_value, 0, 0, 0); |
371 } 372} 373 374/* Default target function prologue and epilogue assembler output. 375 376 If not overridden for epilogue code, then the function body itself 377 contains return instructions wherever needed. */ 378void --- 54 unchanged lines hidden (view full) --- 433/* The next two pages contain routines used to compute the length of an insn 434 and to shorten branches. */ 435 436/* Arrays for insn lengths, and addresses. The latter is referenced by 437 `insn_current_length'. */ 438 439static int *insn_lengths; 440 | 519 } 520} 521 522/* Default target function prologue and epilogue assembler output. 523 524 If not overridden for epilogue code, then the function body itself 525 contains return instructions wherever needed. */ 526void --- 54 unchanged lines hidden (view full) --- 581/* The next two pages contain routines used to compute the length of an insn 582 and to shorten branches. */ 583 584/* Arrays for insn lengths, and addresses. The latter is referenced by 585 `insn_current_length'. */ 586 587static int *insn_lengths; 588 |
441#ifdef HAVE_ATTR_length | |
442varray_type insn_addresses_; | 589varray_type insn_addresses_; |
443#endif | |
444 445/* Max uid for which the above arrays are valid. */ 446static int insn_lengths_max_uid; 447 448/* Address of insn being processed. Used by `insn_current_length'. */ 449int insn_current_address; 450 451/* Address of insn being processed in previous iteration. */ --- 70 unchanged lines hidden (view full) --- 522 return 0; 523 524 case CALL_INSN: 525 length = insn_default_length (insn); 526 break; 527 528 case JUMP_INSN: 529 body = PATTERN (insn); | 590 591/* Max uid for which the above arrays are valid. */ 592static int insn_lengths_max_uid; 593 594/* Address of insn being processed. Used by `insn_current_length'. */ 595int insn_current_address; 596 597/* Address of insn being processed in previous iteration. */ --- 70 unchanged lines hidden (view full) --- 668 return 0; 669 670 case CALL_INSN: 671 length = insn_default_length (insn); 672 break; 673 674 case JUMP_INSN: 675 body = PATTERN (insn); |
530 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC) | 676 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC) |
531 { 532 /* Alignment is machine-dependent and should be handled by 533 ADDR_VEC_ALIGN. */ 534 } 535 else 536 length = insn_default_length (insn); 537 break; 538 --- 243 unchanged lines hidden (view full) --- 782 + align_fuzz (dest, seq, length_unit_log, ~0)); 783 } 784} 785#endif /* HAVE_ATTR_length */ 786 787void 788compute_alignments () 789{ | 677 { 678 /* Alignment is machine-dependent and should be handled by 679 ADDR_VEC_ALIGN. */ 680 } 681 else 682 length = insn_default_length (insn); 683 break; 684 --- 243 unchanged lines hidden (view full) --- 928 + align_fuzz (dest, seq, length_unit_log, ~0)); 929 } 930} 931#endif /* HAVE_ATTR_length */ 932 933void 934compute_alignments () 935{ |
790 int i; | |
791 int log, max_skip, max_log; | 936 int log, max_skip, max_log; |
937 basic_block bb; |
|
792 793 if (label_align) 794 { 795 free (label_align); 796 label_align = 0; 797 } 798 799 max_labelno = max_label_num (); 800 min_labelno = get_first_label_num (); 801 label_align = (struct label_alignment *) 802 xcalloc (max_labelno - min_labelno + 1, sizeof (struct label_alignment)); 803 804 /* If not optimizing or optimizing for size, don't assign any alignments. */ 805 if (! optimize || optimize_size) 806 return; 807 | 938 939 if (label_align) 940 { 941 free (label_align); 942 label_align = 0; 943 } 944 945 max_labelno = max_label_num (); 946 min_labelno = get_first_label_num (); 947 label_align = (struct label_alignment *) 948 xcalloc (max_labelno - min_labelno + 1, sizeof (struct label_alignment)); 949 950 /* If not optimizing or optimizing for size, don't assign any alignments. */ 951 if (! optimize || optimize_size) 952 return; 953 |
808 for (i = 0; i < n_basic_blocks; i++) | 954 FOR_EACH_BB (bb) |
809 { | 955 { |
810 basic_block bb = BASIC_BLOCK (i); | |
811 rtx label = bb->head; 812 int fallthru_frequency = 0, branch_frequency = 0, has_fallthru = 0; 813 edge e; 814 815 if (GET_CODE (label) != CODE_LABEL) 816 continue; 817 max_log = LABEL_ALIGN (label); 818 max_skip = LABEL_ALIGN_MAX_SKIP; --- 13 unchanged lines hidden (view full) --- 832 833 We to catch first case, we align frequently executed blocks. 834 To catch the second, we align blocks that are executed more frequently 835 than the predecessor and the predecessor is likely to not be executed 836 when function is called. */ 837 838 if (!has_fallthru 839 && (branch_frequency > BB_FREQ_MAX / 10 | 956 rtx label = bb->head; 957 int fallthru_frequency = 0, branch_frequency = 0, has_fallthru = 0; 958 edge e; 959 960 if (GET_CODE (label) != CODE_LABEL) 961 continue; 962 max_log = LABEL_ALIGN (label); 963 max_skip = LABEL_ALIGN_MAX_SKIP; --- 13 unchanged lines hidden (view full) --- 977 978 We to catch first case, we align frequently executed blocks. 979 To catch the second, we align blocks that are executed more frequently 980 than the predecessor and the predecessor is likely to not be executed 981 when function is called. */ 982 983 if (!has_fallthru 984 && (branch_frequency > BB_FREQ_MAX / 10 |
840 || (bb->frequency > BASIC_BLOCK (i - 1)->frequency * 10 841 && (BASIC_BLOCK (i - 1)->frequency | 985 || (bb->frequency > bb->prev_bb->frequency * 10 986 && (bb->prev_bb->frequency |
842 <= ENTRY_BLOCK_PTR->frequency / 2)))) 843 { 844 log = JUMP_ALIGN (label); 845 if (max_log < log) 846 { 847 max_log = log; 848 max_skip = JUMP_ALIGN_MAX_SKIP; 849 } 850 } 851 /* In case block is frequent and reached mostly by non-fallthru edge, | 987 <= ENTRY_BLOCK_PTR->frequency / 2)))) 988 { 989 log = JUMP_ALIGN (label); 990 if (max_log < log) 991 { 992 max_log = log; 993 max_skip = JUMP_ALIGN_MAX_SKIP; 994 } 995 } 996 /* In case block is frequent and reached mostly by non-fallthru edge, |
852 align it. It is most likely an first block of loop. */ | 997 align it. It is most likely a first block of loop. */ |
853 if (has_fallthru 854 && branch_frequency + fallthru_frequency > BB_FREQ_MAX / 10 | 998 if (has_fallthru 999 && branch_frequency + fallthru_frequency > BB_FREQ_MAX / 10 |
855 && branch_frequency > fallthru_frequency * 5) | 1000 && branch_frequency > fallthru_frequency * 2) |
856 { 857 log = LOOP_ALIGN (label); 858 if (max_log < log) 859 { 860 max_log = log; 861 max_skip = LOOP_ALIGN_MAX_SKIP; 862 } 863 } --- 105 unchanged lines hidden (view full) --- 969 if (max_log < log) 970 { 971 max_log = log; 972 max_skip = LABEL_ALIGN_MAX_SKIP; 973 } 974 next = NEXT_INSN (insn); 975 /* ADDR_VECs only take room if read-only data goes into the text 976 section. */ | 1001 { 1002 log = LOOP_ALIGN (label); 1003 if (max_log < log) 1004 { 1005 max_log = log; 1006 max_skip = LOOP_ALIGN_MAX_SKIP; 1007 } 1008 } --- 105 unchanged lines hidden (view full) --- 1114 if (max_log < log) 1115 { 1116 max_log = log; 1117 max_skip = LABEL_ALIGN_MAX_SKIP; 1118 } 1119 next = NEXT_INSN (insn); 1120 /* ADDR_VECs only take room if read-only data goes into the text 1121 section. */ |
977 if (JUMP_TABLES_IN_TEXT_SECTION 978#if !defined(READONLY_DATA_SECTION) 979 || 1 980#endif 981 ) | 1122 if (JUMP_TABLES_IN_TEXT_SECTION || !HAVE_READONLY_DATA_SECTION) |
982 if (next && GET_CODE (next) == JUMP_INSN) 983 { 984 rtx nextbody = PATTERN (next); 985 if (GET_CODE (nextbody) == ADDR_VEC 986 || GET_CODE (nextbody) == ADDR_DIFF_VEC) 987 { 988 log = ADDR_VEC_ALIGN (next); 989 if (max_log < log) --- 133 unchanged lines hidden (view full) --- 1123 if (log) 1124 { 1125 int align = 1 << log; 1126 int new_address = (insn_current_address + align - 1) & -align; 1127 insn_lengths[uid] = new_address - insn_current_address; 1128 } 1129 } 1130 | 1123 if (next && GET_CODE (next) == JUMP_INSN) 1124 { 1125 rtx nextbody = PATTERN (next); 1126 if (GET_CODE (nextbody) == ADDR_VEC 1127 || GET_CODE (nextbody) == ADDR_DIFF_VEC) 1128 { 1129 log = ADDR_VEC_ALIGN (next); 1130 if (max_log < log) --- 133 unchanged lines hidden (view full) --- 1264 if (log) 1265 { 1266 int align = 1 << log; 1267 int new_address = (insn_current_address + align - 1) & -align; 1268 insn_lengths[uid] = new_address - insn_current_address; 1269 } 1270 } 1271 |
1131 INSN_ADDRESSES (uid) = insn_current_address; | 1272 INSN_ADDRESSES (uid) = insn_current_address + insn_lengths[uid]; |
1132 1133 if (GET_CODE (insn) == NOTE || GET_CODE (insn) == BARRIER 1134 || GET_CODE (insn) == CODE_LABEL) 1135 continue; 1136 if (INSN_DELETED_P (insn)) 1137 continue; 1138 1139 body = PATTERN (insn); 1140 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC) 1141 { 1142 /* This only takes room if read-only data goes into the text 1143 section. */ | 1273 1274 if (GET_CODE (insn) == NOTE || GET_CODE (insn) == BARRIER 1275 || GET_CODE (insn) == CODE_LABEL) 1276 continue; 1277 if (INSN_DELETED_P (insn)) 1278 continue; 1279 1280 body = PATTERN (insn); 1281 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC) 1282 { 1283 /* This only takes room if read-only data goes into the text 1284 section. */ |
1144 if (JUMP_TABLES_IN_TEXT_SECTION 1145#if !defined(READONLY_DATA_SECTION) 1146 || 1 1147#endif 1148 ) | 1285 if (JUMP_TABLES_IN_TEXT_SECTION || !HAVE_READONLY_DATA_SECTION) |
1149 insn_lengths[uid] = (XVECLEN (body, 1150 GET_CODE (body) == ADDR_DIFF_VEC) 1151 * GET_MODE_SIZE (GET_MODE (body))); 1152 /* Alignment is handled by ADDR_VEC_ALIGN. */ 1153 } 1154 else if (GET_CODE (body) == ASM_INPUT || asm_noperands (body) >= 0) 1155 insn_lengths[uid] = asm_insn_count (body) * insn_default_length (insn); 1156 else if (GET_CODE (body) == SEQUENCE) --- 184 unchanged lines hidden (view full) --- 1341 max_addr += align_fuzz (insn, rel_lab, 0, 0); 1342 } 1343 else 1344 max_addr += align_fuzz (max_lab, rel_lab, 0, 0); 1345 } 1346 PUT_MODE (body, CASE_VECTOR_SHORTEN_MODE (min_addr - rel_addr, 1347 max_addr - rel_addr, 1348 body)); | 1286 insn_lengths[uid] = (XVECLEN (body, 1287 GET_CODE (body) == ADDR_DIFF_VEC) 1288 * GET_MODE_SIZE (GET_MODE (body))); 1289 /* Alignment is handled by ADDR_VEC_ALIGN. */ 1290 } 1291 else if (GET_CODE (body) == ASM_INPUT || asm_noperands (body) >= 0) 1292 insn_lengths[uid] = asm_insn_count (body) * insn_default_length (insn); 1293 else if (GET_CODE (body) == SEQUENCE) --- 184 unchanged lines hidden (view full) --- 1478 max_addr += align_fuzz (insn, rel_lab, 0, 0); 1479 } 1480 else 1481 max_addr += align_fuzz (max_lab, rel_lab, 0, 0); 1482 } 1483 PUT_MODE (body, CASE_VECTOR_SHORTEN_MODE (min_addr - rel_addr, 1484 max_addr - rel_addr, 1485 body)); |
1349 if (JUMP_TABLES_IN_TEXT_SECTION 1350#if !defined(READONLY_DATA_SECTION) 1351 || 1 1352#endif 1353 ) | 1486 if (JUMP_TABLES_IN_TEXT_SECTION || !HAVE_READONLY_DATA_SECTION) |
1354 { 1355 insn_lengths[uid] 1356 = (XVECLEN (body, 1) * GET_MODE_SIZE (GET_MODE (body))); 1357 insn_current_address += insn_lengths[uid]; 1358 if (insn_lengths[uid] != old_length) 1359 something_changed = 1; 1360 } 1361 --- 13 unchanged lines hidden (view full) --- 1375 { 1376 rtx inner_insn = XVECEXP (body, 0, i); 1377 int inner_uid = INSN_UID (inner_insn); 1378 1379 INSN_ADDRESSES (inner_uid) = insn_current_address; 1380 1381 insn_current_address += insn_lengths[inner_uid]; 1382 } | 1487 { 1488 insn_lengths[uid] 1489 = (XVECLEN (body, 1) * GET_MODE_SIZE (GET_MODE (body))); 1490 insn_current_address += insn_lengths[uid]; 1491 if (insn_lengths[uid] != old_length) 1492 something_changed = 1; 1493 } 1494 --- 13 unchanged lines hidden (view full) --- 1508 { 1509 rtx inner_insn = XVECEXP (body, 0, i); 1510 int inner_uid = INSN_UID (inner_insn); 1511 1512 INSN_ADDRESSES (inner_uid) = insn_current_address; 1513 1514 insn_current_address += insn_lengths[inner_uid]; 1515 } |
1383 } | 1516 } |
1384 else 1385 insn_current_address += insn_lengths[uid]; 1386 1387 continue; 1388 } 1389 1390 if (GET_CODE (insn) == INSN && GET_CODE (PATTERN (insn)) == SEQUENCE) 1391 { --- 140 unchanged lines hidden (view full) --- 1532 dwarf2out_frame_debug (NULL_RTX); 1533#endif 1534 1535 /* If debugging, assign block numbers to all of the blocks in this 1536 function. */ 1537 if (write_symbols) 1538 { 1539 remove_unnecessary_notes (); | 1517 else 1518 insn_current_address += insn_lengths[uid]; 1519 1520 continue; 1521 } 1522 1523 if (GET_CODE (insn) == INSN && GET_CODE (PATTERN (insn)) == SEQUENCE) 1524 { --- 140 unchanged lines hidden (view full) --- 1665 dwarf2out_frame_debug (NULL_RTX); 1666#endif 1667 1668 /* If debugging, assign block numbers to all of the blocks in this 1669 function. */ 1670 if (write_symbols) 1671 { 1672 remove_unnecessary_notes (); |
1540 reorder_blocks (); | 1673 scope_to_insns_finalize (); |
1541 number_blocks (current_function_decl); 1542 /* We never actually put out begin/end notes for the top-level 1543 block in the function. But, conceptually, that block is 1544 always needed. */ 1545 TREE_ASM_WRITTEN (DECL_INITIAL (current_function_decl)) = 1; 1546 } 1547 1548 /* First output the function prologue: code to set up the stack frame. */ 1549 (*targetm.asm_out.function_prologue) (file, get_frame_size ()); 1550 | 1674 number_blocks (current_function_decl); 1675 /* We never actually put out begin/end notes for the top-level 1676 block in the function. But, conceptually, that block is 1677 always needed. */ 1678 TREE_ASM_WRITTEN (DECL_INITIAL (current_function_decl)) = 1; 1679 } 1680 1681 /* First output the function prologue: code to set up the stack frame. */ 1682 (*targetm.asm_out.function_prologue) (file, get_frame_size ()); 1683 |
1551#ifdef VMS_DEBUGGING_INFO 1552 /* Output label after the prologue of the function. */ 1553 if (write_symbols == VMS_DEBUG || write_symbols == VMS_AND_DWARF2_DEBUG) 1554 vmsdbgout_after_prologue (); 1555#endif 1556 | |
1557 /* If the machine represents the prologue as RTL, the profiling code must 1558 be emitted when NOTE_INSN_PROLOGUE_END is scanned. */ 1559#ifdef HAVE_prologue 1560 if (! HAVE_prologue) 1561#endif 1562 profile_after_prologue (file); 1563} 1564 --- 21 unchanged lines hidden (view full) --- 1586#if defined(STATIC_CHAIN_INCOMING_REGNUM) || defined(STATIC_CHAIN_REGNUM) 1587 int cxt = current_function_needs_context; 1588#endif 1589#endif /* ASM_OUTPUT_REG_PUSH */ 1590 1591#ifndef NO_PROFILE_COUNTERS 1592 data_section (); 1593 ASM_OUTPUT_ALIGN (file, floor_log2 (align / BITS_PER_UNIT)); | 1684 /* If the machine represents the prologue as RTL, the profiling code must 1685 be emitted when NOTE_INSN_PROLOGUE_END is scanned. */ 1686#ifdef HAVE_prologue 1687 if (! HAVE_prologue) 1688#endif 1689 profile_after_prologue (file); 1690} 1691 --- 21 unchanged lines hidden (view full) --- 1713#if defined(STATIC_CHAIN_INCOMING_REGNUM) || defined(STATIC_CHAIN_REGNUM) 1714 int cxt = current_function_needs_context; 1715#endif 1716#endif /* ASM_OUTPUT_REG_PUSH */ 1717 1718#ifndef NO_PROFILE_COUNTERS 1719 data_section (); 1720 ASM_OUTPUT_ALIGN (file, floor_log2 (align / BITS_PER_UNIT)); |
1594 ASM_OUTPUT_INTERNAL_LABEL (file, "LP", current_function_profile_label_no); | 1721 ASM_OUTPUT_INTERNAL_LABEL (file, "LP", current_function_funcdef_no); |
1595 assemble_integer (const0_rtx, LONG_TYPE_SIZE / BITS_PER_UNIT, align, 1); 1596#endif 1597 1598 function_section (current_function_decl); 1599 1600#if defined(STRUCT_VALUE_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1601 if (sval) 1602 ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_INCOMING_REGNUM); --- 13 unchanged lines hidden (view full) --- 1616#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1617 if (cxt) 1618 { 1619 ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_REGNUM); 1620 } 1621#endif 1622#endif 1623 | 1722 assemble_integer (const0_rtx, LONG_TYPE_SIZE / BITS_PER_UNIT, align, 1); 1723#endif 1724 1725 function_section (current_function_decl); 1726 1727#if defined(STRUCT_VALUE_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1728 if (sval) 1729 ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_INCOMING_REGNUM); --- 13 unchanged lines hidden (view full) --- 1743#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1744 if (cxt) 1745 { 1746 ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_REGNUM); 1747 } 1748#endif 1749#endif 1750 |
1624 FUNCTION_PROFILER (file, current_function_profile_label_no); | 1751 FUNCTION_PROFILER (file, current_function_funcdef_no); |
1625 1626#if defined(STATIC_CHAIN_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1627 if (cxt) 1628 ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_INCOMING_REGNUM); 1629#else 1630#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1631 if (cxt) 1632 { --- 26 unchanged lines hidden (view full) --- 1659 1660 (*debug_hooks->end_function) (high_function_linenum); 1661 1662 /* Finally, output the function epilogue: 1663 code to restore the stack frame and return to the caller. */ 1664 (*targetm.asm_out.function_epilogue) (asm_out_file, get_frame_size ()); 1665 1666 /* And debug output. */ | 1752 1753#if defined(STATIC_CHAIN_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1754 if (cxt) 1755 ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_INCOMING_REGNUM); 1756#else 1757#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH) 1758 if (cxt) 1759 { --- 26 unchanged lines hidden (view full) --- 1786 1787 (*debug_hooks->end_function) (high_function_linenum); 1788 1789 /* Finally, output the function epilogue: 1790 code to restore the stack frame and return to the caller. */ 1791 (*targetm.asm_out.function_epilogue) (asm_out_file, get_frame_size ()); 1792 1793 /* And debug output. */ |
1667 (*debug_hooks->end_epilogue) (); | 1794 (*debug_hooks->end_epilogue) (last_linenum, last_filename); |
1668 1669#if defined (DWARF2_UNWIND_INFO) 1670 if (write_symbols != DWARF2_DEBUG && write_symbols != VMS_AND_DWARF2_DEBUG 1671 && dwarf2out_do_frame ()) | 1795 1796#if defined (DWARF2_UNWIND_INFO) 1797 if (write_symbols != DWARF2_DEBUG && write_symbols != VMS_AND_DWARF2_DEBUG 1798 && dwarf2out_do_frame ()) |
1672 dwarf2out_end_epilogue (); | 1799 dwarf2out_end_epilogue (last_linenum, last_filename); |
1673#endif 1674} 1675 1676/* Output assembler code for some insns: all or part of a function. 1677 For description of args, see `final_start_function', above. 1678 1679 PRESCAN is 1 if we are not really outputting, 1680 just scanning as if we were outputting. --- 77 unchanged lines hidden (view full) --- 1758 CC_STATUS_INIT; 1759 1760 /* Output the insns. */ 1761 for (insn = NEXT_INSN (first); insn;) 1762 { 1763#ifdef HAVE_ATTR_length 1764 if ((unsigned) INSN_UID (insn) >= INSN_ADDRESSES_SIZE ()) 1765 { | 1800#endif 1801} 1802 1803/* Output assembler code for some insns: all or part of a function. 1804 For description of args, see `final_start_function', above. 1805 1806 PRESCAN is 1 if we are not really outputting, 1807 just scanning as if we were outputting. --- 77 unchanged lines hidden (view full) --- 1885 CC_STATUS_INIT; 1886 1887 /* Output the insns. */ 1888 for (insn = NEXT_INSN (first); insn;) 1889 { 1890#ifdef HAVE_ATTR_length 1891 if ((unsigned) INSN_UID (insn) >= INSN_ADDRESSES_SIZE ()) 1892 { |
1766#ifdef STACK_REGS 1767 /* Irritatingly, the reg-stack pass is creating new instructions 1768 and because of REG_DEAD note abuse it has to run after 1769 shorten_branches. Fake address of -1 then. */ 1770 insn_current_address = -1; 1771#else | |
1772 /* This can be triggered by bugs elsewhere in the compiler if 1773 new insns are created after init_insn_lengths is called. */ | 1893 /* This can be triggered by bugs elsewhere in the compiler if 1894 new insns are created after init_insn_lengths is called. */ |
1774 abort (); 1775#endif | 1895 if (GET_CODE (insn) == NOTE) 1896 insn_current_address = -1; 1897 else 1898 abort (); |
1776 } 1777 else 1778 insn_current_address = INSN_ADDRESSES (INSN_UID (insn)); 1779#endif /* HAVE_ATTR_length */ 1780 1781 insn = final_scan_insn (insn, file, optimize, prescan, 0); 1782 } 1783 | 1899 } 1900 else 1901 insn_current_address = INSN_ADDRESSES (INSN_UID (insn)); 1902#endif /* HAVE_ATTR_length */ 1903 1904 insn = final_scan_insn (insn, file, optimize, prescan, 0); 1905 } 1906 |
1907 /* Store function names for edge-profiling. */ 1908 /* ??? Probably should re-use the existing struct function. */ 1909 1910 if (cfun->arc_profile) 1911 { 1912 struct function_list *new_item = xmalloc (sizeof (struct function_list)); 1913 1914 *functions_tail = new_item; 1915 functions_tail = &new_item->next; 1916 1917 new_item->next = 0; 1918 new_item->name = xstrdup (IDENTIFIER_POINTER 1919 (DECL_ASSEMBLER_NAME (current_function_decl))); 1920 new_item->cfg_checksum = profile_info.current_function_cfg_checksum; 1921 new_item->count_edges = profile_info.count_edges_instrumented_now; 1922 } 1923 |
|
1784 free (line_note_exists); 1785 line_note_exists = NULL; 1786} 1787 1788const char * 1789get_insn_template (code, insn) 1790 int code; 1791 rtx insn; --- 10 unchanged lines hidden (view full) --- 1802 abort (); 1803 return (*(insn_output_fn) output) (recog_data.operand, insn); 1804 1805 default: 1806 abort (); 1807 } 1808} 1809 | 1924 free (line_note_exists); 1925 line_note_exists = NULL; 1926} 1927 1928const char * 1929get_insn_template (code, insn) 1930 int code; 1931 rtx insn; --- 10 unchanged lines hidden (view full) --- 1942 abort (); 1943 return (*(insn_output_fn) output) (recog_data.operand, insn); 1944 1945 default: 1946 abort (); 1947 } 1948} 1949 |
1950/* Emit the appropriate declaration for an alternate-entry-point 1951 symbol represented by INSN, to FILE. INSN is a CODE_LABEL with 1952 LABEL_KIND != LABEL_NORMAL. 1953 1954 The case fall-through in this function is intentional. */ 1955static void 1956output_alternate_entry_point (file, insn) 1957 FILE *file; 1958 rtx insn; 1959{ 1960 const char *name = LABEL_NAME (insn); 1961 1962 switch (LABEL_KIND (insn)) 1963 { 1964 case LABEL_WEAK_ENTRY: 1965#ifdef ASM_WEAKEN_LABEL 1966 ASM_WEAKEN_LABEL (file, name); 1967#endif 1968 case LABEL_GLOBAL_ENTRY: 1969 (*targetm.asm_out.globalize_label) (file, name); 1970 case LABEL_STATIC_ENTRY: 1971#ifdef ASM_OUTPUT_TYPE_DIRECTIVE 1972 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function"); 1973#endif 1974 ASM_OUTPUT_LABEL (file, name); 1975 break; 1976 1977 case LABEL_NORMAL: 1978 default: 1979 abort (); 1980 } 1981} 1982 |
|
1810/* The final scan for one insn, INSN. 1811 Args are same as in `final', except that INSN 1812 is the insn being scanned. 1813 Value returned is the next insn to be scanned. 1814 1815 NOPEEPHOLES is the flag to disallow peephole processing (currently 1816 used for within delayed branch sequence output). */ 1817 --- 27 unchanged lines hidden (view full) --- 1845 case NOTE_INSN_DELETED: 1846 case NOTE_INSN_LOOP_BEG: 1847 case NOTE_INSN_LOOP_END: 1848 case NOTE_INSN_LOOP_END_TOP_COND: 1849 case NOTE_INSN_LOOP_CONT: 1850 case NOTE_INSN_LOOP_VTOP: 1851 case NOTE_INSN_FUNCTION_END: 1852 case NOTE_INSN_REPEATED_LINE_NUMBER: | 1983/* The final scan for one insn, INSN. 1984 Args are same as in `final', except that INSN 1985 is the insn being scanned. 1986 Value returned is the next insn to be scanned. 1987 1988 NOPEEPHOLES is the flag to disallow peephole processing (currently 1989 used for within delayed branch sequence output). */ 1990 --- 27 unchanged lines hidden (view full) --- 2018 case NOTE_INSN_DELETED: 2019 case NOTE_INSN_LOOP_BEG: 2020 case NOTE_INSN_LOOP_END: 2021 case NOTE_INSN_LOOP_END_TOP_COND: 2022 case NOTE_INSN_LOOP_CONT: 2023 case NOTE_INSN_LOOP_VTOP: 2024 case NOTE_INSN_FUNCTION_END: 2025 case NOTE_INSN_REPEATED_LINE_NUMBER: |
1853 case NOTE_INSN_RANGE_BEG: 1854 case NOTE_INSN_RANGE_END: 1855 case NOTE_INSN_LIVE: | |
1856 case NOTE_INSN_EXPECTED_VALUE: 1857 break; 1858 1859 case NOTE_INSN_BASIC_BLOCK: 1860#ifdef IA64_UNWIND_INFO 1861 IA64_UNWIND_EMIT (asm_out_file, insn); 1862#endif 1863 if (flag_debug_asm) --- 17 unchanged lines hidden (view full) --- 1881 break; 1882 1883 case NOTE_INSN_EPILOGUE_BEG: 1884 (*targetm.asm_out.function_begin_epilogue) (file); 1885 break; 1886 1887 case NOTE_INSN_FUNCTION_BEG: 1888 app_disable (); | 2026 case NOTE_INSN_EXPECTED_VALUE: 2027 break; 2028 2029 case NOTE_INSN_BASIC_BLOCK: 2030#ifdef IA64_UNWIND_INFO 2031 IA64_UNWIND_EMIT (asm_out_file, insn); 2032#endif 2033 if (flag_debug_asm) --- 17 unchanged lines hidden (view full) --- 2051 break; 2052 2053 case NOTE_INSN_EPILOGUE_BEG: 2054 (*targetm.asm_out.function_begin_epilogue) (file); 2055 break; 2056 2057 case NOTE_INSN_FUNCTION_BEG: 2058 app_disable (); |
1889 (*debug_hooks->end_prologue) (last_linenum); | 2059 (*debug_hooks->end_prologue) (last_linenum, last_filename); |
1890 break; 1891 1892 case NOTE_INSN_BLOCK_BEG: 1893 if (debug_info_level == DINFO_LEVEL_NORMAL 1894 || debug_info_level == DINFO_LEVEL_VERBOSE 1895 || write_symbols == DWARF_DEBUG 1896 || write_symbols == DWARF2_DEBUG 1897 || write_symbols == VMS_AND_DWARF2_DEBUG --- 113 unchanged lines hidden (view full) --- 2011 int max_skip = LABEL_TO_MAX_SKIP (insn); 2012#endif 2013 2014 if (align && NEXT_INSN (insn)) 2015 { 2016#ifdef ASM_OUTPUT_MAX_SKIP_ALIGN 2017 ASM_OUTPUT_MAX_SKIP_ALIGN (file, align, max_skip); 2018#else | 2060 break; 2061 2062 case NOTE_INSN_BLOCK_BEG: 2063 if (debug_info_level == DINFO_LEVEL_NORMAL 2064 || debug_info_level == DINFO_LEVEL_VERBOSE 2065 || write_symbols == DWARF_DEBUG 2066 || write_symbols == DWARF2_DEBUG 2067 || write_symbols == VMS_AND_DWARF2_DEBUG --- 113 unchanged lines hidden (view full) --- 2181 int max_skip = LABEL_TO_MAX_SKIP (insn); 2182#endif 2183 2184 if (align && NEXT_INSN (insn)) 2185 { 2186#ifdef ASM_OUTPUT_MAX_SKIP_ALIGN 2187 ASM_OUTPUT_MAX_SKIP_ALIGN (file, align, max_skip); 2188#else |
2189#ifdef ASM_OUTPUT_ALIGN_WITH_NOP 2190 ASM_OUTPUT_ALIGN_WITH_NOP (file, align); 2191#else |
|
2019 ASM_OUTPUT_ALIGN (file, align); 2020#endif | 2192 ASM_OUTPUT_ALIGN (file, align); 2193#endif |
2194#endif |
|
2021 } 2022 } 2023#ifdef HAVE_cc0 2024 CC_STATUS_INIT; 2025 /* If this label is reached from only one place, set the condition 2026 codes from the instruction just before the branch. */ 2027 2028 /* Disabled because some insns set cc_status in the C output code --- 66 unchanged lines hidden (view full) --- 2095 } 2096 else 2097 function_section (current_function_decl); 2098 2099#ifdef ASM_OUTPUT_CASE_LABEL 2100 ASM_OUTPUT_CASE_LABEL (file, "L", CODE_LABEL_NUMBER (insn), 2101 NEXT_INSN (insn)); 2102#else | 2195 } 2196 } 2197#ifdef HAVE_cc0 2198 CC_STATUS_INIT; 2199 /* If this label is reached from only one place, set the condition 2200 codes from the instruction just before the branch. */ 2201 2202 /* Disabled because some insns set cc_status in the C output code --- 66 unchanged lines hidden (view full) --- 2269 } 2270 else 2271 function_section (current_function_decl); 2272 2273#ifdef ASM_OUTPUT_CASE_LABEL 2274 ASM_OUTPUT_CASE_LABEL (file, "L", CODE_LABEL_NUMBER (insn), 2275 NEXT_INSN (insn)); 2276#else |
2103 if (LABEL_ALTERNATE_NAME (insn)) 2104 ASM_OUTPUT_ALTERNATE_LABEL_NAME (file, insn); 2105 else 2106 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn)); | 2277 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn)); |
2107#endif 2108#endif 2109 break; 2110 } 2111 } | 2278#endif 2279#endif 2280 break; 2281 } 2282 } |
2112 if (LABEL_ALTERNATE_NAME (insn)) 2113 ASM_OUTPUT_ALTERNATE_LABEL_NAME (file, insn); | 2283 if (LABEL_ALT_ENTRY_P (insn)) 2284 output_alternate_entry_point (file, insn); |
2114 else 2115 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn)); 2116 break; 2117 2118 default: 2119 { 2120 rtx body = PATTERN (insn); 2121 int insn_code_number; --- 412 unchanged lines hidden (view full) --- 2534 /* Try to recognize the instruction. 2535 If successful, verify that the operands satisfy the 2536 constraints for the instruction. Crash if they don't, 2537 since `reload' should have changed them so that they do. */ 2538 2539 insn_code_number = recog_memoized (insn); 2540 cleanup_subreg_operands (insn); 2541 | 2285 else 2286 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn)); 2287 break; 2288 2289 default: 2290 { 2291 rtx body = PATTERN (insn); 2292 int insn_code_number; --- 412 unchanged lines hidden (view full) --- 2705 /* Try to recognize the instruction. 2706 If successful, verify that the operands satisfy the 2707 constraints for the instruction. Crash if they don't, 2708 since `reload' should have changed them so that they do. */ 2709 2710 insn_code_number = recog_memoized (insn); 2711 cleanup_subreg_operands (insn); 2712 |
2542 /* Dump the insn in the assembly for debugging. */ 2543 if (flag_dump_rtl_in_asm) 2544 { 2545 print_rtx_head = ASM_COMMENT_START; 2546 print_rtl_single (asm_out_file, insn); 2547 print_rtx_head = ""; 2548 } | 2713 /* Dump the insn in the assembly for debugging. */ 2714 if (flag_dump_rtl_in_asm) 2715 { 2716 print_rtx_head = ASM_COMMENT_START; 2717 print_rtl_single (asm_out_file, insn); 2718 print_rtx_head = ""; 2719 } |
2549 2550 if (! constrain_operands_cached (1)) 2551 fatal_insn_not_found (insn); 2552 2553 /* Some target machines need to prescan each insn before 2554 it is output. */ 2555 2556#ifdef FINAL_PRESCAN_INSN --- 193 unchanged lines hidden (view full) --- 2750 else if (GET_CODE (y) == REG) 2751 { 2752 unsigned int regno = subreg_hard_regno (x, 1); 2753 PUT_CODE (x, REG); 2754 REGNO (x) = regno; 2755 ORIGINAL_REGNO (x) = ORIGINAL_REGNO (y); 2756 /* This field has a different meaning for REGs and SUBREGs. Make 2757 sure to clear it! */ | 2720 2721 if (! constrain_operands_cached (1)) 2722 fatal_insn_not_found (insn); 2723 2724 /* Some target machines need to prescan each insn before 2725 it is output. */ 2726 2727#ifdef FINAL_PRESCAN_INSN --- 193 unchanged lines hidden (view full) --- 2921 else if (GET_CODE (y) == REG) 2922 { 2923 unsigned int regno = subreg_hard_regno (x, 1); 2924 PUT_CODE (x, REG); 2925 REGNO (x) = regno; 2926 ORIGINAL_REGNO (x) = ORIGINAL_REGNO (y); 2927 /* This field has a different meaning for REGs and SUBREGs. Make 2928 sure to clear it! */ |
2758 x->used = 0; | 2929 RTX_FLAG (x, used) = 0; |
2759 } 2760 else 2761 abort (); 2762 } 2763 2764 return *xp; 2765} 2766 --- 198 unchanged lines hidden (view full) --- 2965 char *new_message; 2966 const char *pfx_str; 2967 VA_OPEN (ap, msgid); 2968 VA_FIXEDARG (ap, const char *, msgid); 2969 2970 pfx_str = this_is_asm_operands ? _("invalid `asm': ") : "output_operand: "; 2971 asprintf (&fmt_string, "%s%s", pfx_str, _(msgid)); 2972 vasprintf (&new_message, fmt_string, ap); | 2930 } 2931 else 2932 abort (); 2933 } 2934 2935 return *xp; 2936} 2937 --- 198 unchanged lines hidden (view full) --- 3136 char *new_message; 3137 const char *pfx_str; 3138 VA_OPEN (ap, msgid); 3139 VA_FIXEDARG (ap, const char *, msgid); 3140 3141 pfx_str = this_is_asm_operands ? _("invalid `asm': ") : "output_operand: "; 3142 asprintf (&fmt_string, "%s%s", pfx_str, _(msgid)); 3143 vasprintf (&new_message, fmt_string, ap); |
2973 | 3144 |
2974 if (this_is_asm_operands) 2975 error_for_asm (this_is_asm_operands, "%s", new_message); 2976 else 2977 internal_error ("%s", new_message); 2978 2979 free (fmt_string); 2980 free (new_message); 2981 VA_CLOSE (ap); --- 781 unchanged lines hidden (view full) --- 3763 else 3764 { 3765 *first = GEN_INT (CONST_DOUBLE_LOW (value)); 3766 *second = GEN_INT (CONST_DOUBLE_HIGH (value)); 3767 } 3768 } 3769 else 3770 { | 3145 if (this_is_asm_operands) 3146 error_for_asm (this_is_asm_operands, "%s", new_message); 3147 else 3148 internal_error ("%s", new_message); 3149 3150 free (fmt_string); 3151 free (new_message); 3152 VA_CLOSE (ap); --- 781 unchanged lines hidden (view full) --- 3934 else 3935 { 3936 *first = GEN_INT (CONST_DOUBLE_LOW (value)); 3937 *second = GEN_INT (CONST_DOUBLE_HIGH (value)); 3938 } 3939 } 3940 else 3941 { |
3771#ifdef REAL_ARITHMETIC | |
3772 REAL_VALUE_TYPE r; 3773 long l[2]; 3774 REAL_VALUE_FROM_CONST_DOUBLE (r, value); 3775 3776 /* Note, this converts the REAL_VALUE_TYPE to the target's 3777 format, splits up the floating point double and outputs 3778 exactly 32 bits of it into each of l[0] and l[1] -- 3779 not necessarily BITS_PER_WORD bits. */ --- 12 unchanged lines hidden (view full) --- 3792 l[0] |= ((long) (-1) << 32); 3793 if (l[1] & ((long) 1 << 31)) 3794 l[1] |= ((long) (-1) << 32); 3795 } 3796#endif 3797 3798 *first = GEN_INT ((HOST_WIDE_INT) l[0]); 3799 *second = GEN_INT ((HOST_WIDE_INT) l[1]); | 3942 REAL_VALUE_TYPE r; 3943 long l[2]; 3944 REAL_VALUE_FROM_CONST_DOUBLE (r, value); 3945 3946 /* Note, this converts the REAL_VALUE_TYPE to the target's 3947 format, splits up the floating point double and outputs 3948 exactly 32 bits of it into each of l[0] and l[1] -- 3949 not necessarily BITS_PER_WORD bits. */ --- 12 unchanged lines hidden (view full) --- 3962 l[0] |= ((long) (-1) << 32); 3963 if (l[1] & ((long) 1 << 31)) 3964 l[1] |= ((long) (-1) << 32); 3965 } 3966#endif 3967 3968 *first = GEN_INT ((HOST_WIDE_INT) l[0]); 3969 *second = GEN_INT ((HOST_WIDE_INT) l[1]); |
3800#else 3801 if ((HOST_FLOAT_FORMAT != TARGET_FLOAT_FORMAT 3802 || HOST_BITS_PER_WIDE_INT != BITS_PER_WORD) 3803 && ! flag_pretend_float) 3804 abort (); 3805 3806 if ( 3807#ifdef HOST_WORDS_BIG_ENDIAN 3808 WORDS_BIG_ENDIAN 3809#else 3810 ! WORDS_BIG_ENDIAN 3811#endif 3812 ) 3813 { 3814 /* Host and target agree => no need to swap. */ 3815 *first = GEN_INT (CONST_DOUBLE_LOW (value)); 3816 *second = GEN_INT (CONST_DOUBLE_HIGH (value)); 3817 } 3818 else 3819 { 3820 *second = GEN_INT (CONST_DOUBLE_LOW (value)); 3821 *first = GEN_INT (CONST_DOUBLE_HIGH (value)); 3822 } 3823#endif /* no REAL_ARITHMETIC */ | |
3824 } 3825} 3826 3827/* Return nonzero if this function has no function calls. */ 3828 3829int 3830leaf_function_p () 3831{ --- 28 unchanged lines hidden (view full) --- 3860 && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == CALL_INSN 3861 && ! SIBLING_CALL_P (XVECEXP (PATTERN (insn), 0, 0))) 3862 return 0; 3863 } 3864 3865 return 1; 3866} 3867 | 3970 } 3971} 3972 3973/* Return nonzero if this function has no function calls. */ 3974 3975int 3976leaf_function_p () 3977{ --- 28 unchanged lines hidden (view full) --- 4006 && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == CALL_INSN 4007 && ! SIBLING_CALL_P (XVECEXP (PATTERN (insn), 0, 0))) 4008 return 0; 4009 } 4010 4011 return 1; 4012} 4013 |
3868/* Return 1 if branch is an forward branch. | 4014/* Return 1 if branch is a forward branch. |
3869 Uses insn_shuid array, so it works only in the final pass. May be used by 3870 output templates to customary add branch prediction hints. 3871 */ 3872int 3873final_forward_branch_p (insn) 3874 rtx insn; 3875{ 3876 int insn_id, label_id; --- 148 unchanged lines hidden --- | 4015 Uses insn_shuid array, so it works only in the final pass. May be used by 4016 output templates to customary add branch prediction hints. 4017 */ 4018int 4019final_forward_branch_p (insn) 4020 rtx insn; 4021{ 4022 int insn_id, label_id; --- 148 unchanged lines hidden --- |