This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: RFC: Speeding up libstdc++.so with --dynamic-list-data


On Tue, Jan 09, 2007 at 07:52:42AM -0800, H. J. Lu wrote:
> > 
> > What about just --dynamic-list-cpp that enables the new behavior and 
> > implies --dynamic-list-cpp-typeinfo (I know that it is useless in this 
> > particular case, since C++ typeinfo is data, but in general such an 
> > option sounds more useful than only --dynamic-list-cpp-new).
> 
> I think you only need --dynamic-list-cpp-new for building libstdc++.so.
> -Bsymbolic-functions should be sufficient for other C++ shared
> libraries.
> 

Here is a patch for --dynamic-list-cpp-new with a testcase.


H.J.
---
ld/

2007-01-09  H.J. Lu  <hongjiu.lu@intel.com>

	* NEWS: Mention --dynamic-list-cpp-new.

	* ld.texinfo: Document --dynamic-list-cpp-new.

	* ldlang.c (lang_append_dynamic_list_cpp_new): New.
	* ldlang.h (lang_append_dynamic_list_cpp_new): Likewise.

	* lexsup.c (option_values): Add OPTION_DYNAMIC_LIST_CPP_NEW.
	(ld_options): Add entry for --dynamic-list-cpp-new.
	(parse_args): Handle OPTION_DYNAMIC_LIST_CPP_NEW.

ld/testsuite/

2007-01-09  H.J. Lu  <hongjiu.lu@intel.com>

	* ld-elf/del.cc: New.
	* ld-elf/dl5.cc: Likewise.
	* ld-elf/dl5.out: Likewise.
	* ld-elf/new.cc: Likewise.

	* ld-elf/shared.exp: Add --dynamic-list-cpp-new testcase.

--- ld/NEWS.new	2007-01-09 11:34:46.000000000 -0800
+++ ld/NEWS	2007-01-09 11:34:53.000000000 -0800
@@ -1,4 +1,7 @@
 -*- text -*-
+* ELF: Add --dynamic-list-cpp-new, which puts C++ operator new and
+  delete on the dynamic list.
+
 * ELF: Add -Bsymbolic-functions and --dynamic-list-data, builtin list
   for --dynamic-list, which puts global data symbols on the dynamic list.
 
--- ld/ld.texinfo.new	2007-01-09 11:22:59.000000000 -0800
+++ ld/ld.texinfo	2007-01-09 11:31:50.000000000 -0800
@@ -1155,6 +1155,11 @@ scope and node name.  See @ref{VERSION} 
 @item --dynamic-list-data
 Include all global data symbols to the dynamic list.
 
+@kindex --dynamic-list-cpp-new
+@item --dynamic-list-cpp-new
+Provide the builtin dynamic list for C++ operator new and delete.  It
+is mainly useful for building shared libstdc++.
+
 @kindex --dynamic-list-cpp-typeinfo
 @item --dynamic-list-cpp-typeinfo
 Provide the builtin dynamic list for C++ runtime type identification.
--- ld/ldlang.c.new	2007-01-09 11:22:59.000000000 -0800
+++ ld/ldlang.c	2007-01-09 11:22:59.000000000 -0800
@@ -7086,3 +7086,24 @@ lang_append_dynamic_list_cpp_typeinfo (v
 
   lang_append_dynamic_list (dynamic);
 }
+
+/* Append the list of C++ operator new and delete dynamic symbols to the
+   existing one.  */
+
+void
+lang_append_dynamic_list_cpp_new (void)
+{
+  const char * symbols [] =
+    {
+      "operator new*",
+      "operator delete*"
+    };
+  struct bfd_elf_version_expr *dynamic = NULL;
+  unsigned int i;
+
+  for (i = 0; i < ARRAY_SIZE (symbols); i++)
+    dynamic = lang_new_vers_pattern (dynamic, symbols [i], "C++",
+				     FALSE);
+
+  lang_append_dynamic_list (dynamic);
+}
--- ld/ldlang.h.new	2006-10-24 23:49:21.000000000 -0700
+++ ld/ldlang.h	2007-01-09 11:22:59.000000000 -0800
@@ -607,6 +607,7 @@ extern void lang_register_vers_node
   (const char *, struct bfd_elf_version_tree *, struct bfd_elf_version_deps *);
 extern void lang_append_dynamic_list (struct bfd_elf_version_expr *);
 extern void lang_append_dynamic_list_cpp_typeinfo (void);
+extern void lang_append_dynamic_list_cpp_new (void);
 bfd_boolean unique_section_p
   (const asection *);
 extern void lang_add_unique
--- ld/lexsup.c.new	2007-01-09 11:22:59.000000000 -0800
+++ ld/lexsup.c	2007-01-09 11:24:13.000000000 -0800
@@ -108,6 +108,7 @@ enum option_values
   OPTION_VERSION_SCRIPT,
   OPTION_VERSION_EXPORTS_SECTION,
   OPTION_DYNAMIC_LIST,
+  OPTION_DYNAMIC_LIST_CPP_NEW,
   OPTION_DYNAMIC_LIST_CPP_TYPEINFO,
   OPTION_DYNAMIC_LIST_DATA,
   OPTION_WARN_COMMON,
@@ -508,6 +509,8 @@ static const struct ld_option ld_options
     '\0', NULL, N_("Bind global function references locally"), ONE_DASH },
   { {"dynamic-list-data", no_argument, NULL, OPTION_DYNAMIC_LIST_DATA},
     '\0', NULL, N_("Add data symbols to dynamic list"), TWO_DASHES },
+  { {"dynamic-list-cpp-new", no_argument, NULL, OPTION_DYNAMIC_LIST_CPP_NEW},
+    '\0', NULL, N_("Use C++ operator new/delete dynamic list"), TWO_DASHES },
   { {"dynamic-list-cpp-typeinfo", no_argument, NULL, OPTION_DYNAMIC_LIST_CPP_TYPEINFO},
     '\0', NULL, N_("Use C++ typeinfo dynamic list"), TWO_DASHES },
   { {"dynamic-list", required_argument, NULL, OPTION_DYNAMIC_LIST},
@@ -1257,6 +1260,10 @@ parse_args (unsigned argc, char **argv)
 	  lang_append_dynamic_list_cpp_typeinfo ();
 	  link_info.dynamic = TRUE;
 	  break;
+	case OPTION_DYNAMIC_LIST_CPP_NEW:
+	  lang_append_dynamic_list_cpp_new ();
+	  link_info.dynamic = TRUE;
+	  break;
 	case OPTION_DYNAMIC_LIST:
 	  /* This option indicates a small script that only specifies
 	     a dynamic list.  Read it, but don't assume that we've
--- ld/testsuite/ld-elf/del.cc.new	2007-01-09 14:48:18.000000000 -0800
+++ ld/testsuite/ld-elf/del.cc	2007-01-09 12:58:35.000000000 -0800
@@ -0,0 +1,29 @@
+#include <new>
+
+extern "C" void free (void *);
+
+void
+operator delete (void *ptr, const std::nothrow_t&) throw ()
+{
+  if (ptr)
+    free (ptr);
+}
+
+void
+operator delete (void *ptr) throw ()
+{
+  if (ptr)
+    free (ptr);
+}
+
+void
+operator delete[] (void *ptr) throw ()
+{
+  ::operator delete (ptr);
+}
+
+void
+operator delete[] (void *ptr, const std::nothrow_t&) throw ()
+{
+  ::operator delete (ptr);
+}
--- ld/testsuite/ld-elf/dl5.cc.new	2007-01-09 14:48:18.000000000 -0800
+++ ld/testsuite/ld-elf/dl5.cc	2007-01-09 14:46:22.000000000 -0800
@@ -0,0 +1,61 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <new>
+
+int pass = 0;
+
+void *
+operator new (size_t sz, const std::nothrow_t&) throw ()
+{
+  void *p;
+  pass++;
+  p = malloc(sz);
+  return p;
+}
+
+void *
+operator new (size_t sz) throw (std::bad_alloc)
+{
+  void *p;
+  pass++;
+  p = malloc(sz);
+  return p;
+}
+
+void
+operator delete (void *ptr) throw ()
+{
+  pass++;
+  if (ptr)
+    free (ptr);
+}
+
+class A 
+{
+public:
+  A() {}
+  ~A() { }
+  int a;
+  int b;
+};
+
+
+int
+main (void)
+{
+  A *bb = new A[10];
+  delete [] bb;
+  bb = new (std::nothrow) A [10];
+  delete [] bb;
+
+  if (pass == 4)
+    {
+      printf ("PASS\n");
+      return 0;
+    }
+  else
+    {
+      printf ("FAIL\n");
+      return 1;
+    }
+}
--- ld/testsuite/ld-elf/dl5.out.new	2007-01-09 14:48:18.000000000 -0800
+++ ld/testsuite/ld-elf/dl5.out	2007-01-09 14:47:38.000000000 -0800
@@ -0,0 +1 @@
+PASS
--- ld/testsuite/ld-elf/new.cc.new	2007-01-09 14:48:18.000000000 -0800
+++ ld/testsuite/ld-elf/new.cc	2007-01-09 11:49:37.000000000 -0800
@@ -0,0 +1,48 @@
+#include <new>
+#include <exception_defines.h>
+
+using std::bad_alloc;
+
+extern "C" void *malloc (std::size_t);
+extern "C" void abort (void);
+
+void *
+operator new (std::size_t sz, const std::nothrow_t&) throw()
+{
+  void *p;
+
+  /* malloc (0) is unpredictable; avoid it.  */
+  if (sz == 0)
+    sz = 1;
+  p = (void *) malloc (sz);
+  return p;
+}
+
+void *
+operator new (std::size_t sz) throw (std::bad_alloc)
+{
+  void *p;
+
+  /* malloc (0) is unpredictable; avoid it.  */
+  if (sz == 0)
+    sz = 1;
+  p = (void *) malloc (sz);
+  while (p == 0)
+    {
+      ::abort();
+    }
+
+  return p;
+}
+
+void*
+operator new[] (std::size_t sz) throw (std::bad_alloc)
+{
+  return ::operator new(sz);
+}
+
+void *
+operator new[] (std::size_t sz, const std::nothrow_t& nothrow) throw()
+{
+  return ::operator new(sz, nothrow);
+}
--- ld/testsuite/ld-elf/shared.exp.new	2007-01-09 11:22:59.000000000 -0800
+++ ld/testsuite/ld-elf/shared.exp	2007-01-09 14:47:17.000000000 -0800
@@ -171,6 +171,9 @@ set build_cxx_tests {
   {"Build libdl3a.so with --dynamic-list-cpp-typeinfo"
    "-shared -Wl,--dynamic-list-cpp-typeinfo" "-fPIC"
    {dl3.cc} {} "libdl3c.so" "c++"}
+  {"Build libdnew.so with -Bsymbolic-functions -dynamic-list-cpp-new"
+   "-shared -Wl,-Bsymbolic-functions,--dynamic-list-cpp-new" "-fPIC"
+   {del.cc new.cc} {} "libnew.so" "c++"}
 }
 
 set run_cxx_tests {
@@ -183,6 +186,9 @@ set run_cxx_tests {
     {"Run with libdl3c.so"
      "tmpdir/libdl3c.so" ""
      {dl3main.cc} "dl3c" "dl3a.out" "" "c++"}
+    {"Run with libnew.so"
+     "tmpdir/libnew.so" ""
+     {dl5.cc} "dl5" "dl5.out" "" "c++"}
 }
 
 run_cc_link_tests $build_cxx_tests


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]