1 //===- GNUArchiveReader.h -------------------------------------------------===//
2 //
3 //                     The MCLinker Project
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 #ifndef MCLD_LD_GNUARCHIVEREADER_H
10 #define MCLD_LD_GNUARCHIVEREADER_H
11 
12 #include <mcld/LD/ArchiveReader.h>
13 #include <mcld/LD/Archive.h>
14 
15 namespace mcld {
16 
17 class Module;
18 class Input;
19 class ELFObjectReader;
20 class Archive;
21 class LinkerConfig;
22 
23 /** \class GNUArchiveReader
24  *  \brief GNUArchiveReader reads GNU archive files.
25  */
26 class GNUArchiveReader : public ArchiveReader
27 {
28 public:
29   GNUArchiveReader(Module& pModule, ELFObjectReader& pELFObjectReader);
30 
31   ~GNUArchiveReader();
32 
33   /// readArchive - read an archive, include the needed members, and build up
34   /// the subtree
35   bool readArchive(const LinkerConfig& pConfig, Archive& pArchive);
36 
37   /// isMyFormat
38   bool isMyFormat(Input& input, bool &pContinue) const;
39 
40 private:
41   /// isArchive
42   bool isArchive(const char* pStr) const;
43 
44   /// isThinArchive
45   bool isThinArchive(const char* pStr) const;
46 
47   /// isThinArchive
48   bool isThinArchive(Input& input) const;
49 
50   /// readMemberHeader - read the header of a member in a archive file and then
51   /// return the corresponding archive member (it may be an input object or
52   /// another archive)
53   /// @param pArchiveRoot  - the archive root that holds the strtab (extended
54   ///                        name table)
55   /// @param pArchiveFile  - the archive that contains the needed object
56   /// @param pFileOffset   - file offset of the member header in the archive
57   /// @param pNestedOffset - used when we find a nested archive
58   /// @param pMemberSize   - the file size of this member
59   Input* readMemberHeader(Archive& pArchiveRoot,
60                           Input& pArchiveFile,
61                           uint32_t pFileOffset,
62                           uint32_t& pNestedOffset,
63                           size_t& pMemberSize);
64 
65   /// readSymbolTable - read the archive symbol map (armap)
66   bool readSymbolTable(Archive& pArchive);
67 
68   /// readStringTable - read the strtab for long file name of the archive
69   bool readStringTable(Archive& pArchive);
70 
71   /// shouldIncludeSymbol - given a sym name from armap and check if we should
72   /// include the corresponding archive member, and then return the decision
73   enum Archive::Symbol::Status
74   shouldIncludeSymbol(const llvm::StringRef& pSymName) const;
75 
76   /// includeMember - include the object member in the given file offset, and
77   /// return the size of the object
78   /// @param pConfig - LinkerConfig
79   /// @param pArchiveRoot - the archive root
80   /// @param pFileOffset  - file offset of the member header in the archive
81   size_t includeMember(const LinkerConfig& pConfig,
82                        Archive& pArchiveRoot,
83                        uint32_t pFileOffset);
84 
85   /// includeAllMembers - include all object members. This is called if
86   /// --whole-archive is the attribute for this archive file.
87   bool includeAllMembers(const LinkerConfig& pConfig, Archive& pArchive);
88 
89 private:
90   Module& m_Module;
91   ELFObjectReader& m_ELFObjectReader;
92 };
93 
94 } // namespace of mcld
95 
96 #endif
97 
98