diff mbox

[jit] Add a test of using very long names

Message ID 1411744469-565-1-git-send-email-dmalcolm@redhat.com
State New
Headers show

Commit Message

David Malcolm Sept. 26, 2014, 3:14 p.m. UTC
Committed to branch dmalcolm/jit:

gcc/testsuite/ChangeLog.jit:
	* jit.dg/test-long-names.c: New test case.
	* jit.dg/all-non-failing-tests.h: Add test-long-names.c
	* jit.dg/test-combination.c (create_code): Likewise.
	(verify_code): Likewise.
	* jit.dg/test-threads.c (testcases): Likewise.
---
 gcc/testsuite/jit.dg/all-non-failing-tests.h |   7 ++
 gcc/testsuite/jit.dg/test-combination.c      |   2 +
 gcc/testsuite/jit.dg/test-long-names.c       | 112 +++++++++++++++++++++++++++
 gcc/testsuite/jit.dg/test-threads.c          |   3 +
 4 files changed, 124 insertions(+)
 create mode 100644 gcc/testsuite/jit.dg/test-long-names.c

Comments

Mike Stump Sept. 26, 2014, 6:45 p.m. UTC | #1
On Sep 26, 2014, at 8:14 AM, David Malcolm <dmalcolm@redhat.com> wrote:
> 	* jit.dg/test-long-names.c: New test case.

> +/* 65KB */
> +#define NAME_LENGTH (65 * 1024)

65K was a tiny name back in 1999, 16M was a large name then.  Today, 16M is tiny enough.  And yeah, this was a customer bug report, just normal C++ code with template manglings back then and yeah, we fixed the bug and tested it out to 16M to ensure we would not hit another bug in the next decade.  As far as I know, we didn’t.  If you want to ensure it works nicely for the next decade test out to, say, 128M and then throw that test case away.  I’d be curious if you hit any problems at 128M.
David Malcolm Sept. 26, 2014, 7:31 p.m. UTC | #2
On Fri, 2014-09-26 at 11:45 -0700, Mike Stump wrote:
> On Sep 26, 2014, at 8:14 AM, David Malcolm <dmalcolm@redhat.com>
> wrote:
> > 	* jit.dg/test-long-names.c: New test case.
> 
> > +/* 65KB */
> > +#define NAME_LENGTH (65 * 1024)
> 
> 65K was a tiny name back in 1999, 16M was a large name then.  Today,
> 16M is tiny enough.  And yeah, this was a customer bug report, just
> normal C++ code with template manglings back then and yeah, we fixed
> the bug and tested it out to 16M to ensure we would not hit another
> bug in the next decade.  As far as I know, we didn’t.  If you want to
> ensure it works nicely for the next decade test out to, say, 128M and
> then throw that test case away.  I’d be curious if you hit any
> problems at 128M.

Out of curiosity I tried upping NAME_LENGTH to 129M.

The compiler handled it fine, but FWIW "as" seems to be stuck here:

(gdb) bt
#0  0x0000000000411730 in input_scrub_next_buffer (bufp=bufp@entry=0x693340) at input-scrub.c:390
#1  0x000000000041efab in read_a_source_file (name=<optimized out>) at read.c:768
#2  0x0000000000404188 in perform_an_assembly_pass (argv=0x88bee8, argc=<optimized out>) at as.c:1095
#3  main (argc=2, argv=0x88bee0) at as.c:1242

whilst reading a 952M .s file.

(binutils-2.23.88.0.1-13.fc20.x86_64, fwiw)
Mike Stump Sept. 28, 2014, 3 p.m. UTC | #3
On Sep 26, 2014, at 12:31 PM, David Malcolm <dmalcolm@redhat.com> wrote:
> On Fri, 2014-09-26 at 11:45 -0700, Mike Stump wrote:
>> On Sep 26, 2014, at 8:14 AM, David Malcolm <dmalcolm@redhat.com>
>> wrote:
>>> 	* jit.dg/test-long-names.c: New test case.
>> 
>>> +/* 65KB */
>>> +#define NAME_LENGTH (65 * 1024)
>> 
>> 65K was a tiny name back in 1999, 16M was a large name then.  Today,
>> 16M is tiny enough.  And yeah, this was a customer bug report, just
>> normal C++ code with template manglings back then and yeah, we fixed
>> the bug and tested it out to 16M to ensure we would not hit another
>> bug in the next decade.  As far as I know, we didn’t.  If you want to
>> ensure it works nicely for the next decade test out to, say, 128M and
>> then throw that test case away.  I’d be curious if you hit any
>> problems at 128M.
> 
> Out of curiosity I tried upping NAME_LENGTH to 129M.
> 
> The compiler handled it fine, but FWIW "as" seems to be stuck here

:-(  Then, it doesn’t work.

I’d report the as bug.  Also, you might try binary searching for the limit.  Hopefully 16M works just fine.  If it doesn’t, then someone broke it recently.

I tested a simple program on my machine and got it up to 31M for gcc and 512M for clang.  gcc died as 32M.  clang, well, I grew impatient waiting for the compile times.  512M should bee good for the next 100 years I suspect.  31M is likely fine for the next 2 decades, though, that bug should be fixed.

gcc died like this for me:

gcc: internal compiler error: Illegal instruction: 4 (program cc1)

:-(

$ cat t.c
#include <stdio.h>

/* gcc works to 31, fails as 32, clang goes beyond 512 */

#define M 32*1024*1024

char buf[M+1];

int main() {
  int i;
  for (i = 0; i < M; ++i)
    buf[i] = '0';
  printf ("#include <stdio.h>\n\
\n\
int i%s;\n\
\n\
int main() {\n\
  ++i%s;\n\
  return 0;\n\
}\n\
", buf, buf);

  return 0;
}
diff mbox

Patch

diff --git a/gcc/testsuite/jit.dg/all-non-failing-tests.h b/gcc/testsuite/jit.dg/all-non-failing-tests.h
index 5f7b2ec..10d7199 100644
--- a/gcc/testsuite/jit.dg/all-non-failing-tests.h
+++ b/gcc/testsuite/jit.dg/all-non-failing-tests.h
@@ -102,6 +102,13 @@ 
 #undef create_code
 #undef verify_code
 
+/* test-long-names.c */
+#define create_code create_code_long_names
+#define verify_code verify_code_long_names
+#include "test-long-names.c"
+#undef create_code
+#undef verify_code
+
 /* test-quadratic.c */
 #define create_code create_code_quadratic
 #define verify_code verify_code_quadratic
diff --git a/gcc/testsuite/jit.dg/test-combination.c b/gcc/testsuite/jit.dg/test-combination.c
index 9d3a535..06ba902 100644
--- a/gcc/testsuite/jit.dg/test-combination.c
+++ b/gcc/testsuite/jit.dg/test-combination.c
@@ -28,6 +28,7 @@  create_code (gcc_jit_context *ctxt, void * user_data)
   create_code_functions (ctxt, user_data);
   create_code_hello_world (ctxt, user_data);
   create_code_linked_list (ctxt, user_data);
+  create_code_long_names (ctxt, user_data);
   create_code_quadratic (ctxt, user_data);
   create_code_nested_loop (ctxt, user_data);
   create_code_reading_struct  (ctxt, user_data);
@@ -54,6 +55,7 @@  verify_code (gcc_jit_context *ctxt, gcc_jit_result *result)
   verify_code_functions (ctxt, result);
   verify_code_hello_world (ctxt, result);
   verify_code_linked_list (ctxt, result);
+  verify_code_long_names (ctxt, result);
   verify_code_quadratic (ctxt, result);
   verify_code_nested_loop (ctxt, result);
   verify_code_reading_struct (ctxt, result);
diff --git a/gcc/testsuite/jit.dg/test-long-names.c b/gcc/testsuite/jit.dg/test-long-names.c
new file mode 100644
index 0000000..0fc7e67
--- /dev/null
+++ b/gcc/testsuite/jit.dg/test-long-names.c
@@ -0,0 +1,112 @@ 
+/* Test of using the API with very long names.  */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+#include "libgccjit.h"
+
+#include "harness.h"
+
+/* 65KB */
+#define NAME_LENGTH (65 * 1024)
+
+static struct long_names
+{
+  char struct_name[NAME_LENGTH];
+  char fn_name[NAME_LENGTH];
+  char local_name[NAME_LENGTH];
+  char block_name[NAME_LENGTH];
+} long_names;
+
+static void
+populate_name (const char *prefix, char *buffer)
+{
+  int i;
+
+  /* Begin with the given prefix: */
+  sprintf (buffer, prefix);
+
+  /* Populate the rest of the buffer with 0123456789 repeatedly: */
+  for (i = strlen (prefix); i < NAME_LENGTH - 1; i++)
+    buffer[i] = '0' + (i % 10);
+
+  /* NIL-terminate the buffer: */
+  buffer[NAME_LENGTH - 1] = '\0';
+}
+
+static void
+populate_names (void)
+{
+  populate_name ("struct_", long_names.struct_name);
+  populate_name ("test_fn_", long_names.fn_name);
+  populate_name ("local_", long_names.local_name);
+  populate_name ("block_", long_names.block_name);
+}
+
+void
+create_code (gcc_jit_context *ctxt, void *user_data)
+{
+  /* Where "ETC" is a very long suffix, let's try to inject the
+     equivalent of:
+
+       struct struct_ETC;
+
+       int
+       test_fn_ETC ()
+       {
+	  int local_ETC;
+	  local_ETC = 42;
+	  return local_ETC;
+       }
+
+     to verify that the API copes with such long names.  */
+
+  populate_names ();
+
+  gcc_jit_type *int_type =
+    gcc_jit_context_get_type (ctxt, GCC_JIT_TYPE_INT);
+
+  /* We don't yet use this struct.  */
+  (void)gcc_jit_context_new_opaque_struct (ctxt, NULL,
+					   long_names.struct_name);
+
+  gcc_jit_function *test_fn =
+    gcc_jit_context_new_function (ctxt, NULL,
+				  GCC_JIT_FUNCTION_EXPORTED,
+				  int_type,
+				  long_names.fn_name,
+				  0, NULL,
+				  0);
+  gcc_jit_lvalue *local =
+    gcc_jit_function_new_local (test_fn,
+				NULL,
+				int_type,
+				long_names.local_name);
+
+  gcc_jit_block *block =
+    gcc_jit_function_new_block (test_fn, long_names.block_name);
+
+  gcc_jit_block_add_assignment (
+    block,
+    NULL,
+    local,
+    gcc_jit_context_new_rvalue_from_int (ctxt, int_type, 42));
+
+  gcc_jit_block_end_with_return (
+    block, NULL,
+    gcc_jit_lvalue_as_rvalue (local));
+}
+
+void
+verify_code (gcc_jit_context *ctxt, gcc_jit_result *result)
+{
+  CHECK_NON_NULL (result);
+
+  typedef int (*my_fn_type) (void);
+  CHECK_NON_NULL (result);
+  my_fn_type my_fn =
+    (my_fn_type)gcc_jit_result_get_code (result, long_names.fn_name);
+  CHECK_NON_NULL (my_fn);
+  int val = my_fn ();
+  CHECK_VALUE (val, 42);
+}
diff --git a/gcc/testsuite/jit.dg/test-threads.c b/gcc/testsuite/jit.dg/test-threads.c
index e3dd69f..efa146d 100644
--- a/gcc/testsuite/jit.dg/test-threads.c
+++ b/gcc/testsuite/jit.dg/test-threads.c
@@ -124,6 +124,9 @@  const struct testcase testcases[] = {
   {"linked_list",
    create_code_linked_list,
    verify_code_linked_list},
+  {"long_names",
+   create_code_long_names,
+   verify_code_long_names},
   {"quadratic",
    create_code_quadratic,
    verify_code_quadratic},