riscv_emit_attribute ();
}
+void
+riscv_file_end ()
+{
+ file_end_indicate_exec_stack ();
+ long GNU_PROPERTY_RISCV_FEATURE_1_AND = 0;
+ unsigned long feature_1_and = 0;
+
+ if (TARGET_ZICFISS)
+ feature_1_and |= 0x1 << 0;
+
+ if (TARGET_ZICFILP)
+ feature_1_and |= 0x1 << 1;
+
+ if (feature_1_and)
+ {
+ /* Generate .note.gnu.property section. */
+ switch_to_section (get_section (".note.gnu.property",
+ SECTION_NOTYPE, NULL));
+
+ /* The program property descriptor is aligned to 4 bytes in 32-bit
+ objects and 8 bytes in 64-bit objects. */
+ unsigned p2align = TARGET_64BIT ? 3 : 2;
+
+ fprintf (asm_out_file, "\t.p2align\t%u\n", p2align);
+ /* name length. */
+ fprintf (asm_out_file, "\t.long\t1f - 0f\n");
+ /* data length. */
+ fprintf (asm_out_file, "\t.long\t5f - 2f\n");
+ /* note type. */
+ fprintf (asm_out_file, "\t.long\t5\n");
+ fprintf (asm_out_file, "0:\n");
+ /* vendor name: "GNU". */
+ fprintf (asm_out_file, "\t.asciz\t\"GNU\"\n");
+ fprintf (asm_out_file, "1:\n");
+
+ /* pr_type. */
+ fprintf (asm_out_file, "\t.p2align\t3\n");
+ fprintf (asm_out_file, "2:\n");
+ fprintf (asm_out_file, "\t.long\t0xc0000000\n");
+ /* pr_datasz. */
+ fprintf (asm_out_file, "\t.long\t4f - 3f\n");
+ fprintf (asm_out_file, "3:\n");
+ /* zicfiss, zicfilp. */
+ fprintf (asm_out_file, "\t.long\t%x\n", feature_1_and);
+ fprintf (asm_out_file, "4:\n");
+ fprintf (asm_out_file, "\t.p2align\t%u\n", p2align);
+ fprintf (asm_out_file, "5:\n");
+ }
+}
+
/* Implement TARGET_ASM_OUTPUT_MI_THUNK. Generate rtl rather than asm text
in order to avoid duplicating too much logic from elsewhere. */
#undef TARGET_ASM_FILE_START_FILE_DIRECTIVE
#define TARGET_ASM_FILE_START_FILE_DIRECTIVE true
#undef TARGET_ASM_FILE_END
-#define TARGET_ASM_FILE_END file_end_indicate_exec_stack
+#define TARGET_ASM_FILE_END riscv_file_end
#undef TARGET_EXPAND_BUILTIN_VA_START
#define TARGET_EXPAND_BUILTIN_VA_START riscv_va_start
#define FUNC_SIZE(X) .size X,.-X
#define FUNC_BEGIN(X) \
+ .align 2; \
.globl X; \
FUNC_TYPE (X); \
-X:
+X: \
+ LPAD
#define FUNC_END(X) \
FUNC_SIZE(X)
#define HIDDEN_JUMPTARGET(X) CONCAT1(__hidden_, X)
#define HIDDEN_DEF(X) FUNC_ALIAS(HIDDEN_JUMPTARGET(X), X); \
.hidden HIDDEN_JUMPTARGET(X)
+
+/* GNU_PROPERTY_RISCV64_* macros from elf.h for use in asm code. */
+#define FEATURE_1_AND 0xc0000000
+#define FEATURE_1_FCFI 1
+#define FEATURE_1_BCFI 2
+
+/* Add a NT_GNU_PROPERTY_TYPE_0 note. */
+#if __riscv_xlen == 32
+# define GNU_PROPERTY(type, value) \
+ .section .note.gnu.property, "a"; \
+ .p2align 2; \
+ .word 4; \
+ .word 12; \
+ .word 5; \
+ .asciz "GNU"; \
+ .word type; \
+ .word 4; \
+ .word value; \
+ .text
+#else
+# define GNU_PROPERTY(type, value) \
+ .section .note.gnu.property, "a"; \
+ .p2align 3; \
+ .word 4; \
+ .word 16; \
+ .word 5; \
+ .asciz "GNU"; \
+ .word type; \
+ .word 4; \
+ .word value; \
+ .word 0; \
+ .text
+#endif
+
+/* Add GNU property note with the supported features to all asm code
+ where sysdep.h is included. */
+#undef __VALUE_FOR_FEATURE_1_AND
+#if defined (__riscv_zicfilp) || defined (__riscv_zicfiss)
+# if defined (__riscv_zicfilp)
+# if defined (__riscv_zicfiss)
+# define __VALUE_FOR_FEATURE_1_AND 0x3
+# else
+# define __VALUE_FOR_FEATURE_1_AND 0x1
+# endif
+# else
+# if defined (__riscv_zicfiss)
+# define __VALUE_FOR_FEATURE_1_AND 0x2
+# else
+# error "What?"
+# endif
+# endif
+#endif
+
+#if defined (__VALUE_FOR_FEATURE_1_AND)
+GNU_PROPERTY (FEATURE_1_AND, __VALUE_FOR_FEATURE_1_AND)
+#endif
+#undef __VALUE_FOR_FEATURE_1_AND
+
+#ifdef __riscv_zicfilp
+# define SET_LPAD lui t2, 0
+# define LPAD lpad 0
+#else
+# define SET_LPAD
+# define LPAD
+#endif