There's no point calling for_each_rtx/FOR_EACH_SUBRTX on a LABEL_REF or SYMBOL_REF. We can just handle them directly instead.
gcc/ * varasm.c (compute_reloc_for_rtx_1): Take a const_rtx. Remove the pointer to the cumulative reloc value and return the value for this reloc instead. (compute_reloc_for_rtx): Take a const_rtx. Call compute_reloc_for_rtx_1 directly for SYMBOL_REF and LABEL_REF, avoiding any recursion. Use FOR_EACH_SUBRTX rather than for_each_rtx for the CONST case. Index: gcc/varasm.c =================================================================== --- gcc/varasm.c 2014-08-03 11:25:33.944191769 +0100 +++ gcc/varasm.c 2014-08-03 11:25:34.217194468 +0100 @@ -6484,44 +6484,43 @@ default_unique_section (tree decl, int r set_decl_section_name (decl, string); } -/* Like compute_reloc_for_constant, except for an RTX. The return value - is a mask for which bit 1 indicates a global relocation, and bit 0 - indicates a local relocation. */ +/* Subroutine of compute_reloc_for_rtx for leaf rtxes. */ static int -compute_reloc_for_rtx_1 (rtx *xp, void *data) +compute_reloc_for_rtx_1 (const_rtx x) { - int *preloc = (int *) data; - rtx x = *xp; - switch (GET_CODE (x)) { case SYMBOL_REF: - *preloc |= SYMBOL_REF_LOCAL_P (x) ? 1 : 2; - break; + return SYMBOL_REF_LOCAL_P (x) ? 1 : 2; case LABEL_REF: - *preloc |= 1; - break; + return 1; default: - break; + return 0; } - - return 0; } +/* Like compute_reloc_for_constant, except for an RTX. The return value + is a mask for which bit 1 indicates a global relocation, and bit 0 + indicates a local relocation. */ + static int -compute_reloc_for_rtx (rtx x) +compute_reloc_for_rtx (const_rtx x) { - int reloc; - switch (GET_CODE (x)) { - case CONST: case SYMBOL_REF: case LABEL_REF: - reloc = 0; - for_each_rtx (&x, compute_reloc_for_rtx_1, &reloc); - return reloc; + return compute_reloc_for_rtx_1 (x); + + case CONST: + { + int reloc = 0; + subrtx_iterator::array_type array; + FOR_EACH_SUBRTX (iter, array, x, ALL) + reloc |= compute_reloc_for_rtx_1 (*iter); + return reloc; + } default: return 0;