Mercurial > hg > CbC > CbC_gcc
comparison gcc/config/score/score3.c @ 55:77e2b8dfacca gcc-4.4.5
update it from 4.4.3 to 4.5.0
author | ryoma <e075725@ie.u-ryukyu.ac.jp> |
---|---|
date | Fri, 12 Feb 2010 23:39:51 +0900 |
parents | a06113de4d67 |
children | b7f97abdc517 |
comparison
equal
deleted
inserted
replaced
52:c156f1bd5cd9 | 55:77e2b8dfacca |
---|---|
52 #include "df.h" | 52 #include "df.h" |
53 | 53 |
54 #define BITSET_P(VALUE, BIT) (((VALUE) & (1L << (BIT))) != 0) | 54 #define BITSET_P(VALUE, BIT) (((VALUE) & (1L << (BIT))) != 0) |
55 #define INS_BUF_SZ 128 | 55 #define INS_BUF_SZ 128 |
56 | 56 |
57 /* Define the information needed to generate branch insns. This is | |
58 stored from the compare operation. */ | |
59 extern rtx cmp_op0, cmp_op1; | |
60 extern enum reg_class score_char_to_class[256]; | 57 extern enum reg_class score_char_to_class[256]; |
61 | 58 |
62 static int score3_sdata_max; | 59 static int score3_sdata_max; |
63 static char score3_ins[INS_BUF_SZ + 8]; | 60 static char score3_ins[INS_BUF_SZ + 8]; |
64 | 61 |
381 split_all_insns_noflow (); | 378 split_all_insns_noflow (); |
382 shorten_branches (insn); | 379 shorten_branches (insn); |
383 final_start_function (insn, file, 1); | 380 final_start_function (insn, file, 1); |
384 final (insn, file, 1); | 381 final (insn, file, 1); |
385 final_end_function (); | 382 final_end_function (); |
386 free_after_compilation (cfun); | |
387 | 383 |
388 /* Clean up the vars set above. Note that final_end_function resets | 384 /* Clean up the vars set above. Note that final_end_function resets |
389 the global pointer for us. */ | 385 the global pointer for us. */ |
390 reload_completed = 0; | 386 reload_completed = 0; |
391 } | 387 } |
412 rtx high = score3_force_temporary (temp, | 408 rtx high = score3_force_temporary (temp, |
413 gen_rtx_HIGH (Pmode, copy_rtx (addr))); | 409 gen_rtx_HIGH (Pmode, copy_rtx (addr))); |
414 return gen_rtx_LO_SUM (Pmode, high, addr); | 410 return gen_rtx_LO_SUM (Pmode, high, addr); |
415 } | 411 } |
416 | 412 |
417 /* This function is used to implement LEGITIMIZE_ADDRESS. If *XLOC can | 413 /* This function is used to implement LEGITIMIZE_ADDRESS. If X can |
418 be legitimized in a way that the generic machinery might not expect, | 414 be legitimized in a way that the generic machinery might not expect, |
419 put the new address in *XLOC and return true. */ | 415 return the new address. */ |
420 int | 416 rtx |
421 score3_legitimize_address (rtx *xloc) | 417 score3_legitimize_address (rtx x) |
422 { | 418 { |
423 enum score_symbol_type symbol_type; | 419 enum score_symbol_type symbol_type; |
424 | 420 |
425 if (score3_symbolic_constant_p (*xloc, &symbol_type) | 421 if (score3_symbolic_constant_p (x, &symbol_type) |
426 && symbol_type == SYMBOL_GENERAL) | 422 && symbol_type == SYMBOL_GENERAL) |
427 { | 423 return score3_split_symbol (0, x); |
428 *xloc = score3_split_symbol (0, *xloc); | 424 |
429 return 1; | 425 if (GET_CODE (x) == PLUS |
430 } | 426 && GET_CODE (XEXP (x, 1)) == CONST_INT) |
431 | 427 { |
432 if (GET_CODE (*xloc) == PLUS | 428 rtx reg = XEXP (x, 0); |
433 && GET_CODE (XEXP (*xloc, 1)) == CONST_INT) | |
434 { | |
435 rtx reg = XEXP (*xloc, 0); | |
436 if (!score3_valid_base_register_p (reg, 0)) | 429 if (!score3_valid_base_register_p (reg, 0)) |
437 reg = copy_to_mode_reg (Pmode, reg); | 430 reg = copy_to_mode_reg (Pmode, reg); |
438 *xloc = score3_add_offset (reg, INTVAL (XEXP (*xloc, 1))); | 431 return score3_add_offset (reg, INTVAL (XEXP (x, 1))); |
439 return 1; | 432 } |
440 } | 433 |
441 return 0; | 434 return x; |
442 } | 435 } |
443 | 436 |
444 /* Fill INFO with information about a single argument. CUM is the | 437 /* Fill INFO with information about a single argument. CUM is the |
445 cumulative state for earlier arguments. MODE is the mode of this | 438 cumulative state for earlier arguments. MODE is the mode of this |
446 argument and TYPE is its type (if known). NAMED is true if this | 439 argument and TYPE is its type (if known). NAMED is true if this |
863 | 856 |
864 /* Implement FUNCTION_VALUE and LIBCALL_VALUE. For normal calls, | 857 /* Implement FUNCTION_VALUE and LIBCALL_VALUE. For normal calls, |
865 VALTYPE is the return type and MODE is VOIDmode. For libcalls, | 858 VALTYPE is the return type and MODE is VOIDmode. For libcalls, |
866 VALTYPE is null and MODE is the mode of the return value. */ | 859 VALTYPE is null and MODE is the mode of the return value. */ |
867 rtx | 860 rtx |
868 score3_function_value (tree valtype, tree func ATTRIBUTE_UNUSED, | 861 score3_function_value (tree valtype, tree func, enum machine_mode mode) |
869 enum machine_mode mode) | |
870 { | 862 { |
871 if (valtype) | 863 if (valtype) |
872 { | 864 { |
873 int unsignedp; | 865 int unsignedp; |
874 mode = TYPE_MODE (valtype); | 866 mode = TYPE_MODE (valtype); |
875 unsignedp = TYPE_UNSIGNED (valtype); | 867 unsignedp = TYPE_UNSIGNED (valtype); |
876 mode = promote_mode (valtype, mode, &unsignedp, 1); | 868 mode = promote_function_mode (valtype, mode, &unsignedp, func, 1); |
877 } | 869 } |
878 return gen_rtx_REG (mode, RT_REGNUM); | 870 return gen_rtx_REG (mode, RT_REGNUM); |
879 } | 871 } |
880 | 872 |
881 /* Implement INITIALIZE_TRAMPOLINE macro. */ | 873 /* Implement TARGET_ASM_TRAMPOLINE_TEMPLATE. */ |
874 | |
882 void | 875 void |
883 score3_initialize_trampoline (rtx ADDR, rtx FUNC, rtx CHAIN) | 876 score3_asm_trampoline_template (FILE *f) |
877 { | |
878 fprintf (f, "\t.set r1\n"); | |
879 fprintf (f, "\tmv! r31, r3\n"); | |
880 fprintf (f, "\tnop!\n"); | |
881 fprintf (f, "\tbl nextinsn\n"); | |
882 fprintf (f, "nextinsn:\n"); | |
883 fprintf (f, "\tlw! r1, [r3, 6*4-8]\n"); | |
884 fprintf (f, "\tnop!\n"); | |
885 fprintf (f, "\tlw r23, [r3, 6*4-4]\n"); | |
886 fprintf (f, "\tmv! r3, r31\n"); | |
887 fprintf (f, "\tnop!\n"); | |
888 fprintf (f, "\tbr! r1\n"); | |
889 fprintf (f, "\tnop!\n"); | |
890 fprintf (f, "\t.set nor1\n"); | |
891 } | |
892 | |
893 /* Implement TARGET_TRAMPOLINE_INIT. */ | |
894 void | |
895 score3_trampoline_init (rtx m_tramp, tree fndecl, rtx chain_value) | |
884 { | 896 { |
885 #define FFCACHE "_flush_cache" | 897 #define FFCACHE "_flush_cache" |
886 #define CODE_SIZE (TRAMPOLINE_INSNS * UNITS_PER_WORD) | 898 #define CODE_SIZE (TRAMPOLINE_INSNS * UNITS_PER_WORD) |
887 | 899 |
888 rtx pfunc, pchain; | 900 rtx fnaddr = XEXP (DECL_RTL (fndecl), 0); |
889 | 901 rtx addr = XEXP (m_tramp, 0); |
890 pfunc = plus_constant (ADDR, CODE_SIZE); | 902 rtx mem; |
891 pchain = plus_constant (ADDR, CODE_SIZE + GET_MODE_SIZE (SImode)); | 903 |
892 | 904 emit_block_move (m_tramp, assemble_trampoline_template (), |
893 emit_move_insn (gen_rtx_MEM (SImode, pfunc), FUNC); | 905 GEN_INT (TRAMPOLINE_SIZE), BLOCK_OP_NORMAL); |
894 emit_move_insn (gen_rtx_MEM (SImode, pchain), CHAIN); | 906 |
907 mem = adjust_address (m_tramp, SImode, CODE_SIZE); | |
908 emit_move_insn (mem, fnaddr); | |
909 mem = adjust_address (m_tramp, SImode, CODE_SIZE + GET_MODE_SIZE (SImode)); | |
910 emit_move_insn (mem, chain_value); | |
911 | |
895 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, FFCACHE), | 912 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, FFCACHE), |
896 0, VOIDmode, 2, | 913 0, VOIDmode, 2, |
897 ADDR, Pmode, | 914 addr, Pmode, |
898 GEN_INT (TRAMPOLINE_SIZE), SImode); | 915 GEN_INT (TRAMPOLINE_SIZE), SImode); |
899 #undef FFCACHE | 916 #undef FFCACHE |
900 #undef CODE_SIZE | 917 #undef CODE_SIZE |
901 } | 918 } |
902 | 919 |
914 || regno == FRAME_POINTER_REGNUM) | 931 || regno == FRAME_POINTER_REGNUM) |
915 return 1; | 932 return 1; |
916 return GP_REG_P (regno); | 933 return GP_REG_P (regno); |
917 } | 934 } |
918 | 935 |
919 /* Implement GO_IF_LEGITIMATE_ADDRESS macro. */ | 936 /* Implement TARGET_LEGITIMATE_ADDRESS_P macro. */ |
920 int | 937 bool |
921 score3_address_p (enum machine_mode mode, rtx x, int strict) | 938 score3_legitimate_address_p (enum machine_mode mode, rtx x, bool strict) |
922 { | 939 { |
923 struct score3_address_info addr; | 940 struct score3_address_info addr; |
924 | 941 |
925 return score3_classify_address (&addr, mode, x, strict); | 942 return score3_classify_address (&addr, mode, x, strict); |
926 } | 943 } |
1648 | 1665 |
1649 if (!sibcall_p) | 1666 if (!sibcall_p) |
1650 emit_jump_insn (gen_return_internal_score3 (gen_rtx_REG (Pmode, RA_REGNUM))); | 1667 emit_jump_insn (gen_return_internal_score3 (gen_rtx_REG (Pmode, RA_REGNUM))); |
1651 } | 1668 } |
1652 | 1669 |
1653 void | |
1654 score3_gen_cmp (enum machine_mode mode) | |
1655 { | |
1656 emit_insn (gen_rtx_SET (VOIDmode, gen_rtx_REG (mode, CC_REGNUM), | |
1657 gen_rtx_COMPARE (mode, cmp_op0, cmp_op1))); | |
1658 } | |
1659 | |
1660 /* Return true if X is a symbolic constant that can be calculated in | 1670 /* Return true if X is a symbolic constant that can be calculated in |
1661 the same way as a bare symbol. If it is, store the type of the | 1671 the same way as a bare symbol. If it is, store the type of the |
1662 symbol in *SYMBOL_TYPE. */ | 1672 symbol in *SYMBOL_TYPE. */ |
1663 int | 1673 int |
1664 score3_symbolic_constant_p (rtx x, enum score_symbol_type *symbol_type) | 1674 score3_symbolic_constant_p (rtx x, enum score_symbol_type *symbol_type) |
1693 { | 1703 { |
1694 enum machine_mode mode; | 1704 enum machine_mode mode; |
1695 | 1705 |
1696 mode = score3_select_cc_mode (GET_CODE (ops[1]), ops[2], ops[3]); | 1706 mode = score3_select_cc_mode (GET_CODE (ops[1]), ops[2], ops[3]); |
1697 emit_insn (gen_rtx_SET (VOIDmode, gen_rtx_REG (mode, CC_REGNUM), | 1707 emit_insn (gen_rtx_SET (VOIDmode, gen_rtx_REG (mode, CC_REGNUM), |
1698 gen_rtx_COMPARE (mode, cmp_op0, cmp_op1))); | 1708 gen_rtx_COMPARE (mode, XEXP (ops[1], 0), |
1709 XEXP (ops[1], 1)))); | |
1699 } | 1710 } |
1700 | 1711 |
1701 /* Call and sibcall pattern all need call this function. */ | 1712 /* Call and sibcall pattern all need call this function. */ |
1702 void | 1713 void |
1703 score3_call (rtx *ops, bool sib) | 1714 score3_call (rtx *ops, bool sib) |