Merge lp:~ams-codesourcery/gcc-linaro/cs-merge-20110413 into lp:gcc-linaro/4.5
- cs-merge-20110413
- Merge into 4.5
Status: | Rejected |
---|---|
Rejected by: | Loïc Minier |
Proposed branch: | lp:~ams-codesourcery/gcc-linaro/cs-merge-20110413 |
Merge into: | lp:gcc-linaro/4.5 |
Diff against target: |
1208 lines (+841/-83) 16 files modified
ChangeLog.linaro (+125/-0) gcc/combine.c (+15/-1) gcc/config/arm/arm.c (+356/-5) gcc/config/arm/arm.md (+203/-31) gcc/config/arm/arm.opt (+4/-0) gcc/config/arm/unwind-arm.c (+30/-10) gcc/expmed.c (+2/-2) gcc/final.c (+6/-0) gcc/ifcvt.c (+4/-0) gcc/ipa-pure-const.c (+8/-1) gcc/testsuite/gcc.c-torture/compile/20110322-1.c (+22/-0) gcc/testsuite/gcc.dg/pr47763.c (+9/-0) gcc/testsuite/lib/target-supports.exp (+3/-2) gcc/tree-ssa-copyrename.c (+12/-0) gcc/web.c (+11/-1) libstdc++-v3/libsupc++/eh_arm.cc (+31/-30) |
To merge this branch: | bzr merge lp:~ams-codesourcery/gcc-linaro/cs-merge-20110413 |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Andrew Stubbs (community) | Needs Resubmitting | ||
Review via email:
|
Commit message
Description of the change
Latest batch of merges from Sourcery G++.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Ira Rosen (irar) wrote : | # |
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Linaro Toolchain Builder (cbuild) wrote : | # |
cbuild has taken a snapshot of this branch at r99502 and queued it for build.
The snapshot is available at:
http://
and will be built on the following builders:
a8-builder a9-builder i686 x86_64
You can track the build queue at:
http://
cbuild-snapshot: gcc-linaro-
cbuild-ancestor: lp:gcc-linaro+bzr99492
cbuild-state: check
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Ramana Radhakrishnan (ramana) wrote : | # |
Since this is a large feature branch review is a bit harder in this case.
99493 - OK
99494 - OK
99495 - OK - has gone upstream .
99496 - OK - could go upstream into FSF 4.5 branch if possible.
99497 - OK
99498 - OK
99499 - OK
OK if no regressions.
99500 - OK - Looks sensible but would like to do a round of benchmarking but can go in for sure.
99501 - Not fully reviewed. A first cut review - I *think* this is a sensible approach given that we can't just blanket remove SLOW_UNALIGNED_
99502 - Ambivalent - Not fully reviewed . A comment is we probably want some testcases for this and it looks overall like a nice improvement.Should we take this at the start of the next release, so that it gets baked for 3 weeks more than just a week before the release ?
cheers
Ramana
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Ramana Radhakrishnan (ramana) wrote : | # |
As long as we can get bzr to individually commit these so that any performance archaelogy has a chance to individually benchmark each of these patches I think these are ok.
99493 - OK
99494 - OK
99495 - OK - has gone upstream .
99496 - OK - could go upstream into FSF 4.5 branch if possible.
99497 - OK
99498 - OK
Can we commit 99500, 99501 , 99502 as individual patches and do the merge just after the April release ?
Could we link 99499 only to the bug fix rather than one commit into gcc-linaro/4.5 which is the bug fix ?
Sorry I just think we should then end up having a merge request per feature or a merge request for a bug fix rather than one gigantic merge. I'm still not a power user of bzr so not totally sure if we can do all that's needed here.
Ramana
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Linaro Toolchain Builder (cbuild) wrote : | # |
cbuild successfully built this on i686-lucid-
The build results are available at:
http://
The test suite results changed compared to the branch point lp:gcc-linaro+bzr99492:
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+...
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Linaro Toolchain Builder (cbuild) wrote : | # |
cbuild successfully built this on x86_64-
The build results are available at:
http://
The test suite results changed compared to the branch point lp:gcc-linaro+bzr99492:
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
I'm happy with merging all of the correctness fixes. Please leave the new features such as unaligned memcpy() out until after this release. I want to have time to try them with Python, SPEC, and EEMBC and have time to correct any problems.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Andrew Stubbs (ams-codesourcery) wrote : | # |
> Sorry I just think we should then end up having a merge request per feature or
> a merge request for a bug fix rather than one gigantic merge. I'm still not a
> power user of bzr so not totally sure if we can do all that's needed here.
In the past we've treated CS patches as pre-reviewed (which they are), and committed them directly to lp:gcc-linaro. I've only really changed this as a means to get the extra testing before I check in (I'm going to have to check the gcc.dg/
That said, extra review is always valuable. :)
I deliberately chose to submit them as a batch, because if I had submitted them individually I doubt we'd have had all the test results in time, and anyway some depend on others, at least textually. I did/do intend to do a rebase and push, rather than a merge, so as not to flatten the history. I can leave out some revisions if they're broken, or reviewers don't like them.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Loïc Minier (lool) wrote : | # |
In any case, the history wont be flattened if you do a merge; it will be shown as a merge in the bzr history and all the individual original revisions will still be accessible; see bzr log -n0 or --include-merges to see them (or use bzr vis).
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Linaro Toolchain Builder (cbuild) wrote : | # |
cbuild successfully built this on armv7l-
The build results are available at:
http://
The test suite results changed compared to the branch point lp:gcc-linaro+bzr99492:
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
-PASS: gcc.dg/
-PASS: gcc.dg/
-FAIL: gcc.dg/
-FAIL: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-FAIL: gcc.dg/
-FAIL: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Linaro Toolchain Builder (cbuild) wrote : | # |
cbuild successfully built this on armv7l-
The build results are available at:
http://
The test suite results changed compared to the branch point lp:gcc-linaro+bzr99492:
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
+PASS: gcc.c-torture/
-FAIL: gcc.c-torture/
+PASS: gcc.c-torture/
-UNRESOLVED: gcc.dg/
+PASS: gcc.dg/
-FAIL: gcc.dg/
+PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-FAIL: gcc.dg/
-FAIL: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
+UNSUPPORTED: gcc.dg/
-PASS: gcc.dg/
-PASS: gcc.dg/
-FAIL: gcc.dg/
-FAIL: gcc.dg/
-PASS: gcc.dg/
-...
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
I'd prefer to keep the new features for the next release. It's not far away and it'll give us some more breathing room.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Andrew Stubbs (ams-codesourcery) wrote : | # |
This is now merged as far as 99498.
I'll resubmit the rest later.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
For reference, I've gone through the patches and seen what's where. See:
https:/
or in text:
======== ========= ======== ========== ========== =======
Revision Bug In trunk In our 4.5 In our 4.6 Notes
======== ========= ======== ========== ========== =======
99493 PR45052 162528 Y (twice) Y
99494 175641 99498 N ABI conformance
99495 PR47763 170422 N N Dhrystone improvement
99496 PR47427 169226 N Y ICE
99497 171304 B N Bug
99498 N N N Bad debug info
99499 LP:736439 171840 N N Shrinkwrap
99500 N N N Needs benchmarking
99501 Unaligned; obsolete
99502 Unaligned; obsolete
======== ========= ======== ========== ========== =======
Based on this we should backport 99493, 99494, 99495, 99496, 99497, 99499, and 99500.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
(well, except 99493 and 99496 which are already in our 4.6...)
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
99495 was picked up via the 4.6 release branch.
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Michael Hope (michaelh1) wrote : | # |
I've created merge requests for 99494, 99497, 99499 (4.6 + 4.5), and 99500.
Unmerged revisions
- 99502. By Andrew Stubbs
-
Add unaligned support for built-in memcpy.
Merged from Sourcery G++
- 99501. By Andrew Stubbs
-
Add support for unaligned loads/stores.
Merged from Sourcery G++
- 99500. By Andrew Stubbs
-
Fix performance regression when using NEON.
Merged from Sourcery G++
- 99499. By Andrew Stubbs
-
Fix shrink wrapping bug.
Merged from Sourcery G++
- 99498. By Andrew Stubbs
-
Fix a bug that generated bad debug info.
Merged from Sourcery G++
- 99497. By Andrew Stubbs
-
Fix bug in__builtin_
isgreaterequal. Merged from Sourcery G++
(Backport from FSF)
- 99496. By Andrew Stubbs
-
Fix internal compiler errors.
GCC Bugzilla #47427 & #47428.
Merged from Sourcery G++
(Backport from FSF)
- 99495. By Andrew Stubbs
-
Fix a performance regression in Dhrystone.
Merged from Sourcery SG++.
- 99494. By Andrew Stubbs
-
Fix an ABI conformance issue that affected armcc interoperability.
Merged from Sourcery G++.
- 99493. By Andrew Stubbs
-
Fix a bug in which "volatile" keyword could be ignored.
Merged from Sourcery G++.
(Backport from FSF)
Preview Diff
1 | === modified file 'ChangeLog.linaro' | |||
2 | --- ChangeLog.linaro 2011-04-11 09:52:39 +0000 | |||
3 | +++ ChangeLog.linaro 2011-04-13 13:28:18 +0000 | |||
4 | @@ -1,3 +1,128 @@ | |||
5 | 1 | 2011-04-01 Julian Brown <julian@codesourcery.com> | ||
6 | 2 | |||
7 | 3 | Issue #4220 | ||
8 | 4 | |||
9 | 5 | gcc/ | ||
10 | 6 | * config/arm/arm.c (arm_block_move_unaligned_straight) | ||
11 | 7 | (arm_adjust_block_mem, arm_block_move_unaligned_loop) | ||
12 | 8 | (arm_movmemqi_unaligned): New. | ||
13 | 9 | (arm_gen_movmemqi): Support unaligned block copies. | ||
14 | 10 | |||
15 | 11 | 2011-04-01 Julian Brown <julian@codesourcery.com> | ||
16 | 12 | |||
17 | 13 | Issue #4220 | ||
18 | 14 | |||
19 | 15 | gcc/ | ||
20 | 16 | * config/arm/arm.c (arm_override_options): Add unaligned_access | ||
21 | 17 | support. | ||
22 | 18 | * config/arm/arm.md (UNSPEC_UNALIGNED_LOAD) | ||
23 | 19 | (UNSPEC_UNALIGNED_STORE): Add constants for unspecs. | ||
24 | 20 | (insv, extzv): Add unaligned-access support. | ||
25 | 21 | (extv): Change to expander. Likewise. | ||
26 | 22 | (unaligned_loadsi, unaligned_loadhis, unaligned_loadhiu) | ||
27 | 23 | (unaligned_storesi, unaligned_storehi): New. | ||
28 | 24 | (*extv_reg): New (previous extv implementation). | ||
29 | 25 | * config/arm/arm.opt (munaligned_access): Add option. | ||
30 | 26 | * expmed.c (store_bit_field_1): Don't tweak bitfield numbering for | ||
31 | 27 | memory locations if BITS_BIG_ENDIAN != BYTES_BIG_ENDIAN. | ||
32 | 28 | (extract_bit_field_1): Likewise. | ||
33 | 29 | |||
34 | 30 | 2011-04-01 Julian Brown <julian@codesourcery.com> | ||
35 | 31 | |||
36 | 32 | Issue #6223 | ||
37 | 33 | |||
38 | 34 | gcc/ | ||
39 | 35 | * config/arm/arm.c (arm_vector_alignment_reachable): Don't use | ||
40 | 36 | peeling for alignment for NEON. | ||
41 | 37 | |||
42 | 38 | gcc/testsuite/ | ||
43 | 39 | * lib/target-supports.exp | ||
44 | 40 | (check_effective_target_vector_alignment_reachable): Not true for | ||
45 | 41 | ARM NEON. | ||
46 | 42 | |||
47 | 43 | 2011-03-28 Bernd Schmidt <bernds@codesourcery.com> | ||
48 | 44 | |||
49 | 45 | gcc/ | ||
50 | 46 | * ifcvt.c (cond_exec_process_insns): Don't convert the function | ||
51 | 47 | prologue. | ||
52 | 48 | |||
53 | 49 | gcc/testsuite/ | ||
54 | 50 | * gcc.c-torture/compile/20110322-1.c: New test. | ||
55 | 51 | |||
56 | 52 | 2011-03-28 Paul Brook <paul@codesourcery.com> | ||
57 | 53 | Daniel Jacobowitz <dan@codesourcery.com> | ||
58 | 54 | |||
59 | 55 | Issue #3772 | ||
60 | 56 | gcc/ | ||
61 | 57 | * final.c (notice_source_line): Ignore zero length instructions. | ||
62 | 58 | |||
63 | 59 | 2011-03-22 Sandra Loosemore <sandra@codesourcery.com> | ||
64 | 60 | |||
65 | 61 | Issue #10483 | ||
66 | 62 | |||
67 | 63 | gcc/ | ||
68 | 64 | Backport from mainline: | ||
69 | 65 | |||
70 | 66 | 2011-03-22 Eric Botcazou <ebotcazou@adacore.com> | ||
71 | 67 | |||
72 | 68 | * combine.c (simplify_set): Try harder to find the best CC mode when | ||
73 | 69 | simplifying a nested COMPARE on the RHS. | ||
74 | 70 | |||
75 | 71 | 2011-03-17 Janis Johnson <janisjo@codesourcery.com> | ||
76 | 72 | |||
77 | 73 | Backport from FSF mainline: | ||
78 | 74 | 2011-01-25 Jakub Jelinek <jakub@redhat.com> | ||
79 | 75 | |||
80 | 76 | PR tree-optimization/47427 | ||
81 | 77 | PR tree-optimization/47428 | ||
82 | 78 | * tree-ssa-copyrename.c (copy_rename_partition_coalesce): Don't | ||
83 | 79 | coalesce if the new root var would be TREE_READONLY. | ||
84 | 80 | |||
85 | 81 | 2011-02-23 Jie Zhang <jie@codesourcery.com> | ||
86 | 82 | |||
87 | 83 | Issue #10134 | ||
88 | 84 | |||
89 | 85 | Backport from mainline | ||
90 | 86 | |||
91 | 87 | gcc/ | ||
92 | 88 | 2011-02-23 Jie Zhang <jie@codesourcery.com> | ||
93 | 89 | |||
94 | 90 | PR rtl-optimization/47763 | ||
95 | 91 | * web.c (web_main): Ignore naked clobber when replacing register. | ||
96 | 92 | |||
97 | 93 | gcc/testsuite/ | ||
98 | 94 | 2011-02-23 Jie Zhang <jie@codesourcery.com> | ||
99 | 95 | |||
100 | 96 | PR rtl-optimization/47763 | ||
101 | 97 | * gcc.dg/pr47763.c: New test. | ||
102 | 98 | |||
103 | 99 | 2011-02-16 Nathan Sidwell <nathan@codesourcery.com> | ||
104 | 100 | |||
105 | 101 | Issue #10439 | ||
106 | 102 | gcc/ | ||
107 | 103 | * config/arm/unwind-arm.c (enum __cxa_type_match_result): New. | ||
108 | 104 | (cxa_type_match): Correct declaration. | ||
109 | 105 | (__gnu_unwind_pr_common): Reconstruct | ||
110 | 106 | additional indirection when __cxa_type_match returns | ||
111 | 107 | succeeded_with_ptr_to_base. | ||
112 | 108 | |||
113 | 109 | libstdc++/ | ||
114 | 110 | * libsupc++/eh_arm.c (__cxa_type_match): Construct address of | ||
115 | 111 | thrown object here. Return succeded_with_ptr_to_base for all | ||
116 | 112 | pointer cases. | ||
117 | 113 | |||
118 | 114 | 2011-02-14 Kwok Cheung Yeung <kcy@codesourcery.com> | ||
119 | 115 | |||
120 | 116 | Issue #10417 | ||
121 | 117 | |||
122 | 118 | Backport from mainline | ||
123 | 119 | |||
124 | 120 | gcc/ | ||
125 | 121 | 2010-07-31 Richard Guenther <rguenther@suse.de> | ||
126 | 122 | |||
127 | 123 | PR tree-optimization/45052 | ||
128 | 124 | * ipa-pure-const.c (check_stmt): Check volatileness. | ||
129 | 125 | |||
130 | 1 | 2011-04-10 Michael Hope <michael.hope@linaro.org> | 126 | 2011-04-10 Michael Hope <michael.hope@linaro.org> |
131 | 2 | 127 | ||
132 | 3 | gcc/ | 128 | gcc/ |
133 | 4 | 129 | ||
134 | === modified file 'gcc/combine.c' | |||
135 | --- gcc/combine.c 2011-01-06 11:02:44 +0000 | |||
136 | +++ gcc/combine.c 2011-04-13 13:28:18 +0000 | |||
137 | @@ -5966,10 +5966,18 @@ | |||
138 | 5966 | enum rtx_code new_code; | 5966 | enum rtx_code new_code; |
139 | 5967 | rtx op0, op1, tmp; | 5967 | rtx op0, op1, tmp; |
140 | 5968 | int other_changed = 0; | 5968 | int other_changed = 0; |
141 | 5969 | rtx inner_compare = NULL_RTX; | ||
142 | 5969 | enum machine_mode compare_mode = GET_MODE (dest); | 5970 | enum machine_mode compare_mode = GET_MODE (dest); |
143 | 5970 | 5971 | ||
144 | 5971 | if (GET_CODE (src) == COMPARE) | 5972 | if (GET_CODE (src) == COMPARE) |
146 | 5972 | op0 = XEXP (src, 0), op1 = XEXP (src, 1); | 5973 | { |
147 | 5974 | op0 = XEXP (src, 0), op1 = XEXP (src, 1); | ||
148 | 5975 | if (GET_CODE (op0) == COMPARE && op1 == const0_rtx) | ||
149 | 5976 | { | ||
150 | 5977 | inner_compare = op0; | ||
151 | 5978 | op0 = XEXP (inner_compare, 0), op1 = XEXP (inner_compare, 1); | ||
152 | 5979 | } | ||
153 | 5980 | } | ||
154 | 5973 | else | 5981 | else |
155 | 5974 | op0 = src, op1 = CONST0_RTX (GET_MODE (src)); | 5982 | op0 = src, op1 = CONST0_RTX (GET_MODE (src)); |
156 | 5975 | 5983 | ||
157 | @@ -6011,6 +6019,12 @@ | |||
158 | 6011 | need to use a different CC mode here. */ | 6019 | need to use a different CC mode here. */ |
159 | 6012 | if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC) | 6020 | if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC) |
160 | 6013 | compare_mode = GET_MODE (op0); | 6021 | compare_mode = GET_MODE (op0); |
161 | 6022 | else if (inner_compare | ||
162 | 6023 | && GET_MODE_CLASS (GET_MODE (inner_compare)) == MODE_CC | ||
163 | 6024 | && new_code == old_code | ||
164 | 6025 | && op0 == XEXP (inner_compare, 0) | ||
165 | 6026 | && op1 == XEXP (inner_compare, 1)) | ||
166 | 6027 | compare_mode = GET_MODE (inner_compare); | ||
167 | 6014 | else | 6028 | else |
168 | 6015 | compare_mode = SELECT_CC_MODE (new_code, op0, op1); | 6029 | compare_mode = SELECT_CC_MODE (new_code, op0, op1); |
169 | 6016 | 6030 | ||
170 | 6017 | 6031 | ||
171 | === modified file 'gcc/config/arm/arm.c' | |||
172 | --- gcc/config/arm/arm.c 2011-03-02 11:29:06 +0000 | |||
173 | +++ gcc/config/arm/arm.c 2011-04-13 13:28:18 +0000 | |||
174 | @@ -1896,6 +1896,22 @@ | |||
175 | 1896 | if (arm_selected_tune->core == cortexm4) | 1896 | if (arm_selected_tune->core == cortexm4) |
176 | 1897 | flag_schedule_interblock = 0; | 1897 | flag_schedule_interblock = 0; |
177 | 1898 | 1898 | ||
178 | 1899 | /* Enable -munaligned-access by default for | ||
179 | 1900 | - all ARMv6 architecture-based processors | ||
180 | 1901 | - ARMv7-A, ARMv7-R, and ARMv7-M architecture-based processors. | ||
181 | 1902 | |||
182 | 1903 | Disable -munaligned-access by default for | ||
183 | 1904 | - all pre-ARMv6 architecture-based processors | ||
184 | 1905 | - ARMv6-M architecture-based processors. */ | ||
185 | 1906 | |||
186 | 1907 | if (unaligned_access == 2) | ||
187 | 1908 | { | ||
188 | 1909 | if (arm_arch6 && (arm_arch_notm || arm_arch7)) | ||
189 | 1910 | unaligned_access = 1; | ||
190 | 1911 | else | ||
191 | 1912 | unaligned_access = 0; | ||
192 | 1913 | } | ||
193 | 1914 | |||
194 | 1899 | if (TARGET_THUMB1 && flag_schedule_insns) | 1915 | if (TARGET_THUMB1 && flag_schedule_insns) |
195 | 1900 | { | 1916 | { |
196 | 1901 | /* Don't warn since it's on by default in -O2. */ | 1917 | /* Don't warn since it's on by default in -O2. */ |
197 | @@ -10505,6 +10521,333 @@ | |||
198 | 10505 | return true; | 10521 | return true; |
199 | 10506 | } | 10522 | } |
200 | 10507 | 10523 | ||
201 | 10524 | /* Copy a block of memory using plain ldr/str/ldrh/strh instructions, to permit | ||
202 | 10525 | unaligned copies on processors which support unaligned semantics for those | ||
203 | 10526 | instructions. INTERLEAVE_FACTOR can be used to attempt to hide load latency | ||
204 | 10527 | (using more registers) by doing e.g. load/load/store/store for a factor of 2. | ||
205 | 10528 | An interleave factor of 1 (the minimum) will perform no interleaving. | ||
206 | 10529 | Load/store multiple are used for aligned addresses where possible. */ | ||
207 | 10530 | |||
208 | 10531 | static void | ||
209 | 10532 | arm_block_move_unaligned_straight (rtx dstbase, rtx srcbase, | ||
210 | 10533 | HOST_WIDE_INT length, | ||
211 | 10534 | unsigned int interleave_factor) | ||
212 | 10535 | { | ||
213 | 10536 | rtx *regs = XALLOCAVEC (rtx, interleave_factor); | ||
214 | 10537 | HOST_WIDE_INT block_size_bytes = interleave_factor * UNITS_PER_WORD; | ||
215 | 10538 | HOST_WIDE_INT i, j; | ||
216 | 10539 | HOST_WIDE_INT remaining = length, words; | ||
217 | 10540 | rtx halfword_tmp = NULL, byte_tmp = NULL; | ||
218 | 10541 | rtx dst, src; | ||
219 | 10542 | bool src_aligned = MEM_ALIGN (srcbase) >= BITS_PER_WORD; | ||
220 | 10543 | bool dst_aligned = MEM_ALIGN (dstbase) >= BITS_PER_WORD; | ||
221 | 10544 | HOST_WIDE_INT srcoffset, dstoffset; | ||
222 | 10545 | HOST_WIDE_INT src_autoinc, dst_autoinc; | ||
223 | 10546 | rtx mem, addr; | ||
224 | 10547 | |||
225 | 10548 | gcc_assert (1 <= interleave_factor && interleave_factor <= 4); | ||
226 | 10549 | |||
227 | 10550 | /* Use hard registers if we have aligned source or destination so we can use | ||
228 | 10551 | load/store multiple with contiguous registers. */ | ||
229 | 10552 | if (dst_aligned || src_aligned) | ||
230 | 10553 | for (i = 0; i < interleave_factor; i++) | ||
231 | 10554 | regs[i] = gen_rtx_REG (SImode, i); | ||
232 | 10555 | else | ||
233 | 10556 | for (i = 0; i < interleave_factor; i++) | ||
234 | 10557 | regs[i] = gen_reg_rtx (SImode); | ||
235 | 10558 | |||
236 | 10559 | dst = copy_addr_to_reg (XEXP (dstbase, 0)); | ||
237 | 10560 | src = copy_addr_to_reg (XEXP (srcbase, 0)); | ||
238 | 10561 | |||
239 | 10562 | srcoffset = dstoffset = 0; | ||
240 | 10563 | |||
241 | 10564 | /* Calls to arm_gen_load_multiple and arm_gen_store_multiple update SRC/DST. | ||
242 | 10565 | For copying the last bytes we want to subtract this offset again. */ | ||
243 | 10566 | src_autoinc = dst_autoinc = 0; | ||
244 | 10567 | |||
245 | 10568 | /* Copy BLOCK_SIZE_BYTES chunks. */ | ||
246 | 10569 | |||
247 | 10570 | for (i = 0; i + block_size_bytes <= length; i += block_size_bytes) | ||
248 | 10571 | { | ||
249 | 10572 | /* Load words. */ | ||
250 | 10573 | if (src_aligned && interleave_factor > 1) | ||
251 | 10574 | { | ||
252 | 10575 | emit_insn (arm_gen_load_multiple (arm_regs_in_sequence, | ||
253 | 10576 | interleave_factor, src, TRUE, | ||
254 | 10577 | srcbase, &srcoffset)); | ||
255 | 10578 | src_autoinc += UNITS_PER_WORD * interleave_factor; | ||
256 | 10579 | } | ||
257 | 10580 | else | ||
258 | 10581 | { | ||
259 | 10582 | for (j = 0; j < interleave_factor; j++) | ||
260 | 10583 | { | ||
261 | 10584 | addr = plus_constant (src, srcoffset + j * UNITS_PER_WORD | ||
262 | 10585 | - src_autoinc); | ||
263 | 10586 | mem = adjust_automodify_address (srcbase, SImode, addr, | ||
264 | 10587 | srcoffset + j * UNITS_PER_WORD); | ||
265 | 10588 | emit_insn (gen_unaligned_loadsi (regs[j], mem)); | ||
266 | 10589 | } | ||
267 | 10590 | srcoffset += block_size_bytes; | ||
268 | 10591 | } | ||
269 | 10592 | |||
270 | 10593 | /* Store words. */ | ||
271 | 10594 | if (dst_aligned && interleave_factor > 1) | ||
272 | 10595 | { | ||
273 | 10596 | emit_insn (arm_gen_store_multiple (arm_regs_in_sequence, | ||
274 | 10597 | interleave_factor, dst, TRUE, | ||
275 | 10598 | dstbase, &dstoffset)); | ||
276 | 10599 | dst_autoinc += UNITS_PER_WORD * interleave_factor; | ||
277 | 10600 | } | ||
278 | 10601 | else | ||
279 | 10602 | { | ||
280 | 10603 | for (j = 0; j < interleave_factor; j++) | ||
281 | 10604 | { | ||
282 | 10605 | addr = plus_constant (dst, dstoffset + j * UNITS_PER_WORD | ||
283 | 10606 | - dst_autoinc); | ||
284 | 10607 | mem = adjust_automodify_address (dstbase, SImode, addr, | ||
285 | 10608 | dstoffset + j * UNITS_PER_WORD); | ||
286 | 10609 | emit_insn (gen_unaligned_storesi (mem, regs[j])); | ||
287 | 10610 | } | ||
288 | 10611 | dstoffset += block_size_bytes; | ||
289 | 10612 | } | ||
290 | 10613 | |||
291 | 10614 | remaining -= block_size_bytes; | ||
292 | 10615 | } | ||
293 | 10616 | |||
294 | 10617 | /* Copy any whole words left (note these aren't interleaved with any | ||
295 | 10618 | subsequent halfword/byte load/stores in the interests of simplicity). */ | ||
296 | 10619 | |||
297 | 10620 | words = remaining / UNITS_PER_WORD; | ||
298 | 10621 | |||
299 | 10622 | gcc_assert (words < interleave_factor); | ||
300 | 10623 | |||
301 | 10624 | if (src_aligned && words > 1) | ||
302 | 10625 | { | ||
303 | 10626 | emit_insn (arm_gen_load_multiple (arm_regs_in_sequence, words, src, | ||
304 | 10627 | TRUE, srcbase, &srcoffset)); | ||
305 | 10628 | src_autoinc += UNITS_PER_WORD * words; | ||
306 | 10629 | } | ||
307 | 10630 | else | ||
308 | 10631 | { | ||
309 | 10632 | for (j = 0; j < words; j++) | ||
310 | 10633 | { | ||
311 | 10634 | addr = plus_constant (src, | ||
312 | 10635 | srcoffset + j * UNITS_PER_WORD - src_autoinc); | ||
313 | 10636 | mem = adjust_automodify_address (srcbase, SImode, addr, | ||
314 | 10637 | srcoffset + j * UNITS_PER_WORD); | ||
315 | 10638 | emit_insn (gen_unaligned_loadsi (regs[j], mem)); | ||
316 | 10639 | } | ||
317 | 10640 | srcoffset += words * UNITS_PER_WORD; | ||
318 | 10641 | } | ||
319 | 10642 | |||
320 | 10643 | if (dst_aligned && words > 1) | ||
321 | 10644 | { | ||
322 | 10645 | emit_insn (arm_gen_store_multiple (arm_regs_in_sequence, words, dst, | ||
323 | 10646 | TRUE, dstbase, &dstoffset)); | ||
324 | 10647 | dst_autoinc += words * UNITS_PER_WORD; | ||
325 | 10648 | } | ||
326 | 10649 | else | ||
327 | 10650 | { | ||
328 | 10651 | for (j = 0; j < words; j++) | ||
329 | 10652 | { | ||
330 | 10653 | addr = plus_constant (dst, | ||
331 | 10654 | dstoffset + j * UNITS_PER_WORD - dst_autoinc); | ||
332 | 10655 | mem = adjust_automodify_address (dstbase, SImode, addr, | ||
333 | 10656 | dstoffset + j * UNITS_PER_WORD); | ||
334 | 10657 | emit_insn (gen_unaligned_storesi (mem, regs[j])); | ||
335 | 10658 | } | ||
336 | 10659 | dstoffset += words * UNITS_PER_WORD; | ||
337 | 10660 | } | ||
338 | 10661 | |||
339 | 10662 | remaining -= words * UNITS_PER_WORD; | ||
340 | 10663 | |||
341 | 10664 | gcc_assert (remaining < 4); | ||
342 | 10665 | |||
343 | 10666 | /* Copy a halfword if necessary. */ | ||
344 | 10667 | |||
345 | 10668 | if (remaining >= 2) | ||
346 | 10669 | { | ||
347 | 10670 | halfword_tmp = gen_reg_rtx (SImode); | ||
348 | 10671 | |||
349 | 10672 | addr = plus_constant (src, srcoffset - src_autoinc); | ||
350 | 10673 | mem = adjust_automodify_address (srcbase, HImode, addr, srcoffset); | ||
351 | 10674 | emit_insn (gen_unaligned_loadhiu (halfword_tmp, mem)); | ||
352 | 10675 | |||
353 | 10676 | /* Either write out immediately, or delay until we've loaded the last | ||
354 | 10677 | byte, depending on interleave factor. */ | ||
355 | 10678 | if (interleave_factor == 1) | ||
356 | 10679 | { | ||
357 | 10680 | addr = plus_constant (dst, dstoffset - dst_autoinc); | ||
358 | 10681 | mem = adjust_automodify_address (dstbase, HImode, addr, dstoffset); | ||
359 | 10682 | emit_insn (gen_unaligned_storehi (mem, | ||
360 | 10683 | gen_lowpart (HImode, halfword_tmp))); | ||
361 | 10684 | halfword_tmp = NULL; | ||
362 | 10685 | dstoffset += 2; | ||
363 | 10686 | } | ||
364 | 10687 | |||
365 | 10688 | remaining -= 2; | ||
366 | 10689 | srcoffset += 2; | ||
367 | 10690 | } | ||
368 | 10691 | |||
369 | 10692 | gcc_assert (remaining < 2); | ||
370 | 10693 | |||
371 | 10694 | /* Copy last byte. */ | ||
372 | 10695 | |||
373 | 10696 | if ((remaining & 1) != 0) | ||
374 | 10697 | { | ||
375 | 10698 | byte_tmp = gen_reg_rtx (SImode); | ||
376 | 10699 | |||
377 | 10700 | addr = plus_constant (src, srcoffset - src_autoinc); | ||
378 | 10701 | mem = adjust_automodify_address (srcbase, QImode, addr, srcoffset); | ||
379 | 10702 | emit_move_insn (gen_lowpart (QImode, byte_tmp), mem); | ||
380 | 10703 | |||
381 | 10704 | if (interleave_factor == 1) | ||
382 | 10705 | { | ||
383 | 10706 | addr = plus_constant (dst, dstoffset - dst_autoinc); | ||
384 | 10707 | mem = adjust_automodify_address (dstbase, QImode, addr, dstoffset); | ||
385 | 10708 | emit_move_insn (mem, gen_lowpart (QImode, byte_tmp)); | ||
386 | 10709 | byte_tmp = NULL; | ||
387 | 10710 | dstoffset++; | ||
388 | 10711 | } | ||
389 | 10712 | |||
390 | 10713 | remaining--; | ||
391 | 10714 | srcoffset++; | ||
392 | 10715 | } | ||
393 | 10716 | |||
394 | 10717 | /* Store last halfword if we haven't done so already. */ | ||
395 | 10718 | |||
396 | 10719 | if (halfword_tmp) | ||
397 | 10720 | { | ||
398 | 10721 | addr = plus_constant (dst, dstoffset - dst_autoinc); | ||
399 | 10722 | mem = adjust_automodify_address (dstbase, HImode, addr, dstoffset); | ||
400 | 10723 | emit_insn (gen_unaligned_storehi (mem, | ||
401 | 10724 | gen_lowpart (HImode, halfword_tmp))); | ||
402 | 10725 | dstoffset += 2; | ||
403 | 10726 | } | ||
404 | 10727 | |||
405 | 10728 | /* Likewise for last byte. */ | ||
406 | 10729 | |||
407 | 10730 | if (byte_tmp) | ||
408 | 10731 | { | ||
409 | 10732 | addr = plus_constant (dst, dstoffset - dst_autoinc); | ||
410 | 10733 | mem = adjust_automodify_address (dstbase, QImode, addr, dstoffset); | ||
411 | 10734 | emit_move_insn (mem, gen_lowpart (QImode, byte_tmp)); | ||
412 | 10735 | dstoffset++; | ||
413 | 10736 | } | ||
414 | 10737 | |||
415 | 10738 | gcc_assert (remaining == 0 && srcoffset == dstoffset); | ||
416 | 10739 | } | ||
417 | 10740 | |||
418 | 10741 | /* From mips_adjust_block_mem: | ||
419 | 10742 | |||
420 | 10743 | Helper function for doing a loop-based block operation on memory | ||
421 | 10744 | reference MEM. Each iteration of the loop will operate on LENGTH | ||
422 | 10745 | bytes of MEM. | ||
423 | 10746 | |||
424 | 10747 | Create a new base register for use within the loop and point it to | ||
425 | 10748 | the start of MEM. Create a new memory reference that uses this | ||
426 | 10749 | register. Store them in *LOOP_REG and *LOOP_MEM respectively. */ | ||
427 | 10750 | |||
428 | 10751 | static void | ||
429 | 10752 | arm_adjust_block_mem (rtx mem, HOST_WIDE_INT length, rtx *loop_reg, | ||
430 | 10753 | rtx *loop_mem) | ||
431 | 10754 | { | ||
432 | 10755 | *loop_reg = copy_addr_to_reg (XEXP (mem, 0)); | ||
433 | 10756 | |||
434 | 10757 | /* Although the new mem does not refer to a known location, | ||
435 | 10758 | it does keep up to LENGTH bytes of alignment. */ | ||
436 | 10759 | *loop_mem = change_address (mem, BLKmode, *loop_reg); | ||
437 | 10760 | set_mem_align (*loop_mem, MIN (MEM_ALIGN (mem), length * BITS_PER_UNIT)); | ||
438 | 10761 | } | ||
439 | 10762 | |||
440 | 10763 | /* From mips_block_move_loop: | ||
441 | 10764 | |||
442 | 10765 | Move LENGTH bytes from SRC to DEST using a loop that moves BYTES_PER_ITER | ||
443 | 10766 | bytes at a time. LENGTH must be at least BYTES_PER_ITER. Assume that | ||
444 | 10767 | the memory regions do not overlap. */ | ||
445 | 10768 | |||
446 | 10769 | static void | ||
447 | 10770 | arm_block_move_unaligned_loop (rtx dest, rtx src, HOST_WIDE_INT length, | ||
448 | 10771 | unsigned int interleave_factor, | ||
449 | 10772 | HOST_WIDE_INT bytes_per_iter) | ||
450 | 10773 | { | ||
451 | 10774 | rtx label, src_reg, dest_reg, final_src, test; | ||
452 | 10775 | HOST_WIDE_INT leftover; | ||
453 | 10776 | |||
454 | 10777 | leftover = length % bytes_per_iter; | ||
455 | 10778 | length -= leftover; | ||
456 | 10779 | |||
457 | 10780 | /* Create registers and memory references for use within the loop. */ | ||
458 | 10781 | arm_adjust_block_mem (src, bytes_per_iter, &src_reg, &src); | ||
459 | 10782 | arm_adjust_block_mem (dest, bytes_per_iter, &dest_reg, &dest); | ||
460 | 10783 | |||
461 | 10784 | /* Calculate the value that SRC_REG should have after the last iteration of | ||
462 | 10785 | the loop. */ | ||
463 | 10786 | final_src = expand_simple_binop (Pmode, PLUS, src_reg, GEN_INT (length), | ||
464 | 10787 | 0, 0, OPTAB_WIDEN); | ||
465 | 10788 | |||
466 | 10789 | /* Emit the start of the loop. */ | ||
467 | 10790 | label = gen_label_rtx (); | ||
468 | 10791 | emit_label (label); | ||
469 | 10792 | |||
470 | 10793 | /* Emit the loop body. */ | ||
471 | 10794 | arm_block_move_unaligned_straight (dest, src, bytes_per_iter, | ||
472 | 10795 | interleave_factor); | ||
473 | 10796 | |||
474 | 10797 | /* Move on to the next block. */ | ||
475 | 10798 | emit_move_insn (src_reg, plus_constant (src_reg, bytes_per_iter)); | ||
476 | 10799 | emit_move_insn (dest_reg, plus_constant (dest_reg, bytes_per_iter)); | ||
477 | 10800 | |||
478 | 10801 | /* Emit the loop condition. */ | ||
479 | 10802 | test = gen_rtx_NE (VOIDmode, src_reg, final_src); | ||
480 | 10803 | emit_jump_insn (gen_cbranchsi4 (test, src_reg, final_src, label)); | ||
481 | 10804 | |||
482 | 10805 | /* Mop up any left-over bytes. */ | ||
483 | 10806 | if (leftover) | ||
484 | 10807 | arm_block_move_unaligned_straight (dest, src, leftover, interleave_factor); | ||
485 | 10808 | } | ||
486 | 10809 | |||
487 | 10810 | /* Emit a block move when either the source or destination is unaligned (not | ||
488 | 10811 | aligned to a four-byte boundary). This may need further tuning depending on | ||
489 | 10812 | core type, optimize_size setting, alignment of source/destination, etc. */ | ||
490 | 10813 | |||
491 | 10814 | static int | ||
492 | 10815 | arm_movmemqi_unaligned (rtx *operands) | ||
493 | 10816 | { | ||
494 | 10817 | HOST_WIDE_INT length = INTVAL (operands[2]); | ||
495 | 10818 | |||
496 | 10819 | if (optimize_size) | ||
497 | 10820 | { | ||
498 | 10821 | bool src_aligned = MEM_ALIGN (operands[1]) >= BITS_PER_WORD; | ||
499 | 10822 | bool dst_aligned = MEM_ALIGN (operands[0]) >= BITS_PER_WORD; | ||
500 | 10823 | /* Inlined memcpy using ldr/str/ldrh/strh can be quite big: try to limit | ||
501 | 10824 | size of code if optimizing for size. We'll use ldm/stm if src_aligned | ||
502 | 10825 | or dst_aligned though: allow more interleaving in those cases since the | ||
503 | 10826 | resulting code can be smaller. */ | ||
504 | 10827 | unsigned int interleave_factor = (src_aligned || dst_aligned) ? 2 : 1; | ||
505 | 10828 | HOST_WIDE_INT bytes_per_iter = (src_aligned || dst_aligned) ? 8 : 4; | ||
506 | 10829 | |||
507 | 10830 | if (length > 12) | ||
508 | 10831 | arm_block_move_unaligned_loop (operands[0], operands[1], length, | ||
509 | 10832 | interleave_factor, bytes_per_iter); | ||
510 | 10833 | else | ||
511 | 10834 | arm_block_move_unaligned_straight (operands[0], operands[1], length, | ||
512 | 10835 | interleave_factor); | ||
513 | 10836 | } | ||
514 | 10837 | else | ||
515 | 10838 | { | ||
516 | 10839 | /* Note that the loop created by arm_block_move_unaligned_loop may be | ||
517 | 10840 | subject to loop unrolling, which makes tuning this condition a little | ||
518 | 10841 | awkward. */ | ||
519 | 10842 | if (length > 32) | ||
520 | 10843 | arm_block_move_unaligned_loop (operands[0], operands[1], length, 4, 16); | ||
521 | 10844 | else | ||
522 | 10845 | arm_block_move_unaligned_straight (operands[0], operands[1], length, 4); | ||
523 | 10846 | } | ||
524 | 10847 | |||
525 | 10848 | return 1; | ||
526 | 10849 | } | ||
527 | 10850 | |||
528 | 10508 | int | 10851 | int |
529 | 10509 | arm_gen_movmemqi (rtx *operands) | 10852 | arm_gen_movmemqi (rtx *operands) |
530 | 10510 | { | 10853 | { |
531 | @@ -10517,8 +10860,13 @@ | |||
532 | 10517 | 10860 | ||
533 | 10518 | if (GET_CODE (operands[2]) != CONST_INT | 10861 | if (GET_CODE (operands[2]) != CONST_INT |
534 | 10519 | || GET_CODE (operands[3]) != CONST_INT | 10862 | || GET_CODE (operands[3]) != CONST_INT |
537 | 10520 | || INTVAL (operands[2]) > 64 | 10863 | || INTVAL (operands[2]) > 64) |
538 | 10521 | || INTVAL (operands[3]) & 3) | 10864 | return 0; |
539 | 10865 | |||
540 | 10866 | if (unaligned_access && (INTVAL (operands[3]) & 3) != 0) | ||
541 | 10867 | return arm_movmemqi_unaligned (operands); | ||
542 | 10868 | |||
543 | 10869 | if (INTVAL (operands[3]) & 3) | ||
544 | 10522 | return 0; | 10870 | return 0; |
545 | 10523 | 10871 | ||
546 | 10524 | dstbase = operands[0]; | 10872 | dstbase = operands[0]; |
547 | @@ -23095,10 +23443,13 @@ | |||
548 | 23095 | static bool | 23443 | static bool |
549 | 23096 | arm_vector_alignment_reachable (const_tree type, bool is_packed) | 23444 | arm_vector_alignment_reachable (const_tree type, bool is_packed) |
550 | 23097 | { | 23445 | { |
553 | 23098 | /* Vectors which aren't in packed structures will not be less aligned than | 23446 | /* NOTE: returning true here will unconditionally peel loop iterations so |
554 | 23099 | the natural alignment of their element type, so this is safe. */ | 23447 | that aligned accesses can be used. This is undesirable when misaligned |
555 | 23448 | accesses are available, particularly for small loop iteration counts, | ||
556 | 23449 | since the overhead for dispatching to multiple versions of the loop is | ||
557 | 23450 | quite high. */ | ||
558 | 23100 | if (TARGET_NEON && !BYTES_BIG_ENDIAN) | 23451 | if (TARGET_NEON && !BYTES_BIG_ENDIAN) |
560 | 23101 | return !is_packed; | 23452 | return false; |
561 | 23102 | 23453 | ||
562 | 23103 | return default_builtin_vector_alignment_reachable (type, is_packed); | 23454 | return default_builtin_vector_alignment_reachable (type, is_packed); |
563 | 23104 | } | 23455 | } |
564 | 23105 | 23456 | ||
565 | === modified file 'gcc/config/arm/arm.md' | |||
566 | --- gcc/config/arm/arm.md 2011-03-11 14:26:34 +0000 | |||
567 | +++ gcc/config/arm/arm.md 2011-04-13 13:28:18 +0000 | |||
568 | @@ -104,6 +104,8 @@ | |||
569 | 104 | (UNSPEC_SYMBOL_OFFSET 27) ; The offset of the start of the symbol from | 104 | (UNSPEC_SYMBOL_OFFSET 27) ; The offset of the start of the symbol from |
570 | 105 | ; another symbolic address. | 105 | ; another symbolic address. |
571 | 106 | (UNSPEC_MEMORY_BARRIER 28) ; Represent a memory barrier. | 106 | (UNSPEC_MEMORY_BARRIER 28) ; Represent a memory barrier. |
572 | 107 | (UNSPEC_UNALIGNED_LOAD 29) | ||
573 | 108 | (UNSPEC_UNALIGNED_STORE 30) | ||
574 | 107 | ] | 109 | ] |
575 | 108 | ) | 110 | ) |
576 | 109 | 111 | ||
577 | @@ -2372,7 +2374,7 @@ | |||
578 | 2372 | ;;; this insv pattern, so this pattern needs to be reevalutated. | 2374 | ;;; this insv pattern, so this pattern needs to be reevalutated. |
579 | 2373 | 2375 | ||
580 | 2374 | (define_expand "insv" | 2376 | (define_expand "insv" |
582 | 2375 | [(set (zero_extract:SI (match_operand:SI 0 "s_register_operand" "") | 2377 | [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "") |
583 | 2376 | (match_operand:SI 1 "general_operand" "") | 2378 | (match_operand:SI 1 "general_operand" "") |
584 | 2377 | (match_operand:SI 2 "general_operand" "")) | 2379 | (match_operand:SI 2 "general_operand" "")) |
585 | 2378 | (match_operand:SI 3 "reg_or_int_operand" ""))] | 2380 | (match_operand:SI 3 "reg_or_int_operand" ""))] |
586 | @@ -2386,35 +2388,66 @@ | |||
587 | 2386 | 2388 | ||
588 | 2387 | if (arm_arch_thumb2) | 2389 | if (arm_arch_thumb2) |
589 | 2388 | { | 2390 | { |
600 | 2389 | bool use_bfi = TRUE; | 2391 | if (unaligned_access && MEM_P (operands[0]) |
601 | 2390 | 2392 | && s_register_operand (operands[3], GET_MODE (operands[3])) | |
602 | 2391 | if (GET_CODE (operands[3]) == CONST_INT) | 2393 | && (width == 16 || width == 32) && (start_bit % BITS_PER_UNIT) == 0) |
603 | 2392 | { | 2394 | { |
604 | 2393 | HOST_WIDE_INT val = INTVAL (operands[3]) & mask; | 2395 | rtx base_addr; |
605 | 2394 | 2396 | ||
606 | 2395 | if (val == 0) | 2397 | if (width == 32) |
607 | 2396 | { | 2398 | { |
608 | 2397 | emit_insn (gen_insv_zero (operands[0], operands[1], | 2399 | base_addr = adjust_address (operands[0], SImode, |
609 | 2398 | operands[2])); | 2400 | start_bit / BITS_PER_UNIT); |
610 | 2401 | emit_insn (gen_unaligned_storesi (base_addr, operands[3])); | ||
611 | 2402 | } | ||
612 | 2403 | else | ||
613 | 2404 | { | ||
614 | 2405 | rtx tmp = gen_reg_rtx (HImode); | ||
615 | 2406 | |||
616 | 2407 | base_addr = adjust_address (operands[0], HImode, | ||
617 | 2408 | start_bit / BITS_PER_UNIT); | ||
618 | 2409 | emit_move_insn (tmp, gen_lowpart (HImode, operands[3])); | ||
619 | 2410 | emit_insn (gen_unaligned_storehi (base_addr, tmp)); | ||
620 | 2411 | } | ||
621 | 2412 | DONE; | ||
622 | 2413 | } | ||
623 | 2414 | else if (s_register_operand (operands[0], GET_MODE (operands[0]))) | ||
624 | 2415 | { | ||
625 | 2416 | bool use_bfi = TRUE; | ||
626 | 2417 | |||
627 | 2418 | if (GET_CODE (operands[3]) == CONST_INT) | ||
628 | 2419 | { | ||
629 | 2420 | HOST_WIDE_INT val = INTVAL (operands[3]) & mask; | ||
630 | 2421 | |||
631 | 2422 | if (val == 0) | ||
632 | 2423 | { | ||
633 | 2424 | emit_insn (gen_insv_zero (operands[0], operands[1], | ||
634 | 2425 | operands[2])); | ||
635 | 2426 | DONE; | ||
636 | 2427 | } | ||
637 | 2428 | |||
638 | 2429 | /* See if the set can be done with a single orr instruction. */ | ||
639 | 2430 | if (val == mask && const_ok_for_arm (val << start_bit)) | ||
640 | 2431 | use_bfi = FALSE; | ||
641 | 2432 | } | ||
642 | 2433 | |||
643 | 2434 | if (use_bfi) | ||
644 | 2435 | { | ||
645 | 2436 | if (GET_CODE (operands[3]) != REG) | ||
646 | 2437 | operands[3] = force_reg (SImode, operands[3]); | ||
647 | 2438 | |||
648 | 2439 | emit_insn (gen_insv_t2 (operands[0], operands[1], operands[2], | ||
649 | 2440 | operands[3])); | ||
650 | 2399 | DONE; | 2441 | DONE; |
651 | 2400 | } | 2442 | } |
667 | 2401 | 2443 | } | |
668 | 2402 | /* See if the set can be done with a single orr instruction. */ | 2444 | else |
669 | 2403 | if (val == mask && const_ok_for_arm (val << start_bit)) | 2445 | FAIL; |
655 | 2404 | use_bfi = FALSE; | ||
656 | 2405 | } | ||
657 | 2406 | |||
658 | 2407 | if (use_bfi) | ||
659 | 2408 | { | ||
660 | 2409 | if (GET_CODE (operands[3]) != REG) | ||
661 | 2410 | operands[3] = force_reg (SImode, operands[3]); | ||
662 | 2411 | |||
663 | 2412 | emit_insn (gen_insv_t2 (operands[0], operands[1], operands[2], | ||
664 | 2413 | operands[3])); | ||
665 | 2414 | DONE; | ||
666 | 2415 | } | ||
670 | 2416 | } | 2446 | } |
671 | 2417 | 2447 | ||
672 | 2448 | if (!s_register_operand (operands[0], GET_MODE (operands[0]))) | ||
673 | 2449 | FAIL; | ||
674 | 2450 | |||
675 | 2418 | target = copy_rtx (operands[0]); | 2451 | target = copy_rtx (operands[0]); |
676 | 2419 | /* Avoid using a subreg as a subtarget, and avoid writing a paradoxical | 2452 | /* Avoid using a subreg as a subtarget, and avoid writing a paradoxical |
677 | 2420 | subreg as the final target. */ | 2453 | subreg as the final target. */ |
678 | @@ -3604,7 +3637,7 @@ | |||
679 | 3604 | 3637 | ||
680 | 3605 | (define_expand "extzv" | 3638 | (define_expand "extzv" |
681 | 3606 | [(set (match_dup 4) | 3639 | [(set (match_dup 4) |
683 | 3607 | (ashift:SI (match_operand:SI 1 "register_operand" "") | 3640 | (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "") |
684 | 3608 | (match_operand:SI 2 "const_int_operand" ""))) | 3641 | (match_operand:SI 2 "const_int_operand" ""))) |
685 | 3609 | (set (match_operand:SI 0 "register_operand" "") | 3642 | (set (match_operand:SI 0 "register_operand" "") |
686 | 3610 | (lshiftrt:SI (match_dup 4) | 3643 | (lshiftrt:SI (match_dup 4) |
687 | @@ -3617,10 +3650,53 @@ | |||
688 | 3617 | 3650 | ||
689 | 3618 | if (arm_arch_thumb2) | 3651 | if (arm_arch_thumb2) |
690 | 3619 | { | 3652 | { |
694 | 3620 | emit_insn (gen_extzv_t2 (operands[0], operands[1], operands[2], | 3653 | HOST_WIDE_INT width = INTVAL (operands[2]); |
695 | 3621 | operands[3])); | 3654 | HOST_WIDE_INT bitpos = INTVAL (operands[3]); |
696 | 3622 | DONE; | 3655 | |
697 | 3656 | if (unaligned_access && MEM_P (operands[1]) | ||
698 | 3657 | && (width == 16 || width == 32) && (bitpos % BITS_PER_UNIT) == 0) | ||
699 | 3658 | { | ||
700 | 3659 | rtx base_addr; | ||
701 | 3660 | |||
702 | 3661 | if (width == 32) | ||
703 | 3662 | { | ||
704 | 3663 | base_addr = adjust_address (operands[1], SImode, | ||
705 | 3664 | bitpos / BITS_PER_UNIT); | ||
706 | 3665 | emit_insn (gen_unaligned_loadsi (operands[0], base_addr)); | ||
707 | 3666 | } | ||
708 | 3667 | else | ||
709 | 3668 | { | ||
710 | 3669 | rtx dest = operands[0]; | ||
711 | 3670 | rtx tmp = gen_reg_rtx (SImode); | ||
712 | 3671 | |||
713 | 3672 | /* We may get a paradoxical subreg here. Strip it off. */ | ||
714 | 3673 | if (GET_CODE (dest) == SUBREG | ||
715 | 3674 | && GET_MODE (dest) == SImode | ||
716 | 3675 | && GET_MODE (SUBREG_REG (dest)) == HImode) | ||
717 | 3676 | dest = SUBREG_REG (dest); | ||
718 | 3677 | |||
719 | 3678 | if (GET_MODE_BITSIZE (GET_MODE (dest)) != width) | ||
720 | 3679 | FAIL; | ||
721 | 3680 | |||
722 | 3681 | base_addr = adjust_address (operands[1], HImode, | ||
723 | 3682 | bitpos / BITS_PER_UNIT); | ||
724 | 3683 | emit_insn (gen_unaligned_loadhiu (tmp, base_addr)); | ||
725 | 3684 | emit_move_insn (gen_lowpart (SImode, dest), tmp); | ||
726 | 3685 | } | ||
727 | 3686 | DONE; | ||
728 | 3687 | } | ||
729 | 3688 | else if (s_register_operand (operands[1], GET_MODE (operands[1]))) | ||
730 | 3689 | { | ||
731 | 3690 | emit_insn (gen_extzv_t2 (operands[0], operands[1], operands[2], | ||
732 | 3691 | operands[3])); | ||
733 | 3692 | DONE; | ||
734 | 3693 | } | ||
735 | 3694 | else | ||
736 | 3695 | FAIL; | ||
737 | 3623 | } | 3696 | } |
738 | 3697 | |||
739 | 3698 | if (!s_register_operand (operands[1], GET_MODE (operands[1]))) | ||
740 | 3699 | FAIL; | ||
741 | 3624 | 3700 | ||
742 | 3625 | operands[3] = GEN_INT (rshift); | 3701 | operands[3] = GEN_INT (rshift); |
743 | 3626 | 3702 | ||
744 | @@ -3635,7 +3711,103 @@ | |||
745 | 3635 | }" | 3711 | }" |
746 | 3636 | ) | 3712 | ) |
747 | 3637 | 3713 | ||
749 | 3638 | (define_insn "extv" | 3714 | (define_expand "extv" |
750 | 3715 | [(set (match_operand 0 "s_register_operand" "") | ||
751 | 3716 | (sign_extract (match_operand 1 "nonimmediate_operand" "") | ||
752 | 3717 | (match_operand 2 "const_int_operand" "") | ||
753 | 3718 | (match_operand 3 "const_int_operand" "")))] | ||
754 | 3719 | "arm_arch_thumb2" | ||
755 | 3720 | { | ||
756 | 3721 | HOST_WIDE_INT width = INTVAL (operands[2]); | ||
757 | 3722 | HOST_WIDE_INT bitpos = INTVAL (operands[3]); | ||
758 | 3723 | |||
759 | 3724 | if (unaligned_access && MEM_P (operands[1]) && (width == 16 || width == 32) | ||
760 | 3725 | && (bitpos % BITS_PER_UNIT) == 0) | ||
761 | 3726 | { | ||
762 | 3727 | rtx base_addr; | ||
763 | 3728 | |||
764 | 3729 | if (width == 32) | ||
765 | 3730 | { | ||
766 | 3731 | base_addr = adjust_address (operands[1], SImode, | ||
767 | 3732 | bitpos / BITS_PER_UNIT); | ||
768 | 3733 | emit_insn (gen_unaligned_loadsi (operands[0], base_addr)); | ||
769 | 3734 | } | ||
770 | 3735 | else | ||
771 | 3736 | { | ||
772 | 3737 | rtx dest = operands[0]; | ||
773 | 3738 | rtx tmp = gen_reg_rtx (SImode); | ||
774 | 3739 | |||
775 | 3740 | /* We may get a paradoxical subreg here. Strip it off. */ | ||
776 | 3741 | if (GET_CODE (dest) == SUBREG | ||
777 | 3742 | && GET_MODE (dest) == SImode | ||
778 | 3743 | && GET_MODE (SUBREG_REG (dest)) == HImode) | ||
779 | 3744 | dest = SUBREG_REG (dest); | ||
780 | 3745 | |||
781 | 3746 | if (GET_MODE_BITSIZE (GET_MODE (dest)) != width) | ||
782 | 3747 | FAIL; | ||
783 | 3748 | |||
784 | 3749 | base_addr = adjust_address (operands[1], HImode, | ||
785 | 3750 | bitpos / BITS_PER_UNIT); | ||
786 | 3751 | emit_insn (gen_unaligned_loadhis (tmp, base_addr)); | ||
787 | 3752 | emit_move_insn (gen_lowpart (SImode, dest), tmp); | ||
788 | 3753 | } | ||
789 | 3754 | |||
790 | 3755 | DONE; | ||
791 | 3756 | } | ||
792 | 3757 | else if (s_register_operand (operands[1], GET_MODE (operands[1]))) | ||
793 | 3758 | DONE; | ||
794 | 3759 | else | ||
795 | 3760 | FAIL; | ||
796 | 3761 | }) | ||
797 | 3762 | |||
798 | 3763 | ; ARMv6+ unaligned load/store instructions (used for packed structure accesses). | ||
799 | 3764 | |||
800 | 3765 | (define_insn "unaligned_loadsi" | ||
801 | 3766 | [(set (match_operand:SI 0 "s_register_operand" "=r") | ||
802 | 3767 | (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] | ||
803 | 3768 | UNSPEC_UNALIGNED_LOAD))] | ||
804 | 3769 | "unaligned_access" | ||
805 | 3770 | "ldr%?\t%0, %1\t@ unaligned" | ||
806 | 3771 | [(set_attr "predicable" "yes") | ||
807 | 3772 | (set_attr "type" "load1")]) | ||
808 | 3773 | |||
809 | 3774 | (define_insn "unaligned_loadhis" | ||
810 | 3775 | [(set (match_operand:SI 0 "s_register_operand" "=r") | ||
811 | 3776 | (sign_extend:SI (unspec:HI [(match_operand:HI 1 "memory_operand" "m")] | ||
812 | 3777 | UNSPEC_UNALIGNED_LOAD)))] | ||
813 | 3778 | "unaligned_access" | ||
814 | 3779 | "ldr%(sh%)\t%0, %1\t@ unaligned" | ||
815 | 3780 | [(set_attr "predicable" "yes") | ||
816 | 3781 | (set_attr "type" "load_byte")]) | ||
817 | 3782 | |||
818 | 3783 | (define_insn "unaligned_loadhiu" | ||
819 | 3784 | [(set (match_operand:SI 0 "s_register_operand" "=r") | ||
820 | 3785 | (zero_extend:SI (unspec:HI [(match_operand:HI 1 "memory_operand" "m")] | ||
821 | 3786 | UNSPEC_UNALIGNED_LOAD)))] | ||
822 | 3787 | "unaligned_access" | ||
823 | 3788 | "ldr%(h%)\t%0, %1\t@ unaligned" | ||
824 | 3789 | [(set_attr "predicable" "yes") | ||
825 | 3790 | (set_attr "type" "load_byte")]) | ||
826 | 3791 | |||
827 | 3792 | (define_insn "unaligned_storesi" | ||
828 | 3793 | [(set (match_operand:SI 0 "memory_operand" "=m") | ||
829 | 3794 | (unspec:SI [(match_operand:SI 1 "s_register_operand" "r")] | ||
830 | 3795 | UNSPEC_UNALIGNED_STORE))] | ||
831 | 3796 | "unaligned_access" | ||
832 | 3797 | "str%?\t%1, %0\t@ unaligned" | ||
833 | 3798 | [(set_attr "predicable" "yes") | ||
834 | 3799 | (set_attr "type" "store1")]) | ||
835 | 3800 | |||
836 | 3801 | (define_insn "unaligned_storehi" | ||
837 | 3802 | [(set (match_operand:HI 0 "memory_operand" "=m") | ||
838 | 3803 | (unspec:HI [(match_operand:HI 1 "s_register_operand" "r")] | ||
839 | 3804 | UNSPEC_UNALIGNED_STORE))] | ||
840 | 3805 | "unaligned_access" | ||
841 | 3806 | "str%(h%)\t%1, %0\t@ unaligned" | ||
842 | 3807 | [(set_attr "predicable" "yes") | ||
843 | 3808 | (set_attr "type" "store1")]) | ||
844 | 3809 | |||
845 | 3810 | (define_insn "*extv_reg" | ||
846 | 3639 | [(set (match_operand:SI 0 "s_register_operand" "=r") | 3811 | [(set (match_operand:SI 0 "s_register_operand" "=r") |
847 | 3640 | (sign_extract:SI (match_operand:SI 1 "s_register_operand" "r") | 3812 | (sign_extract:SI (match_operand:SI 1 "s_register_operand" "r") |
848 | 3641 | (match_operand:SI 2 "const_int_operand" "M") | 3813 | (match_operand:SI 2 "const_int_operand" "M") |
849 | 3642 | 3814 | ||
850 | === modified file 'gcc/config/arm/arm.opt' | |||
851 | --- gcc/config/arm/arm.opt 2010-08-05 15:20:54 +0000 | |||
852 | +++ gcc/config/arm/arm.opt 2011-04-13 13:28:18 +0000 | |||
853 | @@ -173,3 +173,7 @@ | |||
854 | 173 | Target Report Var(fix_cm3_ldrd) Init(2) | 173 | Target Report Var(fix_cm3_ldrd) Init(2) |
855 | 174 | Avoid overlapping destination and address registers on LDRD instructions | 174 | Avoid overlapping destination and address registers on LDRD instructions |
856 | 175 | that may trigger Cortex-M3 errata. | 175 | that may trigger Cortex-M3 errata. |
857 | 176 | |||
858 | 177 | munaligned-access | ||
859 | 178 | Target Report Var(unaligned_access) Init(2) | ||
860 | 179 | Enable unaligned word and halfword accesses to packed data. | ||
861 | 176 | 180 | ||
862 | === modified file 'gcc/config/arm/unwind-arm.c' | |||
863 | --- gcc/config/arm/unwind-arm.c 2010-08-12 12:39:35 +0000 | |||
864 | +++ gcc/config/arm/unwind-arm.c 2011-04-13 13:28:18 +0000 | |||
865 | @@ -32,13 +32,18 @@ | |||
866 | 32 | typedef unsigned char bool; | 32 | typedef unsigned char bool; |
867 | 33 | 33 | ||
868 | 34 | typedef struct _ZSt9type_info type_info; /* This names C++ type_info type */ | 34 | typedef struct _ZSt9type_info type_info; /* This names C++ type_info type */ |
869 | 35 | enum __cxa_type_match_result | ||
870 | 36 | { | ||
871 | 37 | ctm_failed = 0, | ||
872 | 38 | ctm_succeeded = 1, | ||
873 | 39 | ctm_succeeded_with_ptr_to_base = 2 | ||
874 | 40 | }; | ||
875 | 35 | 41 | ||
876 | 36 | void __attribute__((weak)) __cxa_call_unexpected(_Unwind_Control_Block *ucbp); | 42 | void __attribute__((weak)) __cxa_call_unexpected(_Unwind_Control_Block *ucbp); |
877 | 37 | bool __attribute__((weak)) __cxa_begin_cleanup(_Unwind_Control_Block *ucbp); | 43 | bool __attribute__((weak)) __cxa_begin_cleanup(_Unwind_Control_Block *ucbp); |
882 | 38 | bool __attribute__((weak)) __cxa_type_match(_Unwind_Control_Block *ucbp, | 44 | enum __cxa_type_match_result __attribute__((weak)) __cxa_type_match |
883 | 39 | const type_info *rttip, | 45 | (_Unwind_Control_Block *ucbp, const type_info *rttip, |
884 | 40 | bool is_reference, | 46 | bool is_reference, void **matched_object); |
881 | 41 | void **matched_object); | ||
885 | 42 | 47 | ||
886 | 43 | _Unwind_Ptr __attribute__((weak)) | 48 | _Unwind_Ptr __attribute__((weak)) |
887 | 44 | __gnu_Unwind_Find_exidx (_Unwind_Ptr, int *); | 49 | __gnu_Unwind_Find_exidx (_Unwind_Ptr, int *); |
888 | @@ -1107,6 +1112,7 @@ | |||
889 | 1107 | _uw rtti; | 1112 | _uw rtti; |
890 | 1108 | bool is_reference = (data[0] & uint32_highbit) != 0; | 1113 | bool is_reference = (data[0] & uint32_highbit) != 0; |
891 | 1109 | void *matched; | 1114 | void *matched; |
892 | 1115 | enum __cxa_type_match_result match_type; | ||
893 | 1110 | 1116 | ||
894 | 1111 | /* Check for no-throw areas. */ | 1117 | /* Check for no-throw areas. */ |
895 | 1112 | if (data[1] == (_uw) -2) | 1118 | if (data[1] == (_uw) -2) |
896 | @@ -1118,17 +1124,31 @@ | |||
897 | 1118 | { | 1124 | { |
898 | 1119 | /* Match a catch specification. */ | 1125 | /* Match a catch specification. */ |
899 | 1120 | rtti = _Unwind_decode_target2 ((_uw) &data[1]); | 1126 | rtti = _Unwind_decode_target2 ((_uw) &data[1]); |
904 | 1121 | if (!__cxa_type_match (ucbp, (type_info *) rtti, | 1127 | match_type = __cxa_type_match (ucbp, |
905 | 1122 | is_reference, | 1128 | (type_info *) rtti, |
906 | 1123 | &matched)) | 1129 | is_reference, |
907 | 1124 | matched = (void *)0; | 1130 | &matched); |
908 | 1125 | } | 1131 | } |
909 | 1132 | else | ||
910 | 1133 | match_type = ctm_succeeded; | ||
911 | 1126 | 1134 | ||
913 | 1127 | if (matched) | 1135 | if (match_type) |
914 | 1128 | { | 1136 | { |
915 | 1129 | ucbp->barrier_cache.sp = | 1137 | ucbp->barrier_cache.sp = |
916 | 1130 | _Unwind_GetGR (context, R_SP); | 1138 | _Unwind_GetGR (context, R_SP); |
918 | 1131 | ucbp->barrier_cache.bitpattern[0] = (_uw) matched; | 1139 | // ctm_succeeded_with_ptr_to_base really |
919 | 1140 | // means _c_t_m indirected the pointer | ||
920 | 1141 | // object. We have to reconstruct the | ||
921 | 1142 | // additional pointer layer by using a temporary. | ||
922 | 1143 | if (match_type == ctm_succeeded_with_ptr_to_base) | ||
923 | 1144 | { | ||
924 | 1145 | ucbp->barrier_cache.bitpattern[2] | ||
925 | 1146 | = (_uw) matched; | ||
926 | 1147 | ucbp->barrier_cache.bitpattern[0] | ||
927 | 1148 | = (_uw) &ucbp->barrier_cache.bitpattern[2]; | ||
928 | 1149 | } | ||
929 | 1150 | else | ||
930 | 1151 | ucbp->barrier_cache.bitpattern[0] = (_uw) matched; | ||
931 | 1132 | ucbp->barrier_cache.bitpattern[1] = (_uw) data; | 1152 | ucbp->barrier_cache.bitpattern[1] = (_uw) data; |
932 | 1133 | return _URC_HANDLER_FOUND; | 1153 | return _URC_HANDLER_FOUND; |
933 | 1134 | } | 1154 | } |
934 | 1135 | 1155 | ||
935 | === modified file 'gcc/expmed.c' | |||
936 | --- gcc/expmed.c 2011-01-18 19:06:14 +0000 | |||
937 | +++ gcc/expmed.c 2011-04-13 13:28:18 +0000 | |||
938 | @@ -720,7 +720,7 @@ | |||
939 | 720 | /* On big-endian machines, we count bits from the most significant. | 720 | /* On big-endian machines, we count bits from the most significant. |
940 | 721 | If the bit field insn does not, we must invert. */ | 721 | If the bit field insn does not, we must invert. */ |
941 | 722 | 722 | ||
943 | 723 | if (BITS_BIG_ENDIAN != BYTES_BIG_ENDIAN) | 723 | if (BITS_BIG_ENDIAN != BYTES_BIG_ENDIAN && !MEM_P (xop0)) |
944 | 724 | xbitpos = unit - bitsize - xbitpos; | 724 | xbitpos = unit - bitsize - xbitpos; |
945 | 725 | 725 | ||
946 | 726 | /* We have been counting XBITPOS within UNIT. | 726 | /* We have been counting XBITPOS within UNIT. |
947 | @@ -1564,7 +1564,7 @@ | |||
948 | 1564 | 1564 | ||
949 | 1565 | /* On big-endian machines, we count bits from the most significant. | 1565 | /* On big-endian machines, we count bits from the most significant. |
950 | 1566 | If the bit field insn does not, we must invert. */ | 1566 | If the bit field insn does not, we must invert. */ |
952 | 1567 | if (BITS_BIG_ENDIAN != BYTES_BIG_ENDIAN) | 1567 | if (BITS_BIG_ENDIAN != BYTES_BIG_ENDIAN && !MEM_P (xop0)) |
953 | 1568 | xbitpos = unit - bitsize - xbitpos; | 1568 | xbitpos = unit - bitsize - xbitpos; |
954 | 1569 | 1569 | ||
955 | 1570 | /* Now convert from counting within UNIT to counting in EXT_MODE. */ | 1570 | /* Now convert from counting within UNIT to counting in EXT_MODE. */ |
956 | 1571 | 1571 | ||
957 | === modified file 'gcc/final.c' | |||
958 | --- gcc/final.c 2011-02-08 10:51:58 +0000 | |||
959 | +++ gcc/final.c 2011-04-13 13:28:18 +0000 | |||
960 | @@ -2751,6 +2751,12 @@ | |||
961 | 2751 | if (filename == NULL) | 2751 | if (filename == NULL) |
962 | 2752 | return false; | 2752 | return false; |
963 | 2753 | 2753 | ||
964 | 2754 | #ifdef HAVE_ATTR_length | ||
965 | 2755 | /* Prevent duplicate line markers at the same location. */ | ||
966 | 2756 | if (get_attr_length (insn) == 0) | ||
967 | 2757 | return false; | ||
968 | 2758 | #endif | ||
969 | 2759 | |||
970 | 2754 | if (force_source_line | 2760 | if (force_source_line |
971 | 2755 | || filename != last_filename | 2761 | || filename != last_filename |
972 | 2756 | || last_linenum != linenum) | 2762 | || last_linenum != linenum) |
973 | 2757 | 2763 | ||
974 | === modified file 'gcc/ifcvt.c' | |||
975 | --- gcc/ifcvt.c 2011-02-08 12:07:29 +0000 | |||
976 | +++ gcc/ifcvt.c 2011-04-13 13:28:18 +0000 | |||
977 | @@ -311,6 +311,10 @@ | |||
978 | 311 | 311 | ||
979 | 312 | for (insn = start; ; insn = NEXT_INSN (insn)) | 312 | for (insn = start; ; insn = NEXT_INSN (insn)) |
980 | 313 | { | 313 | { |
981 | 314 | /* dwarf2out can't cope with conditional prologues. */ | ||
982 | 315 | if (NOTE_P (insn) && NOTE_KIND (insn) == NOTE_INSN_PROLOGUE_END) | ||
983 | 316 | return FALSE; | ||
984 | 317 | |||
985 | 314 | if (NOTE_P (insn) || DEBUG_INSN_P (insn)) | 318 | if (NOTE_P (insn) || DEBUG_INSN_P (insn)) |
986 | 315 | goto insn_done; | 319 | goto insn_done; |
987 | 316 | 320 | ||
988 | 317 | 321 | ||
989 | === modified file 'gcc/ipa-pure-const.c' | |||
990 | --- gcc/ipa-pure-const.c 2010-11-15 22:27:24 +0000 | |||
991 | +++ gcc/ipa-pure-const.c 2011-04-13 13:28:18 +0000 | |||
992 | @@ -422,7 +422,14 @@ | |||
993 | 422 | if (dump_file) | 422 | if (dump_file) |
994 | 423 | fprintf (dump_file, " Volatile stmt is not const/pure\n"); | 423 | fprintf (dump_file, " Volatile stmt is not const/pure\n"); |
995 | 424 | } | 424 | } |
997 | 425 | 425 | ||
998 | 426 | if (gimple_has_volatile_ops (stmt)) | ||
999 | 427 | { | ||
1000 | 428 | local->pure_const_state = IPA_NEITHER; | ||
1001 | 429 | if (dump_file) | ||
1002 | 430 | fprintf (dump_file, " Volatile stmt is not const/pure\n"); | ||
1003 | 431 | } | ||
1004 | 432 | |||
1005 | 426 | /* Look for loads and stores. */ | 433 | /* Look for loads and stores. */ |
1006 | 427 | walk_stmt_load_store_ops (stmt, local, check_load, check_store); | 434 | walk_stmt_load_store_ops (stmt, local, check_load, check_store); |
1007 | 428 | 435 | ||
1008 | 429 | 436 | ||
1009 | === added file 'gcc/testsuite/gcc.c-torture/compile/20110322-1.c' | |||
1010 | --- gcc/testsuite/gcc.c-torture/compile/20110322-1.c 1970-01-01 00:00:00 +0000 | |||
1011 | +++ gcc/testsuite/gcc.c-torture/compile/20110322-1.c 2011-04-13 13:28:18 +0000 | |||
1012 | @@ -0,0 +1,22 @@ | |||
1013 | 1 | void asn1_length_der (unsigned long int len, unsigned char *ans, int *ans_len) | ||
1014 | 2 | { | ||
1015 | 3 | int k; | ||
1016 | 4 | unsigned char temp[4]; | ||
1017 | 5 | if (len < 128) { | ||
1018 | 6 | if (ans != ((void *) 0)) | ||
1019 | 7 | ans[0] = (unsigned char) len; | ||
1020 | 8 | *ans_len = 1; | ||
1021 | 9 | } else { | ||
1022 | 10 | k = 0; | ||
1023 | 11 | while (len) { | ||
1024 | 12 | temp[k++] = len & 0xFF; | ||
1025 | 13 | len = len >> 8; | ||
1026 | 14 | } | ||
1027 | 15 | *ans_len = k + 1; | ||
1028 | 16 | if (ans != ((void *) 0)) { | ||
1029 | 17 | ans[0] = ((unsigned char) k & 0x7F) + 128; | ||
1030 | 18 | while (k--) | ||
1031 | 19 | ans[*ans_len - 1 - k] = temp[k]; | ||
1032 | 20 | } | ||
1033 | 21 | } | ||
1034 | 22 | } | ||
1035 | 0 | 23 | ||
1036 | === added file 'gcc/testsuite/gcc.dg/pr47763.c' | |||
1037 | --- gcc/testsuite/gcc.dg/pr47763.c 1970-01-01 00:00:00 +0000 | |||
1038 | +++ gcc/testsuite/gcc.dg/pr47763.c 2011-04-13 13:28:18 +0000 | |||
1039 | @@ -0,0 +1,9 @@ | |||
1040 | 1 | /* { dg-do compile } */ | ||
1041 | 2 | /* { dg-options "-O2 -funroll-loops -fdump-rtl-web" } */ | ||
1042 | 3 | |||
1043 | 4 | foo() | ||
1044 | 5 | { | ||
1045 | 6 | } | ||
1046 | 7 | |||
1047 | 8 | /* { dg-final { scan-rtl-dump-not "Web oldreg" "web" } } */ | ||
1048 | 9 | /* { dg-final { cleanup-rtl-dump "web" } } */ | ||
1049 | 0 | 10 | ||
1050 | === modified file 'gcc/testsuite/lib/target-supports.exp' | |||
1051 | --- gcc/testsuite/lib/target-supports.exp 2011-02-22 11:38:56 +0000 | |||
1052 | +++ gcc/testsuite/lib/target-supports.exp 2011-04-13 13:28:18 +0000 | |||
1053 | @@ -2722,8 +2722,9 @@ | |||
1054 | 2722 | if [info exists et_vector_alignment_reachable_saved] { | 2722 | if [info exists et_vector_alignment_reachable_saved] { |
1055 | 2723 | verbose "check_effective_target_vector_alignment_reachable: using cached result" 2 | 2723 | verbose "check_effective_target_vector_alignment_reachable: using cached result" 2 |
1056 | 2724 | } else { | 2724 | } else { |
1059 | 2725 | if { [check_effective_target_vect_aligned_arrays] | 2725 | if { ([check_effective_target_vect_aligned_arrays] |
1060 | 2726 | || [check_effective_target_natural_alignment_32] } { | 2726 | || [check_effective_target_natural_alignment_32]) |
1061 | 2727 | && !([istarget arm*-*-*] && [check_effective_target_arm_neon]) } { | ||
1062 | 2727 | set et_vector_alignment_reachable_saved 1 | 2728 | set et_vector_alignment_reachable_saved 1 |
1063 | 2728 | } else { | 2729 | } else { |
1064 | 2729 | set et_vector_alignment_reachable_saved 0 | 2730 | set et_vector_alignment_reachable_saved 0 |
1065 | 2730 | 2731 | ||
1066 | === modified file 'gcc/tree-ssa-copyrename.c' | |||
1067 | --- gcc/tree-ssa-copyrename.c 2011-01-20 10:36:29 +0000 | |||
1068 | +++ gcc/tree-ssa-copyrename.c 2011-04-13 13:28:18 +0000 | |||
1069 | @@ -225,6 +225,18 @@ | |||
1070 | 225 | ign2 = false; | 225 | ign2 = false; |
1071 | 226 | } | 226 | } |
1072 | 227 | 227 | ||
1073 | 228 | /* Don't coalesce if the new chosen root variable would be read-only. | ||
1074 | 229 | If both ign1 && ign2, then the root var of the larger partition | ||
1075 | 230 | wins, so reject in that case if any of the root vars is TREE_READONLY. | ||
1076 | 231 | Otherwise reject only if the root var, on which replace_ssa_name_symbol | ||
1077 | 232 | will be called below, is readonly. */ | ||
1078 | 233 | if ((TREE_READONLY (root1) && ign2) || (TREE_READONLY (root2) && ign1)) | ||
1079 | 234 | { | ||
1080 | 235 | if (debug) | ||
1081 | 236 | fprintf (debug, " : Readonly variable. No coalesce.\n"); | ||
1082 | 237 | return false; | ||
1083 | 238 | } | ||
1084 | 239 | |||
1085 | 228 | /* Don't coalesce if the two variables aren't type compatible . */ | 240 | /* Don't coalesce if the two variables aren't type compatible . */ |
1086 | 229 | if (!types_compatible_p (TREE_TYPE (root1), TREE_TYPE (root2)) | 241 | if (!types_compatible_p (TREE_TYPE (root1), TREE_TYPE (root2)) |
1087 | 230 | /* There is a disconnect between the middle-end type-system and | 242 | /* There is a disconnect between the middle-end type-system and |
1088 | 231 | 243 | ||
1089 | === modified file 'gcc/web.c' | |||
1090 | --- gcc/web.c 2010-01-26 16:27:34 +0000 | |||
1091 | +++ gcc/web.c 2011-04-13 13:28:18 +0000 | |||
1092 | @@ -350,7 +350,17 @@ | |||
1093 | 350 | FOR_BB_INSNS (bb, insn) | 350 | FOR_BB_INSNS (bb, insn) |
1094 | 351 | { | 351 | { |
1095 | 352 | unsigned int uid = INSN_UID (insn); | 352 | unsigned int uid = INSN_UID (insn); |
1097 | 353 | if (NONDEBUG_INSN_P (insn)) | 353 | |
1098 | 354 | if (NONDEBUG_INSN_P (insn) | ||
1099 | 355 | /* Ignore naked clobber. For example, reg 134 in the second insn | ||
1100 | 356 | of the following sequence will not be replaced. | ||
1101 | 357 | |||
1102 | 358 | (insn (clobber (reg:SI 134))) | ||
1103 | 359 | |||
1104 | 360 | (insn (set (reg:SI 0 r0) (reg:SI 134))) | ||
1105 | 361 | |||
1106 | 362 | Thus the later passes can optimize them away. */ | ||
1107 | 363 | && GET_CODE (PATTERN (insn)) != CLOBBER) | ||
1108 | 354 | { | 364 | { |
1109 | 355 | df_ref *use_rec; | 365 | df_ref *use_rec; |
1110 | 356 | df_ref *def_rec; | 366 | df_ref *def_rec; |
1111 | 357 | 367 | ||
1112 | === modified file 'libstdc++-v3/libsupc++/eh_arm.cc' | |||
1113 | --- libstdc++-v3/libsupc++/eh_arm.cc 2009-04-09 14:00:19 +0000 | |||
1114 | +++ libstdc++-v3/libsupc++/eh_arm.cc 2011-04-13 13:28:18 +0000 | |||
1115 | @@ -30,10 +30,11 @@ | |||
1116 | 30 | using namespace __cxxabiv1; | 30 | using namespace __cxxabiv1; |
1117 | 31 | 31 | ||
1118 | 32 | 32 | ||
1123 | 33 | // Given the thrown type THROW_TYPE, pointer to a variable containing a | 33 | // Given the thrown type THROW_TYPE, exception object UE_HEADER and a |
1124 | 34 | // pointer to the exception object THROWN_PTR_P and a type CATCH_TYPE to | 34 | // type CATCH_TYPE to compare against, return whether or not there is |
1125 | 35 | // compare against, return whether or not there is a match and if so, | 35 | // a match and if so, update *THROWN_PTR_P to point to either the |
1126 | 36 | // update *THROWN_PTR_P. | 36 | // type-matched object, or in the case of a pointer type, the object |
1127 | 37 | // pointed to by the pointer. | ||
1128 | 37 | 38 | ||
1129 | 38 | extern "C" __cxa_type_match_result | 39 | extern "C" __cxa_type_match_result |
1130 | 39 | __cxa_type_match(_Unwind_Exception* ue_header, | 40 | __cxa_type_match(_Unwind_Exception* ue_header, |
1131 | @@ -41,51 +42,51 @@ | |||
1132 | 41 | bool is_reference __attribute__((__unused__)), | 42 | bool is_reference __attribute__((__unused__)), |
1133 | 42 | void** thrown_ptr_p) | 43 | void** thrown_ptr_p) |
1134 | 43 | { | 44 | { |
1139 | 44 | bool forced_unwind = __is_gxx_forced_unwind_class(ue_header->exception_class); | 45 | bool forced_unwind |
1140 | 45 | bool foreign_exception = !forced_unwind && !__is_gxx_exception_class(ue_header->exception_class); | 46 | = __is_gxx_forced_unwind_class(ue_header->exception_class); |
1141 | 46 | bool dependent_exception = | 47 | bool foreign_exception |
1142 | 47 | __is_dependent_exception(ue_header->exception_class); | 48 | = !forced_unwind && !__is_gxx_exception_class(ue_header->exception_class); |
1143 | 49 | bool dependent_exception | ||
1144 | 50 | = __is_dependent_exception(ue_header->exception_class); | ||
1145 | 48 | __cxa_exception* xh = __get_exception_header_from_ue(ue_header); | 51 | __cxa_exception* xh = __get_exception_header_from_ue(ue_header); |
1146 | 49 | __cxa_dependent_exception *dx = __get_dependent_exception_from_ue(ue_header); | 52 | __cxa_dependent_exception *dx = __get_dependent_exception_from_ue(ue_header); |
1147 | 50 | const std::type_info* throw_type; | 53 | const std::type_info* throw_type; |
1148 | 54 | void *thrown_ptr = 0; | ||
1149 | 51 | 55 | ||
1150 | 52 | if (forced_unwind) | 56 | if (forced_unwind) |
1151 | 53 | throw_type = &typeid(abi::__forced_unwind); | 57 | throw_type = &typeid(abi::__forced_unwind); |
1152 | 54 | else if (foreign_exception) | 58 | else if (foreign_exception) |
1153 | 55 | throw_type = &typeid(abi::__foreign_exception); | 59 | throw_type = &typeid(abi::__foreign_exception); |
1154 | 56 | else if (dependent_exception) | ||
1155 | 57 | throw_type = __get_exception_header_from_obj | ||
1156 | 58 | (dx->primaryException)->exceptionType; | ||
1157 | 59 | else | 60 | else |
1161 | 60 | throw_type = xh->exceptionType; | 61 | { |
1162 | 61 | 62 | if (dependent_exception) | |
1163 | 62 | void* thrown_ptr = *thrown_ptr_p; | 63 | xh = __get_exception_header_from_obj (dx->primaryException); |
1164 | 64 | throw_type = xh->exceptionType; | ||
1165 | 65 | // We used to require the caller set the target of thrown_ptr_p, | ||
1166 | 66 | // but that's incorrect -- the EHABI makes no such requirement | ||
1167 | 67 | // -- and not all callers will set it. Fortunately callers that | ||
1168 | 68 | // do initialize will always pass us the value we calculate | ||
1169 | 69 | // here, so there's no backwards compatibility problem. | ||
1170 | 70 | thrown_ptr = __get_object_from_ue (ue_header); | ||
1171 | 71 | } | ||
1172 | 72 | |||
1173 | 73 | __cxa_type_match_result result = ctm_succeeded; | ||
1174 | 63 | 74 | ||
1175 | 64 | // Pointer types need to adjust the actual pointer, not | 75 | // Pointer types need to adjust the actual pointer, not |
1176 | 65 | // the pointer to pointer that is the exception object. | 76 | // the pointer to pointer that is the exception object. |
1177 | 66 | // This also has the effect of passing pointer types | 77 | // This also has the effect of passing pointer types |
1178 | 67 | // "by value" through the __cxa_begin_catch return value. | 78 | // "by value" through the __cxa_begin_catch return value. |
1179 | 68 | if (throw_type->__is_pointer_p()) | 79 | if (throw_type->__is_pointer_p()) |
1181 | 69 | thrown_ptr = *(void**) thrown_ptr; | 80 | { |
1182 | 81 | thrown_ptr = *(void**) thrown_ptr; | ||
1183 | 82 | // We need to indicate the indirection to our caller. | ||
1184 | 83 | result = ctm_succeeded_with_ptr_to_base; | ||
1185 | 84 | } | ||
1186 | 70 | 85 | ||
1187 | 71 | if (catch_type->__do_catch(throw_type, &thrown_ptr, 1)) | 86 | if (catch_type->__do_catch(throw_type, &thrown_ptr, 1)) |
1188 | 72 | { | 87 | { |
1189 | 73 | *thrown_ptr_p = thrown_ptr; | 88 | *thrown_ptr_p = thrown_ptr; |
1205 | 74 | 89 | return result; | |
1191 | 75 | if (typeid(*catch_type) == typeid (typeid(void*))) | ||
1192 | 76 | { | ||
1193 | 77 | const __pointer_type_info *catch_pointer_type = | ||
1194 | 78 | static_cast<const __pointer_type_info *> (catch_type); | ||
1195 | 79 | const __pointer_type_info *throw_pointer_type = | ||
1196 | 80 | static_cast<const __pointer_type_info *> (throw_type); | ||
1197 | 81 | |||
1198 | 82 | if (typeid (*catch_pointer_type->__pointee) != typeid (void) | ||
1199 | 83 | && (*catch_pointer_type->__pointee != | ||
1200 | 84 | *throw_pointer_type->__pointee)) | ||
1201 | 85 | return ctm_succeeded_with_ptr_to_base; | ||
1202 | 86 | } | ||
1203 | 87 | |||
1204 | 88 | return ctm_succeeded; | ||
1206 | 89 | } | 90 | } |
1207 | 90 | 91 | ||
1208 | 91 | return ctm_failed; | 92 | return ctm_failed; |
I am out of the office until 17/04/2011.
Note: This is an automated response to your message "[Merge]
lp:~ams-codesourcery/gcc-linaro/cs-merge-20110413 into lp:gcc-linaro"
sent on 13/4/2011 16:28:34.
This is the only notification you will receive while this person is away.