This patch fixes -mno-call-main which did not work with LTO.
Instead of emitting .global __call_main + __call_main=0 in some
module, it uses a %{mno-call-main: --defsym __call_main=0} spec.
The problem with the old implementation is that avr_no_call_main_p was
set by cc1[plus] (in avr_insert_attributes) but used by lto1 (in
avr_file_end).
The new approach uses --defsym __call_main=0 in order to avoid link
fails due to multiple definitions of __call_main in *.o and lib<mcu>.a.
This is for trunk. If you agree, I would also packport it.
Johann
--
AVR: target/125194 - Make -mno-call-main work with -flto.
Instead of emitting .global __call_main + __call_main=0 in some module,
use a %{mno-call-main: --defsym __call_main=0} spec.
The problem with the old implementation is that avr_no_call_main_p was set
by cc1[plus] (in avr_insert_attributes) but used by lto1 (in avr_file_end).
The new approach uses --defsym __call_main=0 in order to avoid link
fails due to multiple definitions of __call_main in *.o and lib<mcu>.a.
PR target/125194
gcc/
* config/avr/avr.cc (avr_no_call_main_p): Remove variable...
(avr_file_end): ...and code that uses it.
(avr_insert_attributes): Same. Add "used" to main attributes
when -mno-call-main.
* config/avr/avr.opt (-mcall-main): Add Save option flag.
* config/avr/gen-avr-mmcu-specs.cc (print_mcu): Emit code
for link_no_call_main specs.
* config/avr/specs.h (LINK_SPEC): Add %(link_no_call_main).diff --git a/gcc/config/avr/avr.cc b/gcc/config/avr/avr.cc
index b0e9d9000e..25cb518b0f 100644
--- a/gcc/config/avr/avr.cc
+++ b/gcc/config/avr/avr.cc
@@ -249,9 +249,6 @@ bool avr_need_clear_bss_p = false;
bool avr_need_copy_data_p = false;
bool avr_has_rodata_p = false;
-/* To track if we satisfy __call_main from AVR-LibC. */
-bool avr_no_call_main_p = false;
-
/* Counts how often pass avr-fuse-add has been executed. Is is kept in
sync with cfun->machine->n_avr_fuse_add_executed and serves as an
insn condition for shift insn splitters. */
@@ -11906,7 +11903,9 @@ avr_insert_attributes (tree node, tree *attributes)
*attributes = tree_cons (get_identifier ("section"),
arg, *attributes);
}
- avr_no_call_main_p = true;
+ if (!lookup_attribute ("used", *attributes))
+ *attributes = tree_cons (get_identifier ("used"),
+ NULL_TREE, *attributes);
}
} // -mno-call-main
#endif // AVR-LibC
@@ -12467,15 +12466,6 @@ avr_file_end (void)
if (avr_need_clear_bss_p)
fputs (".global __do_clear_bss\n", asm_out_file);
-
- /* Don't let __call_main call main() and exit().
- Defining this symbol will keep the code from being pulled
- in from lib<mcu>.a as requested by AVR-LibC's gcrt1.S.
- We invoke main() by other means: putting it in .init9. */
-
- if (avr_no_call_main_p)
- fputs (".global __call_main\n"
- "__call_main = 0\n", asm_out_file);
}
diff --git a/gcc/config/avr/avr.opt b/gcc/config/avr/avr.opt
index 8bc2f5f173..56264ee6d1 100644
--- a/gcc/config/avr/avr.opt
+++ b/gcc/config/avr/avr.opt
@@ -39,7 +39,7 @@ Target RejectNegative Joined Var(avropt_n_flash) UInteger Init(-1)
This option is used internally. Set the number of 64 KiB flash segments.
mcall-main
-Target Var(avropt_call_main) UInteger Init(1)
+Target Var(avropt_call_main) UInteger Init(1) Save
Call main and exit (default).
mskip-bug
diff --git a/gcc/config/avr/gen-avr-mmcu-specs.cc b/gcc/config/avr/gen-avr-mmcu-specs.cc
index 42623d7e87..470d40538e 100644
--- a/gcc/config/avr/gen-avr-mmcu-specs.cc
+++ b/gcc/config/avr/gen-avr-mmcu-specs.cc
@@ -355,6 +355,8 @@ print_mcu (const avr_mcu_t *mcu, const McuInfo &mi)
fprintf (f, "*link_relax:\n\t%s\n\n", LINK_RELAX_SPEC);
+ fprintf (f, "*link_no_call_main:\n\t%s\n\n", "%{mno-call-main: --defsym __call_main=0}");
+
fprintf (f, "*link_arch:\n\t%s", link_arch_spec);
if (mi.is_device
&& rodata_pm_offset)
diff --git a/gcc/config/avr/specs.h b/gcc/config/avr/specs.h
index 4f71f8a657..1fca4a1d6e 100644
--- a/gcc/config/avr/specs.h
+++ b/gcc/config/avr/specs.h
@@ -67,6 +67,7 @@ along with GCC; see the file COPYING3. If not see
"%(link_relax) " \
"%(link_pmem_wrap) " \
"%(link_rodata_in_ram) " \
+ "%(link_no_call_main) " \
"%{shared:%eshared is not supported} "
#undef LIB_SPEC