public inbox for binutils@sourceware.org
 help / color / mirror / Atom feed
* [PATCH][GOLD] Add make_elf_object target hooks.
@ 2009-08-18  3:12 Doug Kwan (關振德)
  2009-08-18 14:41 ` Ian Lance Taylor
  0 siblings, 1 reply; 6+ messages in thread
From: Doug Kwan (關振德) @ 2009-08-18  3:12 UTC (permalink / raw)
  To: binutils

[-- Attachment #1: Type: text/plain, Size: 589 bytes --]

Hi,

    This patch adds hooks in the Target class for creating ELF objects
via a target.  The hooks are useful for targets requiring
target-specific extension to the existing ELF object classes via
sub-classing.  This is tested on x86_64-unknown-linux-gnu.

-Doug

2009-08-17  Doug Kwan  <dougkwan@google.com>

	* object.cc(make_elf_sized_object): Find target and ask target to
	make an ELF object.
	* target.cc: Include dynobj.h.
	(make_elf_object_implementation): New.
 	(Target::do_make_elf_object): New.
	* target.h (Target::make_elf_object): New.
	(Target::do_make_elf_object): New.

[-- Attachment #2: patch.txt --]
[-- Type: text/plain, Size: 6467 bytes --]

Index: gold/object.cc
===================================================================
RCS file: /cvs/src/src/gold/object.cc,v
retrieving revision 1.97
diff -u -p -r1.97 object.cc
--- gold/object.cc	5 Aug 2009 20:51:56 -0000	1.97
+++ gold/object.cc	17 Aug 2009 22:32:59 -0000
@@ -2237,27 +2237,18 @@ Object*
 make_elf_sized_object(const std::string& name, Input_file* input_file,
 		      off_t offset, const elfcpp::Ehdr<size, big_endian>& ehdr)
 {
-  int et = ehdr.get_e_type();
-  if (et == elfcpp::ET_REL)
+  Target* target = select_target(ehdr.get_e_machine(), size, big_endian,
+				 ehdr.get_e_ident()[elfcpp::EI_OSABI],
+				 ehdr.get_e_ident()[elfcpp::EI_ABIVERSION]);
+  if (target == NULL)
     {
-      Sized_relobj<size, big_endian>* obj =
-	new Sized_relobj<size, big_endian>(name, input_file, offset, ehdr);
-      obj->setup(ehdr);
-      return obj;
-    }
-  else if (et == elfcpp::ET_DYN)
-    {
-      Sized_dynobj<size, big_endian>* obj =
-	new Sized_dynobj<size, big_endian>(name, input_file, offset, ehdr);
-      obj->setup(ehdr);
-      return obj;
-    }
-  else
-    {
-      gold_error(_("%s: unsupported ELF file type %d"),
-		 name.c_str(), et);
+      gold_fatal(_("%s: unsupported ELF machine number %d"),
+		 name.c_str(), ehdr.get_e_machine());
       return NULL;
     }
+
+  return target->make_elf_object<size, big_endian>(name, input_file, offset,
+						   ehdr);
 }
 
 } // End anonymous namespace.
Index: gold/target.cc
===================================================================
RCS file: /cvs/src/src/gold/target.cc,v
retrieving revision 1.1
diff -u -p -r1.1 target.cc
--- gold/target.cc	5 Jun 2009 21:32:56 -0000	1.1
+++ gold/target.cc	17 Aug 2009 22:32:59 -0000
@@ -22,6 +22,7 @@
 
 #include "gold.h"
 #include "target.h"
+#include "dynobj.h"
 
 namespace gold
 {
@@ -56,3 +57,94 @@ Target::do_is_local_label_name (const ch
 }
 
 } // End namespace gold.
+
+namespace
+{
+
+using namespace gold;
+
+// Implementations of methods Target::do_make_elf_object are almost identical
+// except for the address sizes and endianities.  So we extract this
+// into a template.
+
+template<int size, bool big_endian>
+inline Object*
+make_elf_object_implementation(
+    const std::string& name,
+    Input_file* input_file,
+    off_t offset,
+    const elfcpp::Ehdr<size, big_endian>& ehdr)
+{
+  int et = ehdr.get_e_type();
+  if (et == elfcpp::ET_REL)
+    {
+      Sized_relobj<size, big_endian>* obj =
+	new Sized_relobj<size, big_endian>(name, input_file, offset, ehdr);
+      obj->setup(ehdr);
+      return obj;
+    }
+  else if (et == elfcpp::ET_DYN)
+    {
+      Sized_dynobj<size, big_endian>* obj =
+	new Sized_dynobj<size, big_endian>(name, input_file, offset, ehdr);
+      obj->setup(ehdr);
+      return obj;
+    }
+  else
+    {
+      gold_error(_("%s: unsupported ELF file type %d"),
+		 name.c_str(), et);
+      return NULL;
+    }
+}
+
+} // End anonymous namespace.
+
+namespace gold
+{
+
+// Make an ELF object called NAME by reading INPUT_FILE at OFFSET.  EHDR
+// is the ELF header of the object.  There are four versions of this
+// for different address sizes and endianities.
+
+#ifdef HAVE_TARGET_32_LITTLE
+Object*
+Target::do_make_elf_object(const std::string& name, Input_file* input_file,
+			   off_t offset, const elfcpp::Ehdr<32, false>& ehdr)
+{
+  return make_elf_object_implementation<32, false>(name, input_file, offset,
+						   ehdr);
+}
+#endif
+
+#ifdef HAVE_TARGET_32_BIG
+Object*
+Target::do_make_elf_object(const std::string& name, Input_file* input_file,
+			   off_t offset, const elfcpp::Ehdr<32, true>& ehdr)
+{
+  return make_elf_object_implementation<32, true>(name, input_file, offset,
+						  ehdr);
+}
+#endif
+
+#ifdef HAVE_TARGET_64_LITTLE
+Object*
+Target::do_make_elf_object(const std::string& name, Input_file* input_file,
+			   off_t offset, const elfcpp::Ehdr<64, false>& ehdr)
+{
+  return make_elf_object_implementation<64, false>(name, input_file, offset,
+						   ehdr);
+}
+#endif
+
+#ifdef HAVE_TARGET_64_BIG
+Object*
+Target::do_make_elf_object(const std::string& name, Input_file* input_file,
+			   off_t offset, const elfcpp::Ehdr<64, true>& ehdr)
+{
+  return make_elf_object_implementation<64, true>(name, input_file, offset,
+						  ehdr);
+}
+#endif
+
+} // End namespace gold.
Index: gold/target.h
===================================================================
RCS file: /cvs/src/src/gold/target.h,v
retrieving revision 1.34
diff -u -p -r1.34 target.h
--- gold/target.h	22 Jun 2009 06:51:53 -0000	1.34
+++ gold/target.h	17 Aug 2009 22:33:00 -0000
@@ -216,6 +216,13 @@ class Target
   is_local_label_name(const char* name) const
   { return this->do_is_local_label_name(name); }
 
+  // Make an ELF object.
+  template<int size, bool big_endian>
+  Object*
+  make_elf_object(const std::string& name, Input_file* input_file,
+		  off_t offset, const elfcpp::Ehdr<size, big_endian>& ehdr)
+  { return this->do_make_elf_object(name, input_file, offset, ehdr); }
+
  protected:
   // This struct holds the constant information for a child class.  We
   // use a struct to avoid the overhead of virtual function calls for
@@ -301,6 +308,37 @@ class Target
   virtual bool
   do_is_local_label_name(const char*) const;
 
+  // make_elf_object hooks.  There are four versions of these for
+  // different address sizes and endianities.
+  
+#ifdef HAVE_TARGET_32_LITTLE
+  // Virtual functions which may be overriden by the child class.
+  virtual Object*
+  do_make_elf_object(const std::string& name, Input_file* input_file,
+		     off_t offset, const elfcpp::Ehdr<32, false>& ehdr);
+#endif
+
+#ifdef HAVE_TARGET_32_BIG
+  // Virtual functions which may be overriden by the child class.
+  virtual Object*
+  do_make_elf_object(const std::string& name, Input_file* input_file,
+		     off_t offset, const elfcpp::Ehdr<32, true>& ehdr);
+#endif
+
+#ifdef HAVE_TARGET_64_LITTLE
+  // Virtual functions which may be overriden by the child class.
+  virtual Object*
+  do_make_elf_object(const std::string& name, Input_file* input_file,
+		     off_t offset, const elfcpp::Ehdr<64, false>& ehdr);
+#endif
+
+#ifdef HAVE_TARGET_64_BIG
+  // Virtual functions which may be overriden by the child class.
+  virtual Object*
+  do_make_elf_object(const std::string& name, Input_file* input_file,
+		     off_t offset, const elfcpp::Ehdr<64, true>& ehdr);
+#endif
+
  private:
   Target(const Target&);
   Target& operator=(const Target&);

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2009-08-18 23:42 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2009-08-18  3:12 [PATCH][GOLD] Add make_elf_object target hooks Doug Kwan (關振德)
2009-08-18 14:41 ` Ian Lance Taylor
2009-08-18 16:29   ` Doug Kwan (關振德)
2009-08-18 18:35     ` Ian Lance Taylor
2009-08-18 19:08       ` Doug Kwan (關振德)
2009-08-19  0:02         ` Ian Lance Taylor

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).