aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorKaveh R. Ghazi <ghazi@caip.rutgers.edu>2003-05-08 13:45:38 +0000
committerKaveh Ghazi <ghazi@gcc.gnu.org>2003-05-08 13:45:38 +0000
commit7dc61d6cfb77ab9d3c59cc04d4bfb732bdb5f7d0 (patch)
tree5a03f0bcac76ac17d2d946ba52f8619024d49c7b /gcc
parent53415fa1a1f7b3c13dde3aa0a73f35ae4dcc335b (diff)
downloadgcc-7dc61d6cfb77ab9d3c59cc04d4bfb732bdb5f7d0.zip
gcc-7dc61d6cfb77ab9d3c59cc04d4bfb732bdb5f7d0.tar.gz
gcc-7dc61d6cfb77ab9d3c59cc04d4bfb732bdb5f7d0.tar.bz2
builtins.c (readonly_data_expr): New function.
gcc: * builtins.c (readonly_data_expr): New function. (expand_builtin_memmove): Optimize any rodata source, not just strings. testsuite gcc.c-torture/execute/string-opt-19.c: Add general rodata tests. (bcopy): Call memmove. From-SVN: r66597
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog6
-rw-r--r--gcc/builtins.c28
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.c-torture/execute/string-opt-19.c70
4 files changed, 88 insertions, 21 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index fc627a1..c099384 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,9 @@
+2003-05-08 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
+
+ * builtins.c (readonly_data_expr): New function.
+ (expand_builtin_memmove): Optimize any rodata source, not just
+ strings.
+
2003-05-07 David Mosberger <davidm@hpl.hp.com>
* unwind-libunwind.c (_Unwind_FindEnclosingFunction): New.
diff --git a/gcc/builtins.c b/gcc/builtins.c
index c309997..6745300 100644
--- a/gcc/builtins.c
+++ b/gcc/builtins.c
@@ -168,6 +168,7 @@ static tree fold_builtin_inf PARAMS ((tree, int));
static tree fold_builtin_nan PARAMS ((tree, tree, int));
static int validate_arglist PARAMS ((tree, ...));
static tree fold_trunc_transparent_mathfn PARAMS ((tree));
+static bool readonly_data_expr PARAMS ((tree));
/* Return the alignment in bits of EXP, a pointer valued expression.
But don't return more than MAX_ALIGN no matter what.
@@ -2423,10 +2424,16 @@ expand_builtin_memmove (arglist, target, mode)
if (src_align == 0)
return 0;
- /* If src is a string constant and strings are not writable,
- we can use normal memcpy. */
- if (!flag_writable_strings && c_getstr (src))
- return expand_builtin_memcpy (arglist, target, mode, 0);
+ /* If src is categorized for a readonly section we can use
+ normal memcpy. */
+ if (readonly_data_expr (src))
+ {
+ tree const fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
+ if (!fn)
+ return 0;
+ return expand_expr (build_function_call_expr (fn, arglist),
+ target, mode, EXPAND_NORMAL);
+ }
/* Otherwise, call the normal function. */
return 0;
@@ -5449,3 +5456,16 @@ purge_builtin_constant_p ()
}
}
+/* Returns true is EXP represents data that would potentially reside
+ in a readonly section. */
+
+static bool
+readonly_data_expr (tree exp)
+{
+ STRIP_NOPS (exp);
+
+ if (TREE_CODE (exp) == ADDR_EXPR)
+ return decl_readonly_section (TREE_OPERAND (exp, 0), 0);
+ else
+ return false;
+}
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index baf9936..a11244a 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2003-05-08 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
+
+ gcc.c-torture/execute/string-opt-19.c: Add general rodata tests.
+ (bcopy): Call memmove.
+
2003-05-08 Roger Sayle <roger@eyesopen.com>
* g77.f-torture/compile/8485.f: New test case.
diff --git a/gcc/testsuite/gcc.c-torture/execute/string-opt-19.c b/gcc/testsuite/gcc.c-torture/execute/string-opt-19.c
index 92b84c6..3382316 100644
--- a/gcc/testsuite/gcc.c-torture/execute/string-opt-19.c
+++ b/gcc/testsuite/gcc.c-torture/execute/string-opt-19.c
@@ -13,10 +13,61 @@ extern int memcmp (const void *, const void *, size_t);
const char s1[] = "123";
char p[32] = "";
+static const struct foo
+{
+ char *s;
+ double d;
+ long l;
+} foo[] =
+{
+ { "hello world1", 3.14159, 101L },
+ { "hello world2", 3.14159, 102L },
+ { "hello world3", 3.14159, 103L },
+ { "hello world4", 3.14159, 104L },
+ { "hello world5", 3.14159, 105L },
+ { "hello world6", 3.14159, 106L }
+};
+
+static const struct bar
+{
+ char *s;
+ const struct foo f[3];
+} bar[] =
+{
+ {
+ "hello world10",
+ {
+ { "hello1", 3.14159, 201L },
+ { "hello2", 3.14159, 202L },
+ { "hello3", 3.14159, 203L },
+ }
+ },
+ {
+ "hello world11",
+ {
+ { "hello4", 3.14159, 204L },
+ { "hello5", 3.14159, 205L },
+ { "hello6", 3.14159, 206L },
+ }
+ }
+};
+
+static const int baz[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 0 };
+
int main()
{
- int i;
const char *s;
+ struct foo f1[sizeof foo/sizeof*foo];
+ struct bar b1[sizeof bar/sizeof*bar];
+ int bz[sizeof baz/sizeof*baz];
+
+ if (memmove (f1, foo, sizeof (foo)) != f1 || memcmp (f1, foo, sizeof(foo)))
+ abort();
+ if (memmove (b1, bar, sizeof (bar)) != b1 || memcmp (b1, bar, sizeof(bar)))
+ abort();
+ bcopy (baz, bz, sizeof (baz));
+ if (memcmp (bz, baz, sizeof(baz)))
+ abort();
if (memmove (p, "abcde", 6) != p || memcmp (p, "abcde", 6))
abort ();
@@ -70,20 +121,5 @@ __attribute__ ((noinline))
static void
bcopy (const void *s, void *d, size_t n)
{
-#ifdef __OPTIMIZE__
- abort ();
-#else
- char *dst = (char *) d;
- const char *src = (const char *) s;
- if (src < dst)
- {
- dst += n;
- src += n;
- while (n--)
- *--dst = *--src;
- }
- else
- while (n--)
- *dst++ = *src++;
-#endif
+ memmove (d, s, n);
}